From 7930249a335ca46e2b50fcbe9fc9b4fcb92b9fc3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Thu, 4 May 2023 12:19:25 +0200 Subject: [PATCH 01/45] add getDescription function for GridProperties --- include/crpropa/Grid.h | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) diff --git a/include/crpropa/Grid.h b/include/crpropa/Grid.h index a13d6e4b3..eb4912548 100644 --- a/include/crpropa/Grid.h +++ b/include/crpropa/Grid.h @@ -9,6 +9,8 @@ #include #include +#include +#include #if HAVE_SIMD #include #include @@ -122,6 +124,20 @@ class GridProperties: public Referenced { void setInterpolationType(interpolationType i) { ipol = i; } + + /** show all GridProperty parameters + * @param unit unit for the lengthscale (origin, spacing). Default is 1 = SI units + */ + std::string getDescription(double unit = 1) const { + std::stringstream ss; + ss << "GridProperties:\torigin: " << origin / unit + << "\t" << "Nx: " << Nx << " Ny: " << Ny << " Nz: " << Nz + << "\t" << "spacing: " << spacing / unit + << "\t" << "refletive: " << reflective + << "\t" << "interpolation: " << ipol + << "\n"; + return ss.str(); + } }; /** From 3e307e230f0ee6586fce1a4f5b44bb219b9f441e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Thu, 4 May 2023 16:57:32 +0200 Subject: [PATCH 02/45] update interpolation type for grids * add default interploationType * add getInterpolationType * add getInterpolationTypeName --- include/crpropa/Grid.h | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/include/crpropa/Grid.h b/include/crpropa/Grid.h index eb4912548..2a89fd1be 100644 --- a/include/crpropa/Grid.h +++ b/include/crpropa/Grid.h @@ -134,7 +134,7 @@ class GridProperties: public Referenced { << "\t" << "Nx: " << Nx << " Ny: " << Ny << " Nz: " << Nz << "\t" << "spacing: " << spacing / unit << "\t" << "refletive: " << reflective - << "\t" << "interpolation: " << ipol + << "\t" << "interpolation: " << ipol << "\n"; return ss.str(); } @@ -172,6 +172,7 @@ class Grid: public Referenced { setSpacing(Vector3d(spacing)); setReflective(false); setClipVolume(false); + setInterpolationType(TRILINEAR); } /** Constructor for non-cubic grid @@ -187,6 +188,7 @@ class Grid: public Referenced { setSpacing(Vector3d(spacing)); setReflective(false); setClipVolume(false); + setInterpolationType(TRILINEAR); } /** Constructor for non-cubic grid with spacing vector @@ -202,6 +204,7 @@ class Grid: public Referenced { setSpacing(spacing); setReflective(false); setClipVolume(false); + setInterpolationType(TRILINEAR); } /** Constructor for GridProperties @@ -253,6 +256,21 @@ class Grid: public Referenced { } } + interpolationType getInterpolationType() { + return ipolType; + } + + std::string getInterpolationTypeName() { + if (ipolType == TRILINEAR) + return "TRILINEAR"; + if (ipolType == TRICUBIC) + return "TRICUBIC"; + if (ipolType == NEAREST_NEIGHBOUR) + return "NEAREST_NEIGHBOUR"; + + return "NOT_UNDERSTOOD"; + } + /** returns the position of the lower left front corner of the volume */ Vector3d getOrigin() const { return origin; From 331dd69e195e1523331d87890be006898a8e633b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Thu, 4 May 2023 16:59:31 +0200 Subject: [PATCH 03/45] add possibility to store gridprop for TXT saving --- include/crpropa/GridTools.h | 6 ++++-- src/GridTools.cpp | 29 ++++++++++++++++++++++++++--- 2 files changed, 30 insertions(+), 5 deletions(-) diff --git a/include/crpropa/GridTools.h b/include/crpropa/GridTools.h index d74b24670..7732b0fd7 100644 --- a/include/crpropa/GridTools.h +++ b/include/crpropa/GridTools.h @@ -137,17 +137,19 @@ void loadGridFromTxt(ref_ptr grid, std::string filename, @param grid a vector grid (Grid3f) @param filename name of output file @param conversion multiply every point in grid by a conversion factor + @param storeProperties if true the grid properties are stored as a comment */ void dumpGridToTxt(ref_ptr grid, std::string filename, - double conversion = 1); + double conversion = 1, bool storeProperties = false); /** Dump a Grid1f to a plain text file. @param grid a scalar grid (Grid1f) @param filename name of output file @param conversion multiply every point in grid by a conversion factor + @param storeProperties if true the grid properties are stored as a comment */ void dumpGridToTxt(ref_ptr grid, std::string filename, - double conversion = 1); + double conversion = 1, bool storeProperties = false); #ifdef CRPROPA_HAVE_FFTW3F /** diff --git a/src/GridTools.cpp b/src/GridTools.cpp index 5103cc5fa..d87816275 100644 --- a/src/GridTools.cpp +++ b/src/GridTools.cpp @@ -267,8 +267,9 @@ void loadGridFromTxt(ref_ptr grid, std::string filename, double c) { ss << "load Grid1f: " << filename << " not found"; throw std::runtime_error(ss.str()); } + // skip header lines - while (fin.peek() == '#') + while (fin.peek() == '#') fin.ignore(std::numeric_limits::max(), '\n'); for (int ix = 0; ix < grid->getNx(); ix++) { @@ -285,13 +286,24 @@ void loadGridFromTxt(ref_ptr grid, std::string filename, double c) { fin.close(); } -void dumpGridToTxt(ref_ptr grid, std::string filename, double c) { +void dumpGridToTxt(ref_ptr grid, std::string filename, double c, bool saveProp) { std::ofstream fout(filename.c_str()); if (!fout) { std::stringstream ss; ss << "dump Grid3f: " << filename << " not found"; throw std::runtime_error(ss.str()); } + + // store the properties in the file as header information + if (saveProp) { + fout << "# GridProperties: Type Grid3f" + << "\t" << "origin: " << grid -> getOrigin() + << "\t" << "gridsize: " << grid -> getNx() << " " << grid -> getNy() << " " << grid -> getNz() + << "\t" << "spacing: " << grid -> getSpacing () + << "\t" << "reflective: " << grid -> isReflective() + << "\t" << "interpolation: " << grid -> getInterpolationTypeName() << "\n"; + } + for (int ix = 0; ix < grid->getNx(); ix++) { for (int iy = 0; iy < grid->getNy(); iy++) { for (int iz = 0; iz < grid->getNz(); iz++) { @@ -303,13 +315,24 @@ void dumpGridToTxt(ref_ptr grid, std::string filename, double c) { fout.close(); } -void dumpGridToTxt(ref_ptr grid, std::string filename, double c) { +void dumpGridToTxt(ref_ptr grid, std::string filename, double c, bool saveProp) { std::ofstream fout(filename.c_str()); if (!fout) { std::stringstream ss; ss << "dump Grid1f: " << filename << " not found"; throw std::runtime_error(ss.str()); } + + // save properties as header information + if (saveProp) { + fout << "# GridProperties: Type Grid1f" + << "\t" << "origin: " << grid -> getOrigin() + << "\t" << "gridsize: " << grid -> getNx() << " " << grid -> getNy() << " " << grid -> getNz() + << "\t" << "spacing: " << grid -> getSpacing () + << "\t" << "reflective: " << grid -> isReflective() + << "\t" << "interpolation: " << grid -> getInterpolationTypeName() << "\n"; + } + for (int ix = 0; ix < grid->getNx(); ix++) { for (int iy = 0; iy < grid->getNy(); iy++) { for (int iz = 0; iz < grid->getNz(); iz++) { From 91f373c453c4dd1a1240e7519950961171082ece Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Thu, 4 May 2023 17:13:55 +0200 Subject: [PATCH 04/45] loading function for Grid1f with Gridproperties --- include/crpropa/GridTools.h | 6 ++++ src/GridTools.cpp | 62 +++++++++++++++++++++++++++++++++++++ 2 files changed, 68 insertions(+) diff --git a/include/crpropa/GridTools.h b/include/crpropa/GridTools.h index 7732b0fd7..6542a466c 100644 --- a/include/crpropa/GridTools.h +++ b/include/crpropa/GridTools.h @@ -125,6 +125,12 @@ void dumpGrid(ref_ptr grid, std::string filename, void loadGridFromTxt(ref_ptr grid, std::string filename, double conversion = 1); +/** Load a Grid1f from a plain text file based on the gridproperties stored in the header + @param filename name of the input file + @param conversion multiply every point in a grid by a conversion factor +*/ +ref_ptr loadGrid1fFromTxt(std::string filename, double conversion = 1); + /** Load a Grid1f from a plain text file @param grid a scalar grid (Grid1f) to which the points will be loaded @param filename name of input file diff --git a/src/GridTools.cpp b/src/GridTools.cpp index d87816275..af2bdcd0c 100644 --- a/src/GridTools.cpp +++ b/src/GridTools.cpp @@ -286,6 +286,68 @@ void loadGridFromTxt(ref_ptr grid, std::string filename, double c) { fin.close(); } +ref_ptr loadGrid1fFromTxt(std::string filename, double c) { + std::ifstream fin(filename.c_str()); + if (!fin) { + std::stringstream ss; + ss << "load Grid1f: " << filename << " not found"; + throw std::runtime_error(ss.str()); + } + + // search in header lines for GridProperties + while (fin.peek() == '#') { + std::string line; + std::getline(fin, line); + + // find gridproperties in the header + if (line.rfind("GridProperties:") == 2) { + GridProperties gp(Vector3d(0.), 1, 1, 1, 1.); // simple grid properties for default + std::stringstream ss(line); + + // skip first names and check type + std::string name, type; + ss >> name >> name >> name >> type; + if (type != "Grid1f") + throw std::runtime_error("try to load Grid1f, but Gridproperties assume grid type " + type); + + // grid origin + double x, y, z; + ss >> name >> x >> y >> z ; + gp.origin = Vector3d(x, y, z); + + // grid size + ss >> name >> gp.Nx >> gp.Ny >> gp.Nz; + + // spacing + double dX, dY, dZ; + ss >> name >> dX >> dY >> dZ; + gp.spacing = Vector3d(dX, dY, dZ); + + // reflective + ss >> name >> gp.reflective; + + // interpolation type + ss >> name >> type; + if (type == "TRICUBIC") + gp.setInterpolationType(TRICUBIC); + else if (type == "NEAREST_NEIGHBOUR") + gp.setInterpolationType(NEAREST_NEIGHBOUR); + else + gp.setInterpolationType(TRILINEAR); + + // create new grid + ref_ptr grid = new Grid1f(gp); + fin.close(); + + // load data for grid + loadGridFromTxt(grid, filename, c); + + return grid; + } + } + std::runtime_error("could not find GridProperties in file " + filename); +} + void dumpGridToTxt(ref_ptr grid, std::string filename, double c, bool saveProp) { std::ofstream fout(filename.c_str()); if (!fout) { From 5632e8f1fb87817208f084d20d6077a21452e0ba Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Thu, 4 May 2023 17:28:23 +0200 Subject: [PATCH 05/45] loading function for Grid3f with Gridproperties --- include/crpropa/GridTools.h | 6 ++++ src/GridTools.cpp | 63 +++++++++++++++++++++++++++++++++++++ 2 files changed, 69 insertions(+) diff --git a/include/crpropa/GridTools.h b/include/crpropa/GridTools.h index 6542a466c..62be8efa8 100644 --- a/include/crpropa/GridTools.h +++ b/include/crpropa/GridTools.h @@ -117,6 +117,12 @@ void dumpGrid(ref_ptr grid, std::string filename, void dumpGrid(ref_ptr grid, std::string filename, double conversion = 1); +/** Load a Grid3f from a plain text file based on the gridproperties stored in the header + @param filename name of the input file + @param conversion multiply every point in a grid by a conversion factor +*/ +ref_ptr loadGrid3fFromTxt(std::string filename, double conversion = 1); + /** Load a Grid3f grid from a plain text file. @param grid a vector grid (Grid3f) to which the points will be loaded @param filename name of input file diff --git a/src/GridTools.cpp b/src/GridTools.cpp index af2bdcd0c..d7da0961c 100644 --- a/src/GridTools.cpp +++ b/src/GridTools.cpp @@ -260,6 +260,69 @@ void loadGridFromTxt(ref_ptr grid, std::string filename, double c) { fin.close(); } +ref_ptr loadGrid3fFromTxt(std::string filename, double c) { + std::ifstream fin(filename.c_str()); + if (!fin) { + std::stringstream ss; + ss << "load Grid3f: " << filename << " not found"; + throw std::runtime_error(ss.str()); + } + + // search in header lines for GridProperties + while (fin.peek() == '#') { + std::string line; + std::getline(fin, line); + + // find gridproperties in the header + if (line.rfind("GridProperties:") == 2) { + GridProperties gp(Vector3d(0.), 1, 1, 1, 1.); // simple grid properties for default + std::stringstream ss(line); + + // skip first names and check type + std::string name, type; + ss >> name >> name >> name >> type; + if (type != "Grid3f") + throw std::runtime_error("try to load Grid3f, but Gridproperties assume grid type " + type); + + // grid origin + double x, y, z; + ss >> name >> x >> y >> z ; + gp.origin = Vector3d(x, y, z); + + // grid size + ss >> name >> gp.Nx >> gp.Ny >> gp.Nz; + + // spacing + double dX, dY, dZ; + ss >> name >> dX >> dY >> dZ; + gp.spacing = Vector3d(dX, dY, dZ); + + // reflective + ss >> name >> gp.reflective; + + // interpolation type + ss >> name >> type; + if (type == "TRICUBIC") + gp.setInterpolationType(TRICUBIC); + else if (type == "NEAREST_NEIGHBOUR") + gp.setInterpolationType(NEAREST_NEIGHBOUR); + else + gp.setInterpolationType(TRILINEAR); + + // create new grid + ref_ptr grid = new Grid3f(gp); + fin.close(); + + // load data for grid + loadGridFromTxt(grid, filename, c); + + return grid; + } + } + std::runtime_error("could not find GridProperties in file " + filename); +} + + void loadGridFromTxt(ref_ptr grid, std::string filename, double c) { std::ifstream fin(filename.c_str()); if (!fin) { From 6c9ff3edac7aa5cc35e6eb02fef987a786118235 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Mon, 8 May 2023 09:10:42 +0200 Subject: [PATCH 06/45] add tests for grid loading with properties --- test/testCore.cpp | 108 ++++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 105 insertions(+), 3 deletions(-) diff --git a/test/testCore.cpp b/test/testCore.cpp index 72e4a6c78..1ec69d185 100644 --- a/test/testCore.cpp +++ b/test/testCore.cpp @@ -861,6 +861,111 @@ TEST(Grid3f, DumpLoadTxt) { } } +TEST(Grid1f, DumpLoadTxtGridProperties) { + // grid to dump + ref_ptr grid = new Grid1f(Vector3d(0.5, 1.5, 2.5), 3, 2, 4, Vector3d(0.2, 1.2, 2.2)); + grid -> setInterpolationType(TRICUBIC); + grid -> setReflective(true); + + // set some values for the grid + for (int ix = 0; ix < grid -> getNx(); ix++) { + for (int iy = 0; iy < grid -> getNy(); iy++) { + for (int iz = 0; iz < grid -> getNz(); iz++) + grid -> get(ix, iy, iz) = ix + iy + iz; + } + } + + // store with properties + dumpGridToTxt(grid, "testDump.txt", 1., true); + + // reload grid + ref_ptr loadedGrid = loadGrid1fFromTxt("testDump.txt"); + + // check grid properties + EXPECT_EQ(grid -> getNx(), loadedGrid -> getNx()); + EXPECT_EQ(grid -> getNy(), loadedGrid -> getNy()); + EXPECT_EQ(grid -> getNz(), loadedGrid -> getNz()); + + Vector3d orig = grid -> getOrigin(); + Vector3d loadedOrigin = loadedGrid -> getOrigin(); + EXPECT_EQ(orig.x, loadedOrigin.x); + EXPECT_EQ(orig.y, loadedOrigin.y); + EXPECT_EQ(orig.z, loadedOrigin.z); + + Vector3d spacing = grid -> getSpacing(); + Vector3d loadedSpacing = loadedGrid -> getSpacing(); + EXPECT_EQ(spacing.x, loadedSpacing.x); + EXPECT_EQ(spacing.y, loadedSpacing.y); + EXPECT_EQ(spacing.z, loadedSpacing.z); + + EXPECT_EQ(grid -> getInterpolationType(), loadedGrid -> getInterpolationType()); + + EXPECT_EQ(grid -> isReflective(), loadedGrid -> isReflective()); + + // compare loaded values + for (int ix = 0; ix < grid -> getNx(); ix++) { + for (int iy = 0; iy < grid -> getNy(); iy++) { + for (int iz = 0; iz < grid -> getNz(); iz++) + EXPECT_EQ(grid -> get(ix, iy, iz), loadedGrid -> get(ix, iy, iz)); + } + } +} + +TEST(Grid3f, DumpLoadTxtGridProperties) { + // grid to dump + ref_ptr grid = new Grid3f(Vector3d(0.5, 1.5, 2.5), 3, 2, 4, Vector3d(0.2, 1.2, 2.2)); + grid -> setInterpolationType(NEAREST_NEIGHBOUR); + grid -> setReflective(true); + + // set some values for the grid + for (int ix = 0; ix < grid -> getNx(); ix++) { + for (int iy = 0; iy < grid -> getNy(); iy++) { + for (int iz = 0; iz < grid -> getNz(); iz++) + grid -> get(ix, iy, iz) = Vector3f(-iy, ix, 2 * iz); + } + } + + // store with properties + dumpGridToTxt(grid, "testDump.txt", 1., true); + + // reload grid + ref_ptr loadedGrid = loadGrid3fFromTxt("testDump.txt"); + + // check grid properties + EXPECT_EQ(grid -> getNx(), loadedGrid -> getNx()); + EXPECT_EQ(grid -> getNy(), loadedGrid -> getNy()); + EXPECT_EQ(grid -> getNz(), loadedGrid -> getNz()); + + Vector3d orig = grid -> getOrigin(); + Vector3d loadedOrigin = loadedGrid -> getOrigin(); + EXPECT_EQ(orig.x, loadedOrigin.x); + EXPECT_EQ(orig.y, loadedOrigin.y); + EXPECT_EQ(orig.z, loadedOrigin.z); + + Vector3d spacing = grid -> getSpacing(); + Vector3d loadedSpacing = loadedGrid -> getSpacing(); + EXPECT_EQ(spacing.x, loadedSpacing.x); + EXPECT_EQ(spacing.y, loadedSpacing.y); + EXPECT_EQ(spacing.z, loadedSpacing.z); + + EXPECT_EQ(grid -> getInterpolationType(), loadedGrid -> getInterpolationType()); + + EXPECT_EQ(grid -> isReflective(), loadedGrid -> isReflective()); + + // compare loaded values + for (int ix = 0; ix < grid -> getNx(); ix++) { + for (int iy = 0; iy < grid -> getNy(); iy++) { + for (int iz = 0; iz < grid -> getNz(); iz++) { + Vector3f gridValue = grid -> get(ix, iy, iz); + Vector3f loadedValue = loadedGrid -> get(ix, iy, iz); + EXPECT_EQ(gridValue.x, loadedValue.x); + EXPECT_EQ(gridValue.y, loadedValue.y); + EXPECT_EQ(gridValue.z, loadedValue.z); + } + } + } +} + TEST(Grid3f, Speed) { // Dump and load a field grid Grid3f grid(Vector3d(0.), 3, 3); @@ -880,8 +985,6 @@ TEST(CylindricalProjectionMap, functions) { EXPECT_NEAR(v.getPhi(), 2.4, .00001); EXPECT_NEAR(v.getTheta(), 1.2, .000001); - - CylindricalProjectionMap cpm(24, 12); size_t bin = 50; Vector3d d = cpm.directionFromBin(bin); @@ -910,7 +1013,6 @@ TEST(EmissionMap, functions) { r = em.drawDirection(2, 50 * EeV, d2); EXPECT_FALSE(r); - } TEST(EmissionMap, merge) { From f4c8b4e208f277a750f203270005449167b2fd5b Mon Sep 17 00:00:00 2001 From: Julien Date: Mon, 8 Apr 2024 16:41:30 +0200 Subject: [PATCH 07/45] add lxml to documentation dependency --- .github/workflows/create_documentation.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/create_documentation.yml b/.github/workflows/create_documentation.yml index 5888cfc81..91c4097d3 100644 --- a/.github/workflows/create_documentation.yml +++ b/.github/workflows/create_documentation.yml @@ -31,7 +31,7 @@ jobs: sudo apt-get install libmuparser-dev libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov doxygen graphviz sudo apt-get install pandoc # do not only use pip to install pandoc, see https://stackoverflow.com/questions/62398231/building-docs-fails-due-to-missing-pandoc pip install -r doc/pages/example_notebooks/requirements.txt # load requirements for notebooks - pip install sphinx sphinx_rtd_theme m2r2 nbsphinx breathe pandoc exhale # load requirements for documentation + pip install sphinx sphinx_rtd_theme m2r2 nbsphinx lxml breathe pandoc exhale # load requirements for documentation - name: Set up the build env: CXX: ${{ matrix.config.cxx }} From b471b831796b4575cb2d29708d6262335b3242a5 Mon Sep 17 00:00:00 2001 From: Julien Date: Mon, 8 Apr 2024 16:53:34 +0200 Subject: [PATCH 08/45] change lxml to lxml_html_clean --- .github/workflows/create_documentation.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/create_documentation.yml b/.github/workflows/create_documentation.yml index c3b885133..b176fbca4 100644 --- a/.github/workflows/create_documentation.yml +++ b/.github/workflows/create_documentation.yml @@ -27,7 +27,7 @@ jobs: sudo apt-get install libmuparser-dev libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov doxygen graphviz sudo apt-get install pandoc # do not only use pip to install pandoc, see https://stackoverflow.com/questions/62398231/building-docs-fails-due-to-missing-pandoc pip install -r doc/pages/example_notebooks/requirements.txt # load requirements for notebooks - pip install sphinx sphinx_rtd_theme m2r2 nbsphinx lxml breathe pandoc exhale # load requirements for documentation + pip install sphinx sphinx_rtd_theme m2r2 nbsphinx lxml_html_clean breathe pandoc exhale # load requirements for documentation - name: Set up the build env: CXX: ${{ matrix.config.cxx }} From 1be2ecbb62d8e256843da49810ce38f267fb5a3d Mon Sep 17 00:00:00 2001 From: Julien Date: Tue, 9 Apr 2024 08:13:27 +0200 Subject: [PATCH 09/45] add coverage Report to documentation --- doc/coverageReport/amber.png | Bin 0 -> 141 bytes doc/coverageReport/emerald.png | Bin 0 -> 141 bytes doc/coverageReport/gcov.css | 519 +++++ doc/coverageReport/glass.png | Bin 0 -> 167 bytes .../numpy/__multiarray_api.h.func-sort-c.html | 76 + .../numpy/__multiarray_api.h.func.html | 76 + .../numpy/__multiarray_api.h.gcov.html | 1642 +++++++++++++ .../numpy/__ufunc_api.h.func-sort-c.html | 76 + .../include/numpy/__ufunc_api.h.func.html | 76 + .../include/numpy/__ufunc_api.h.gcov.html | 390 ++++ .../core/include/numpy/index-sort-f.html | 113 + .../core/include/numpy/index-sort-l.html | 113 + .../numpy/core/include/numpy/index.html | 113 + .../numpy/ndarraytypes.h.func-sort-c.html | 72 + .../include/numpy/ndarraytypes.h.func.html | 72 + .../include/numpy/ndarraytypes.h.gcov.html | 2021 ++++++++++++++++ .../crpropa/AssocVector.h.func-sort-c.html | 92 + .../include/crpropa/AssocVector.h.func.html | 92 + .../include/crpropa/AssocVector.h.gcov.html | 457 ++++ .../crpropa/Candidate.h.func-sort-c.html | 72 + .../include/crpropa/Candidate.h.func.html | 72 + .../include/crpropa/Candidate.h.gcov.html | 258 ++ .../include/crpropa/Common.h.func-sort-c.html | 80 + .../include/crpropa/Common.h.func.html | 80 + .../include/crpropa/Common.h.gcov.html | 163 ++ .../crpropa/EmissionMap.h.func-sort-c.html | 72 + .../include/crpropa/EmissionMap.h.func.html | 72 + .../include/crpropa/EmissionMap.h.gcov.html | 212 ++ .../crpropa/Geometry.h.func-sort-c.html | 76 + .../include/crpropa/Geometry.h.func.html | 76 + .../include/crpropa/Geometry.h.gcov.html | 165 ++ .../include/crpropa/Grid.h.func-sort-c.html | 296 +++ .../include/crpropa/Grid.h.func.html | 296 +++ .../include/crpropa/Grid.h.gcov.html | 640 +++++ .../crpropa/Logging.h.func-sort-c.html | 96 + .../include/crpropa/Logging.h.func.html | 96 + .../include/crpropa/Logging.h.gcov.html | 111 + .../include/crpropa/Module.h.func-sort-c.html | 72 + .../include/crpropa/Module.h.func.html | 72 + .../include/crpropa/Module.h.gcov.html | 141 ++ .../crpropa/ParticleState.h.func-sort-c.html | 72 + .../include/crpropa/ParticleState.h.func.html | 72 + .../include/crpropa/ParticleState.h.gcov.html | 196 ++ .../PhotonBackground.h.func-sort-c.html | 148 ++ .../crpropa/PhotonBackground.h.func.html | 148 ++ .../crpropa/PhotonBackground.h.gcov.html | 398 ++++ .../include/crpropa/Random.h.func-sort-c.html | 72 + .../include/crpropa/Random.h.func.html | 72 + .../include/crpropa/Random.h.gcov.html | 317 +++ .../crpropa/Referenced.h.func-sort-c.html | 148 ++ .../include/crpropa/Referenced.h.func.html | 148 ++ .../include/crpropa/Referenced.h.gcov.html | 320 +++ .../include/crpropa/Source.h.func-sort-c.html | 76 + .../include/crpropa/Source.h.func.html | 76 + .../include/crpropa/Source.h.gcov.html | 1002 ++++++++ .../crpropa/Variant.h.func-sort-c.html | 136 ++ .../include/crpropa/Variant.h.func.html | 136 ++ .../include/crpropa/Variant.h.gcov.html | 410 ++++ .../crpropa/Vector3.h.func-sort-c.html | 236 ++ .../include/crpropa/Vector3.h.func.html | 236 ++ .../include/crpropa/Vector3.h.gcov.html | 516 ++++ .../AdvectionField.h.func-sort-c.html | 72 + .../advectionField/AdvectionField.h.func.html | 72 + .../advectionField/AdvectionField.h.gcov.html | 367 +++ .../crpropa/advectionField/index-sort-f.html | 93 + .../crpropa/advectionField/index-sort-l.html | 93 + .../include/crpropa/advectionField/index.html | 93 + .../include/crpropa/index-sort-f.html | 233 ++ .../include/crpropa/index-sort-l.html | 233 ++ doc/coverageReport/include/crpropa/index.html | 233 ++ .../GalacticMagneticField.h.func-sort-c.html | 88 + .../GalacticMagneticField.h.func.html | 88 + .../GalacticMagneticField.h.gcov.html | 210 ++ .../MagneticField.h.func-sort-c.html | 100 + .../magneticField/MagneticField.h.func.html | 100 + .../magneticField/MagneticField.h.gcov.html | 248 ++ .../MagneticFieldGrid.h.func-sort-c.html | 72 + .../MagneticFieldGrid.h.func.html | 72 + .../MagneticFieldGrid.h.gcov.html | 139 ++ .../crpropa/magneticField/index-sort-f.html | 113 + .../crpropa/magneticField/index-sort-l.html | 113 + .../include/crpropa/magneticField/index.html | 113 + .../GridTurbulence.h.func-sort-c.html | 72 + .../turbulentField/GridTurbulence.h.func.html | 72 + .../turbulentField/GridTurbulence.h.gcov.html | 151 ++ .../HelicalGridTurbulence.h.func-sort-c.html | 76 + .../HelicalGridTurbulence.h.func.html | 76 + .../HelicalGridTurbulence.h.gcov.html | 147 ++ .../SimpleGridTurbulence.h.func-sort-c.html | 100 + .../SimpleGridTurbulence.h.func.html | 100 + .../SimpleGridTurbulence.h.gcov.html | 192 ++ .../TurbulentField.h.func-sort-c.html | 108 + .../turbulentField/TurbulentField.h.func.html | 108 + .../turbulentField/TurbulentField.h.gcov.html | 195 ++ .../turbulentField/index-sort-f.html | 123 + .../turbulentField/index-sort-l.html | 123 + .../magneticField/turbulentField/index.html | 123 + .../MagneticLens.h.func-sort-c.html | 96 + .../magneticLens/MagneticLens.h.func.html | 96 + .../magneticLens/MagneticLens.h.gcov.html | 352 +++ .../ParticleMapsContainer.h.func-sort-c.html | 80 + .../ParticleMapsContainer.h.func.html | 80 + .../ParticleMapsContainer.h.gcov.html | 221 ++ .../Pixelization.h.func-sort-c.html | 84 + .../magneticLens/Pixelization.h.func.html | 84 + .../magneticLens/Pixelization.h.gcov.html | 217 ++ .../crpropa/magneticLens/index-sort-f.html | 113 + .../crpropa/magneticLens/index-sort-l.html | 113 + .../include/crpropa/magneticLens/index.html | 113 + .../Cordes.h.func-sort-c.html | 72 + .../massDistribution/Cordes.h.func.html | 72 + .../massDistribution/Cordes.h.gcov.html | 121 + .../Density.h.func-sort-c.html | 116 + .../massDistribution/Density.h.func.html | 116 + .../massDistribution/Density.h.gcov.html | 134 ++ .../Ferriere.h.func-sort-c.html | 72 + .../massDistribution/Ferriere.h.func.html | 72 + .../massDistribution/Ferriere.h.gcov.html | 153 ++ .../Massdistribution.h.func-sort-c.html | 72 + .../Massdistribution.h.func.html | 72 + .../Massdistribution.h.gcov.html | 212 ++ .../Nakanishi.h.func-sort-c.html | 72 + .../massDistribution/Nakanishi.h.func.html | 72 + .../massDistribution/Nakanishi.h.gcov.html | 150 ++ .../massDistribution/index-sort-f.html | 133 ++ .../massDistribution/index-sort-l.html | 133 ++ .../crpropa/massDistribution/index.html | 133 ++ .../module/Boundary.h.func-sort-c.html | 72 + .../crpropa/module/Boundary.h.func.html | 72 + .../crpropa/module/Boundary.h.gcov.html | 283 +++ .../module/BreakCondition.h.func-sort-c.html | 72 + .../crpropa/module/BreakCondition.h.func.html | 72 + .../crpropa/module/BreakCondition.h.gcov.html | 221 ++ .../module/HDF5Output.h.func-sort-c.html | 72 + .../crpropa/module/HDF5Output.h.func.html | 72 + .../crpropa/module/HDF5Output.h.gcov.html | 217 ++ .../module/NuclearDecay.h.func-sort-c.html | 72 + .../crpropa/module/NuclearDecay.h.func.html | 72 + .../crpropa/module/NuclearDecay.h.gcov.html | 163 ++ .../module/Observer.h.func-sort-c.html | 72 + .../crpropa/module/Observer.h.func.html | 72 + .../crpropa/module/Observer.h.gcov.html | 351 +++ .../module/OutputShell.h.func-sort-c.html | 72 + .../crpropa/module/OutputShell.h.func.html | 72 + .../crpropa/module/OutputShell.h.gcov.html | 124 + .../PhotoDisintegration.h.func-sort-c.html | 72 + .../module/PhotoDisintegration.h.func.html | 72 + .../module/PhotoDisintegration.h.gcov.html | 167 ++ .../module/PropagationBP.h.func-sort-c.html | 72 + .../crpropa/module/PropagationBP.h.func.html | 72 + .../crpropa/module/PropagationBP.h.gcov.html | 225 ++ .../module/PropagationCK.h.func-sort-c.html | 72 + .../crpropa/module/PropagationCK.h.func.html | 72 + .../crpropa/module/PropagationCK.h.gcov.html | 178 ++ .../module/Redshift.h.func-sort-c.html | 72 + .../crpropa/module/Redshift.h.func.html | 72 + .../crpropa/module/Redshift.h.gcov.html | 111 + .../SimplePropagation.h.func-sort-c.html | 72 + .../module/SimplePropagation.h.func.html | 72 + .../module/SimplePropagation.h.gcov.html | 115 + .../module/TextOutput.h.func-sort-c.html | 72 + .../crpropa/module/TextOutput.h.func.html | 72 + .../crpropa/module/TextOutput.h.gcov.html | 155 ++ .../crpropa/module/Tools.h.func-sort-c.html | 72 + .../include/crpropa/module/Tools.h.func.html | 72 + .../include/crpropa/module/Tools.h.gcov.html | 150 ++ .../include/crpropa/module/index-sort-f.html | 213 ++ .../include/crpropa/module/index-sort-l.html | 213 ++ .../include/crpropa/module/index.html | 213 ++ doc/coverageReport/index-sort-f.html | 293 +++ doc/coverageReport/index-sort-l.html | 293 +++ doc/coverageReport/index.html | 293 +++ .../src/ParticleIDMethods.cc.func-sort-c.html | 200 ++ .../HepPID/src/ParticleIDMethods.cc.func.html | 200 ++ .../HepPID/src/ParticleIDMethods.cc.gcov.html | 641 +++++ .../src/ParticleName.cc.func-sort-c.html | 124 + .../libs/HepPID/src/ParticleName.cc.func.html | 124 + .../libs/HepPID/src/ParticleName.cc.gcov.html | 2075 +++++++++++++++++ .../HepPID/src/Version.cc.func-sort-c.html | 84 + .../libs/HepPID/src/Version.cc.func.html | 84 + .../libs/HepPID/src/Version.cc.gcov.html | 106 + .../libs/HepPID/src/index-sort-f.html | 113 + .../libs/HepPID/src/index-sort-l.html | 113 + doc/coverageReport/libs/HepPID/src/index.html | 113 + .../error_handling.cc.func-sort-c.html | 100 + .../healpix_base/error_handling.cc.func.html | 100 + .../healpix_base/error_handling.cc.gcov.html | 136 ++ .../geom_utils.cc.func-sort-c.html | 84 + .../libs/healpix_base/geom_utils.cc.func.html | 84 + .../libs/healpix_base/geom_utils.cc.gcov.html | 151 ++ .../healpix_base.cc.func-sort-c.html | 436 ++++ .../healpix_base/healpix_base.cc.func.html | 436 ++++ .../healpix_base/healpix_base.cc.gcov.html | 1454 ++++++++++++ .../alloc_utils.h.func-sort-c.html | 96 + .../healpix_base/alloc_utils.h.func.html | 96 + .../healpix_base/alloc_utils.h.gcov.html | 154 ++ .../healpix_base/arr.h.func-sort-c.html | 76 + .../include/healpix_base/arr.h.func.html | 76 + .../include/healpix_base/arr.h.gcov.html | 734 ++++++ .../error_handling.h.func-sort-c.html | 76 + .../healpix_base/error_handling.h.func.html | 76 + .../healpix_base/error_handling.h.gcov.html | 180 ++ .../geom_utils.h.func-sort-c.html | 80 + .../healpix_base/geom_utils.h.func.html | 80 + .../healpix_base/geom_utils.h.gcov.html | 161 ++ .../healpix_base.h.func-sort-c.html | 208 ++ .../healpix_base/healpix_base.h.func.html | 208 ++ .../healpix_base/healpix_base.h.gcov.html | 457 ++++ .../include/healpix_base/index-sort-f.html | 173 ++ .../include/healpix_base/index-sort-l.html | 173 ++ .../include/healpix_base/index.html | 173 ++ .../math_utils.h.func-sort-c.html | 88 + .../healpix_base/math_utils.h.func.html | 88 + .../healpix_base/math_utils.h.gcov.html | 259 ++ .../healpix_base/pointing.h.func-sort-c.html | 72 + .../include/healpix_base/pointing.h.func.html | 72 + .../include/healpix_base/pointing.h.gcov.html | 161 ++ .../healpix_base/rangeset.h.func-sort-c.html | 120 + .../include/healpix_base/rangeset.h.func.html | 120 + .../include/healpix_base/rangeset.h.gcov.html | 363 +++ .../healpix_base/vec3.h.func-sort-c.html | 80 + .../include/healpix_base/vec3.h.func.html | 80 + .../include/healpix_base/vec3.h.gcov.html | 229 ++ .../libs/healpix_base/index-sort-f.html | 123 + .../libs/healpix_base/index-sort-l.html | 123 + .../libs/healpix_base/index.html | 123 + .../healpix_base/pointing.cc.func-sort-c.html | 92 + .../libs/healpix_base/pointing.cc.func.html | 92 + .../libs/healpix_base/pointing.cc.gcov.html | 148 ++ .../include/kiss/convert.h.func-sort-c.html | 76 + .../kiss/include/kiss/convert.h.func.html | 76 + .../kiss/include/kiss/convert.h.gcov.html | 150 ++ .../libs/kiss/include/kiss/index-sort-f.html | 103 + .../libs/kiss/include/kiss/index-sort-l.html | 103 + .../libs/kiss/include/kiss/index.html | 103 + .../include/kiss/logger.h.func-sort-c.html | 336 +++ .../libs/kiss/include/kiss/logger.h.func.html | 336 +++ .../libs/kiss/include/kiss/logger.h.gcov.html | 131 ++ .../libs/kiss/src/index-sort-f.html | 113 + .../libs/kiss/src/index-sort-l.html | 113 + doc/coverageReport/libs/kiss/src/index.html | 113 + .../libs/kiss/src/logger.cpp.func-sort-c.html | 104 + .../libs/kiss/src/logger.cpp.func.html | 104 + .../libs/kiss/src/logger.cpp.gcov.html | 161 ++ .../libs/kiss/src/path.cpp.func-sort-c.html | 104 + .../libs/kiss/src/path.cpp.func.html | 104 + .../libs/kiss/src/path.cpp.gcov.html | 245 ++ .../libs/kiss/src/string.cpp.func-sort-c.html | 100 + .../libs/kiss/src/string.cpp.func.html | 100 + .../libs/kiss/src/string.cpp.gcov.html | 165 ++ doc/coverageReport/ruby.png | Bin 0 -> 141 bytes doc/coverageReport/snow.png | Bin 0 -> 141 bytes .../src/Candidate.cpp.func-sort-c.html | 212 ++ .../src/Candidate.cpp.func.html | 212 ++ .../src/Candidate.cpp.gcov.html | 331 +++ .../src/Clock.cpp.func-sort-c.html | 104 + doc/coverageReport/src/Clock.cpp.func.html | 104 + doc/coverageReport/src/Clock.cpp.gcov.html | 231 ++ .../src/Common.cpp.func-sort-c.html | 96 + doc/coverageReport/src/Common.cpp.func.html | 96 + doc/coverageReport/src/Common.cpp.gcov.html | 212 ++ .../src/Cosmology.cpp.func-sort-c.html | 132 ++ .../src/Cosmology.cpp.func.html | 132 ++ .../src/Cosmology.cpp.gcov.html | 245 ++ .../src/EmissionMap.cpp.func-sort-c.html | 204 ++ .../src/EmissionMap.cpp.func.html | 204 ++ .../src/EmissionMap.cpp.gcov.html | 370 +++ .../src/Geometry.cpp.func-sort-c.html | 124 + doc/coverageReport/src/Geometry.cpp.func.html | 124 + doc/coverageReport/src/Geometry.cpp.gcov.html | 200 ++ .../src/GridTools.cpp.func-sort-c.html | 148 ++ .../src/GridTools.cpp.func.html | 148 ++ .../src/GridTools.cpp.gcov.html | 491 ++++ .../src/Module.cpp.func-sort-c.html | 120 + doc/coverageReport/src/Module.cpp.func.html | 120 + doc/coverageReport/src/Module.cpp.gcov.html | 156 ++ .../src/ParticleID.cpp.func-sort-c.html | 92 + .../src/ParticleID.cpp.func.html | 92 + .../src/ParticleID.cpp.gcov.html | 130 ++ .../src/ParticleMass.cpp.func-sort-c.html | 88 + .../src/ParticleMass.cpp.func.html | 88 + .../src/ParticleMass.cpp.gcov.html | 150 ++ .../src/ParticleState.cpp.func-sort-c.html | 140 ++ .../src/ParticleState.cpp.func.html | 140 ++ .../src/ParticleState.cpp.gcov.html | 178 ++ .../src/PhotonBackground.cpp.func-sort-c.html | 132 ++ .../src/PhotonBackground.cpp.func.html | 132 ++ .../src/PhotonBackground.cpp.gcov.html | 291 +++ .../src/ProgressBar.cpp.func-sort-c.html | 92 + .../src/ProgressBar.cpp.func.html | 92 + .../src/ProgressBar.cpp.gcov.html | 153 ++ .../src/Random.cpp.func-sort-c.html | 256 ++ doc/coverageReport/src/Random.cpp.func.html | 256 ++ doc/coverageReport/src/Random.cpp.gcov.html | 605 +++++ .../src/Source.cpp.func-sort-c.html | 656 ++++++ doc/coverageReport/src/Source.cpp.func.html | 656 ++++++ doc/coverageReport/src/Source.cpp.gcov.html | 1218 ++++++++++ .../src/Variant.cpp.func-sort-c.html | 264 +++ doc/coverageReport/src/Variant.cpp.func.html | 264 +++ doc/coverageReport/src/Variant.cpp.gcov.html | 1200 ++++++++++ .../AdvectionField.cpp.func-sort-c.html | 408 ++++ .../AdvectionField.cpp.func.html | 408 ++++ .../AdvectionField.cpp.gcov.html | 610 +++++ .../src/advectionField/index-sort-f.html | 93 + .../src/advectionField/index-sort-l.html | 93 + .../src/advectionField/index.html | 93 + .../src/base64.cpp.func-sort-c.html | 80 + doc/coverageReport/src/base64.cpp.func.html | 80 + doc/coverageReport/src/base64.cpp.gcov.html | 205 ++ doc/coverageReport/src/index-sort-f.html | 253 ++ doc/coverageReport/src/index-sort-l.html | 253 ++ doc/coverageReport/src/index.html | 253 ++ ...rchimedeanSpiralField.cpp.func-sort-c.html | 112 + .../ArchimedeanSpiralField.cpp.func.html | 112 + .../ArchimedeanSpiralField.cpp.gcov.html | 162 ++ .../CMZField.cpp.func-sort-c.html | 144 ++ .../src/magneticField/CMZField.cpp.func.html | 144 ++ .../src/magneticField/CMZField.cpp.gcov.html | 382 +++ .../JF12Field.cpp.func-sort-c.html | 188 ++ .../src/magneticField/JF12Field.cpp.func.html | 188 ++ .../src/magneticField/JF12Field.cpp.gcov.html | 452 ++++ .../JF12FieldSolenoidal.cpp.func-sort-c.html | 128 + .../JF12FieldSolenoidal.cpp.func.html | 128 + .../JF12FieldSolenoidal.cpp.gcov.html | 378 +++ .../MagneticField.cpp.func-sort-c.html | 136 ++ .../magneticField/MagneticField.cpp.func.html | 136 ++ .../magneticField/MagneticField.cpp.gcov.html | 188 ++ .../MagneticFieldGrid.cpp.func-sort-c.html | 116 + .../MagneticFieldGrid.cpp.func.html | 116 + .../MagneticFieldGrid.cpp.gcov.html | 133 ++ .../PT11Field.cpp.func-sort-c.html | 108 + .../src/magneticField/PT11Field.cpp.func.html | 108 + .../src/magneticField/PT11Field.cpp.gcov.html | 206 ++ ...ngleModeMagneticField.cpp.func-sort-c.html | 80 + ...rizedSingleModeMagneticField.cpp.func.html | 80 + ...rizedSingleModeMagneticField.cpp.gcov.html | 142 ++ .../TF17Field.cpp.func-sort-c.html | 188 ++ .../src/magneticField/TF17Field.cpp.func.html | 188 ++ .../src/magneticField/TF17Field.cpp.gcov.html | 383 +++ .../src/magneticField/index-sort-f.html | 173 ++ .../src/magneticField/index-sort-l.html | 173 ++ .../src/magneticField/index.html | 173 ++ .../GridTurbulence.cpp.func-sort-c.html | 124 + .../GridTurbulence.cpp.func.html | 124 + .../GridTurbulence.cpp.gcov.html | 289 +++ ...HelicalGridTurbulence.cpp.func-sort-c.html | 80 + .../HelicalGridTurbulence.cpp.func.html | 80 + .../HelicalGridTurbulence.cpp.gcov.html | 206 ++ .../PlaneWaveTurbulence.cpp.func-sort-c.html | 80 + .../PlaneWaveTurbulence.cpp.func.html | 80 + .../PlaneWaveTurbulence.cpp.gcov.html | 517 ++++ .../SimpleGridTurbulence.cpp.func-sort-c.html | 80 + .../SimpleGridTurbulence.cpp.func.html | 80 + .../SimpleGridTurbulence.cpp.gcov.html | 193 ++ .../turbulentField/index-sort-f.html | 123 + .../turbulentField/index-sort-l.html | 123 + .../magneticField/turbulentField/index.html | 123 + .../MagneticLens.cpp.func-sort-c.html | 124 + .../magneticLens/MagneticLens.cpp.func.html | 124 + .../magneticLens/MagneticLens.cpp.gcov.html | 353 +++ .../ModelMatrix.cpp.func-sort-c.html | 100 + .../magneticLens/ModelMatrix.cpp.func.html | 100 + .../magneticLens/ModelMatrix.cpp.gcov.html | 237 ++ ...ParticleMapsContainer.cpp.func-sort-c.html | 124 + .../ParticleMapsContainer.cpp.func.html | 124 + .../ParticleMapsContainer.cpp.gcov.html | 275 +++ .../Pixelization.cpp.func-sort-c.html | 104 + .../magneticLens/Pixelization.cpp.func.html | 104 + .../magneticLens/Pixelization.cpp.gcov.html | 205 ++ .../src/magneticLens/index-sort-f.html | 123 + .../src/magneticLens/index-sort-l.html | 123 + .../src/magneticLens/index.html | 123 + .../ConstantDensity.cpp.func-sort-c.html | 148 ++ .../ConstantDensity.cpp.func.html | 148 ++ .../ConstantDensity.cpp.gcov.html | 213 ++ .../Cordes.cpp.func-sort-c.html | 100 + .../src/massDistribution/Cordes.cpp.func.html | 100 + .../src/massDistribution/Cordes.cpp.gcov.html | 122 + .../Ferriere.cpp.func-sort-c.html | 128 + .../massDistribution/Ferriere.cpp.func.html | 128 + .../massDistribution/Ferriere.cpp.gcov.html | 349 +++ .../Massdistribution.cpp.func-sort-c.html | 160 ++ .../Massdistribution.cpp.func.html | 160 ++ .../Massdistribution.cpp.gcov.html | 222 ++ .../Nakanishi.cpp.func-sort-c.html | 128 + .../massDistribution/Nakanishi.cpp.func.html | 128 + .../massDistribution/Nakanishi.cpp.gcov.html | 195 ++ .../src/massDistribution/index-sort-f.html | 133 ++ .../src/massDistribution/index-sort-l.html | 133 ++ .../src/massDistribution/index.html | 133 ++ .../module/Acceleration.cpp.func-sort-c.html | 128 + .../src/module/Acceleration.cpp.func.html | 128 + .../src/module/Acceleration.cpp.gcov.html | 260 +++ .../AdiabaticCooling.cpp.func-sort-c.html | 92 + .../src/module/AdiabaticCooling.cpp.func.html | 92 + .../src/module/AdiabaticCooling.cpp.gcov.html | 130 ++ .../src/module/Boundary.cpp.func-sort-c.html | 252 ++ .../src/module/Boundary.cpp.func.html | 252 ++ .../src/module/Boundary.cpp.gcov.html | 370 +++ .../BreakCondition.cpp.func-sort-c.html | 224 ++ .../src/module/BreakCondition.cpp.func.html | 224 ++ .../src/module/BreakCondition.cpp.gcov.html | 343 +++ .../CandidateSplitting.cpp.func-sort-c.html | 116 + .../module/CandidateSplitting.cpp.func.html | 116 + .../module/CandidateSplitting.cpp.gcov.html | 194 ++ .../module/DiffusionSDE.cpp.func-sort-c.html | 172 ++ .../src/module/DiffusionSDE.cpp.func.html | 172 ++ .../src/module/DiffusionSDE.cpp.gcov.html | 480 ++++ ...MDoublePairProduction.cpp.func-sort-c.html | 112 + .../EMDoublePairProduction.cpp.func.html | 112 + .../EMDoublePairProduction.cpp.gcov.html | 209 ++ ...erseComptonScattering.cpp.func-sort-c.html | 124 + .../EMInverseComptonScattering.cpp.func.html | 124 + .../EMInverseComptonScattering.cpp.gcov.html | 325 +++ .../EMPairProduction.cpp.func-sort-c.html | 124 + .../src/module/EMPairProduction.cpp.func.html | 124 + .../src/module/EMPairProduction.cpp.gcov.html | 340 +++ ...TripletPairProduction.cpp.func-sort-c.html | 116 + .../EMTripletPairProduction.cpp.func.html | 116 + .../EMTripletPairProduction.cpp.gcov.html | 263 +++ .../ElasticScattering.cpp.func-sort-c.html | 100 + .../module/ElasticScattering.cpp.func.html | 100 + .../module/ElasticScattering.cpp.gcov.html | 212 ++ ...lectronPairProduction.cpp.func-sort-c.html | 112 + .../ElectronPairProduction.cpp.func.html | 112 + .../ElectronPairProduction.cpp.gcov.html | 233 ++ .../module/HDF5Output.cpp.func-sort-c.html | 128 + .../src/module/HDF5Output.cpp.func.html | 128 + .../src/module/HDF5Output.cpp.gcov.html | 468 ++++ .../MomentumDiffusion.cpp.func-sort-c.html | 112 + .../module/MomentumDiffusion.cpp.func.html | 112 + .../module/MomentumDiffusion.cpp.gcov.html | 147 ++ .../module/NuclearDecay.cpp.func-sort-c.html | 124 + .../src/module/NuclearDecay.cpp.func.html | 124 + .../src/module/NuclearDecay.cpp.gcov.html | 395 ++++ .../src/module/Observer.cpp.func-sort-c.html | 248 ++ .../src/module/Observer.cpp.func.html | 248 ++ .../src/module/Observer.cpp.gcov.html | 427 ++++ .../src/module/Output.cpp.func-sort-c.html | 136 ++ .../src/module/Output.cpp.func.html | 136 ++ .../src/module/Output.cpp.gcov.html | 210 ++ .../module/OutputShell.cpp.func-sort-c.html | 96 + .../src/module/OutputShell.cpp.func.html | 96 + .../src/module/OutputShell.cpp.gcov.html | 134 ++ .../ParticleCollector.cpp.func-sort-c.html | 168 ++ .../module/ParticleCollector.cpp.func.html | 168 ++ .../module/ParticleCollector.cpp.gcov.html | 194 ++ .../PhotoDisintegration.cpp.func-sort-c.html | 120 + .../module/PhotoDisintegration.cpp.func.html | 120 + .../module/PhotoDisintegration.cpp.gcov.html | 406 ++++ .../PhotoPionProduction.cpp.func-sort-c.html | 232 ++ .../module/PhotoPionProduction.cpp.func.html | 232 ++ .../module/PhotoPionProduction.cpp.gcov.html | 758 ++++++ .../PhotonOutput1D.cpp.func-sort-c.html | 108 + .../src/module/PhotonOutput1D.cpp.func.html | 108 + .../src/module/PhotonOutput1D.cpp.gcov.html | 180 ++ .../module/PropagationBP.cpp.func-sort-c.html | 136 ++ .../src/module/PropagationBP.cpp.func.html | 136 ++ .../src/module/PropagationBP.cpp.gcov.html | 285 +++ .../module/PropagationCK.cpp.func-sort-c.html | 128 + .../src/module/PropagationCK.cpp.func.html | 128 + .../src/module/PropagationCK.cpp.gcov.html | 278 +++ .../src/module/Redshift.cpp.func-sort-c.html | 88 + .../src/module/Redshift.cpp.func.html | 88 + .../src/module/Redshift.cpp.gcov.html | 138 ++ .../RestrictToRegion.cpp.func-sort-c.html | 84 + .../src/module/RestrictToRegion.cpp.func.html | 84 + .../src/module/RestrictToRegion.cpp.gcov.html | 101 + .../SimplePropagation.cpp.func-sort-c.html | 100 + .../module/SimplePropagation.cpp.func.html | 100 + .../module/SimplePropagation.cpp.gcov.html | 128 + .../SynchrotronRadiation.cpp.func-sort-c.html | 156 ++ .../module/SynchrotronRadiation.cpp.func.html | 156 ++ .../module/SynchrotronRadiation.cpp.gcov.html | 306 +++ .../module/TextOutput.cpp.func-sort-c.html | 128 + .../src/module/TextOutput.cpp.func.html | 128 + .../src/module/TextOutput.cpp.gcov.html | 457 ++++ .../src/module/Tools.cpp.func-sort-c.html | 136 ++ .../src/module/Tools.cpp.func.html | 136 ++ .../src/module/Tools.cpp.gcov.html | 199 ++ .../src/module/index-sort-f.html | 383 +++ .../src/module/index-sort-l.html | 383 +++ doc/coverageReport/src/module/index.html | 383 +++ doc/coverageReport/test/index-sort-f.html | 243 ++ doc/coverageReport/test/index-sort-l.html | 243 ++ doc/coverageReport/test/index.html | 243 ++ .../testAdiabaticCooling.cpp.func-sort-c.html | 80 + .../test/testAdiabaticCooling.cpp.func.html | 80 + .../test/testAdiabaticCooling.cpp.gcov.html | 131 ++ .../testAdvectionField.cpp.func-sort-c.html | 92 + .../test/testAdvectionField.cpp.func.html | 92 + .../test/testAdvectionField.cpp.gcov.html | 245 ++ .../testBreakCondition.cpp.func-sort-c.html | 196 ++ .../test/testBreakCondition.cpp.func.html | 196 ++ .../test/testBreakCondition.cpp.gcov.html | 621 +++++ ...estCandidateSplitting.cpp.func-sort-c.html | 80 + .../test/testCandidateSplitting.cpp.func.html | 80 + .../test/testCandidateSplitting.cpp.gcov.html | 166 ++ .../test/testCore.cpp.func-sort-c.html | 308 +++ .../test/testCore.cpp.func.html | 308 +++ .../test/testCore.cpp.gcov.html | 1144 +++++++++ .../test/testDensity.cpp.func-sort-c.html | 100 + .../test/testDensity.cpp.func.html | 100 + .../test/testDensity.cpp.gcov.html | 372 +++ .../testFunctionalGroups.cpp.func-sort-c.html | 80 + .../test/testFunctionalGroups.cpp.func.html | 80 + .../test/testFunctionalGroups.cpp.gcov.html | 126 + .../test/testInteraction.cpp.func-sort-c.html | 284 +++ .../test/testInteraction.cpp.func.html | 284 +++ .../test/testInteraction.cpp.gcov.html | 1229 ++++++++++ .../testMagneticField.cpp.func-sort-c.html | 136 ++ .../test/testMagneticField.cpp.func.html | 136 ++ .../test/testMagneticField.cpp.gcov.html | 292 +++ .../testMagneticLens.cpp.func-sort-c.html | 100 + .../test/testMagneticLens.cpp.func.html | 100 + .../test/testMagneticLens.cpp.gcov.html | 248 ++ .../test/testModuleList.cpp.func-sort-c.html | 100 + .../test/testModuleList.cpp.func.html | 100 + .../test/testModuleList.cpp.gcov.html | 155 ++ .../test/testOutput.cpp.func-sort-c.html | 144 ++ .../test/testOutput.cpp.func.html | 144 ++ .../test/testOutput.cpp.gcov.html | 355 +++ .../test/testPropagation.cpp.func-sort-c.html | 148 ++ .../test/testPropagation.cpp.func.html | 148 ++ .../test/testPropagation.cpp.gcov.html | 632 +++++ .../test/testSource.cpp.func-sort-c.html | 168 ++ .../test/testSource.cpp.func.html | 168 ++ .../test/testSource.cpp.gcov.html | 516 ++++ .../testTurbulentField.cpp.func-sort-c.html | 104 + .../test/testTurbulentField.cpp.func.html | 104 + .../test/testTurbulentField.cpp.gcov.html | 218 ++ .../test/testVector3.cpp.func-sort-c.html | 124 + .../test/testVector3.cpp.func.html | 124 + .../test/testVector3.cpp.gcov.html | 238 ++ doc/coverageReport/updown.png | Bin 0 -> 117 bytes doc/pages/Code-Coverage.md | 7 + 536 files changed, 101307 insertions(+) create mode 100644 doc/coverageReport/amber.png create mode 100644 doc/coverageReport/emerald.png create mode 100644 doc/coverageReport/gcov.css create mode 100644 doc/coverageReport/glass.png create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html create mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/AssocVector.h.func.html create mode 100644 doc/coverageReport/include/crpropa/AssocVector.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Candidate.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Candidate.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Common.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Common.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Common.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/EmissionMap.h.func.html create mode 100644 doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Geometry.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Geometry.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Grid.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Grid.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Logging.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Logging.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Module.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Module.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Module.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/ParticleState.h.func.html create mode 100644 doc/coverageReport/include/crpropa/ParticleState.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/PhotonBackground.h.func.html create mode 100644 doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Random.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Random.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Random.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Referenced.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Referenced.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Source.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Source.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Source.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Variant.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Variant.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/Vector3.h.func.html create mode 100644 doc/coverageReport/include/crpropa/Vector3.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html create mode 100644 doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/advectionField/index-sort-f.html create mode 100644 doc/coverageReport/include/crpropa/advectionField/index-sort-l.html create mode 100644 doc/coverageReport/include/crpropa/advectionField/index.html create mode 100644 doc/coverageReport/include/crpropa/index-sort-f.html create mode 100644 doc/coverageReport/include/crpropa/index-sort-l.html create mode 100644 doc/coverageReport/include/crpropa/index.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/index-sort-f.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/index-sort-l.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/index.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html create mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html create mode 100644 doc/coverageReport/include/crpropa/magneticLens/index.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html create mode 100644 doc/coverageReport/include/crpropa/massDistribution/index.html create mode 100644 doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/Boundary.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/Observer.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/Observer.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/OutputShell.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/Redshift.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/TextOutput.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html create mode 100644 doc/coverageReport/include/crpropa/module/Tools.h.func.html create mode 100644 doc/coverageReport/include/crpropa/module/Tools.h.gcov.html create mode 100644 doc/coverageReport/include/crpropa/module/index-sort-f.html create mode 100644 doc/coverageReport/include/crpropa/module/index-sort-l.html create mode 100644 doc/coverageReport/include/crpropa/module/index.html create mode 100644 doc/coverageReport/index-sort-f.html create mode 100644 doc/coverageReport/index-sort-l.html create mode 100644 doc/coverageReport/index.html create mode 100644 doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html create mode 100644 doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html create mode 100644 doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html create mode 100644 doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html create mode 100644 doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html create mode 100644 doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html create mode 100644 doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html create mode 100644 doc/coverageReport/libs/HepPID/src/Version.cc.func.html create mode 100644 doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html create mode 100644 doc/coverageReport/libs/HepPID/src/index-sort-f.html create mode 100644 doc/coverageReport/libs/HepPID/src/index-sort-l.html create mode 100644 doc/coverageReport/libs/HepPID/src/index.html create mode 100644 doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/error_handling.cc.func.html create mode 100644 doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html create mode 100644 doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html create mode 100644 doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/index.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html create mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html create mode 100644 doc/coverageReport/libs/healpix_base/index-sort-f.html create mode 100644 doc/coverageReport/libs/healpix_base/index-sort-l.html create mode 100644 doc/coverageReport/libs/healpix_base/index.html create mode 100644 doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html create mode 100644 doc/coverageReport/libs/healpix_base/pointing.cc.func.html create mode 100644 doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/index.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html create mode 100644 doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html create mode 100644 doc/coverageReport/libs/kiss/src/index-sort-f.html create mode 100644 doc/coverageReport/libs/kiss/src/index-sort-l.html create mode 100644 doc/coverageReport/libs/kiss/src/index.html create mode 100644 doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html create mode 100644 doc/coverageReport/libs/kiss/src/logger.cpp.func.html create mode 100644 doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html create mode 100644 doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html create mode 100644 doc/coverageReport/libs/kiss/src/path.cpp.func.html create mode 100644 doc/coverageReport/libs/kiss/src/path.cpp.gcov.html create mode 100644 doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html create mode 100644 doc/coverageReport/libs/kiss/src/string.cpp.func.html create mode 100644 doc/coverageReport/libs/kiss/src/string.cpp.gcov.html create mode 100644 doc/coverageReport/ruby.png create mode 100644 doc/coverageReport/snow.png create mode 100644 doc/coverageReport/src/Candidate.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Candidate.cpp.func.html create mode 100644 doc/coverageReport/src/Candidate.cpp.gcov.html create mode 100644 doc/coverageReport/src/Clock.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Clock.cpp.func.html create mode 100644 doc/coverageReport/src/Clock.cpp.gcov.html create mode 100644 doc/coverageReport/src/Common.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Common.cpp.func.html create mode 100644 doc/coverageReport/src/Common.cpp.gcov.html create mode 100644 doc/coverageReport/src/Cosmology.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Cosmology.cpp.func.html create mode 100644 doc/coverageReport/src/Cosmology.cpp.gcov.html create mode 100644 doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/EmissionMap.cpp.func.html create mode 100644 doc/coverageReport/src/EmissionMap.cpp.gcov.html create mode 100644 doc/coverageReport/src/Geometry.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Geometry.cpp.func.html create mode 100644 doc/coverageReport/src/Geometry.cpp.gcov.html create mode 100644 doc/coverageReport/src/GridTools.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/GridTools.cpp.func.html create mode 100644 doc/coverageReport/src/GridTools.cpp.gcov.html create mode 100644 doc/coverageReport/src/Module.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Module.cpp.func.html create mode 100644 doc/coverageReport/src/Module.cpp.gcov.html create mode 100644 doc/coverageReport/src/ParticleID.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/ParticleID.cpp.func.html create mode 100644 doc/coverageReport/src/ParticleID.cpp.gcov.html create mode 100644 doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/ParticleMass.cpp.func.html create mode 100644 doc/coverageReport/src/ParticleMass.cpp.gcov.html create mode 100644 doc/coverageReport/src/ParticleState.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/ParticleState.cpp.func.html create mode 100644 doc/coverageReport/src/ParticleState.cpp.gcov.html create mode 100644 doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/PhotonBackground.cpp.func.html create mode 100644 doc/coverageReport/src/PhotonBackground.cpp.gcov.html create mode 100644 doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/ProgressBar.cpp.func.html create mode 100644 doc/coverageReport/src/ProgressBar.cpp.gcov.html create mode 100644 doc/coverageReport/src/Random.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Random.cpp.func.html create mode 100644 doc/coverageReport/src/Random.cpp.gcov.html create mode 100644 doc/coverageReport/src/Source.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Source.cpp.func.html create mode 100644 doc/coverageReport/src/Source.cpp.gcov.html create mode 100644 doc/coverageReport/src/Variant.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/Variant.cpp.func.html create mode 100644 doc/coverageReport/src/Variant.cpp.gcov.html create mode 100644 doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html create mode 100644 doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html create mode 100644 doc/coverageReport/src/advectionField/index-sort-f.html create mode 100644 doc/coverageReport/src/advectionField/index-sort-l.html create mode 100644 doc/coverageReport/src/advectionField/index.html create mode 100644 doc/coverageReport/src/base64.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/base64.cpp.func.html create mode 100644 doc/coverageReport/src/base64.cpp.gcov.html create mode 100644 doc/coverageReport/src/index-sort-f.html create mode 100644 doc/coverageReport/src/index-sort-l.html create mode 100644 doc/coverageReport/src/index.html create mode 100644 doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/CMZField.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/JF12Field.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/MagneticField.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/PT11Field.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/TF17Field.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/index-sort-f.html create mode 100644 doc/coverageReport/src/magneticField/index-sort-l.html create mode 100644 doc/coverageReport/src/magneticField/index.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html create mode 100644 doc/coverageReport/src/magneticField/turbulentField/index.html create mode 100644 doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html create mode 100644 doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html create mode 100644 doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html create mode 100644 doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html create mode 100644 doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html create mode 100644 doc/coverageReport/src/magneticLens/index-sort-f.html create mode 100644 doc/coverageReport/src/magneticLens/index-sort-l.html create mode 100644 doc/coverageReport/src/magneticLens/index.html create mode 100644 doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html create mode 100644 doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html create mode 100644 doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/massDistribution/Cordes.cpp.func.html create mode 100644 doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html create mode 100644 doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html create mode 100644 doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html create mode 100644 doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html create mode 100644 doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html create mode 100644 doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html create mode 100644 doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html create mode 100644 doc/coverageReport/src/massDistribution/index-sort-f.html create mode 100644 doc/coverageReport/src/massDistribution/index-sort-l.html create mode 100644 doc/coverageReport/src/massDistribution/index.html create mode 100644 doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/Acceleration.cpp.func.html create mode 100644 doc/coverageReport/src/module/Acceleration.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html create mode 100644 doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/Boundary.cpp.func.html create mode 100644 doc/coverageReport/src/module/Boundary.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/BreakCondition.cpp.func.html create mode 100644 doc/coverageReport/src/module/BreakCondition.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/CandidateSplitting.cpp.func.html create mode 100644 doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/DiffusionSDE.cpp.func.html create mode 100644 doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html create mode 100644 doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html create mode 100644 doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/EMPairProduction.cpp.func.html create mode 100644 doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html create mode 100644 doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/ElasticScattering.cpp.func.html create mode 100644 doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html create mode 100644 doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/HDF5Output.cpp.func.html create mode 100644 doc/coverageReport/src/module/HDF5Output.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html create mode 100644 doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/NuclearDecay.cpp.func.html create mode 100644 doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/Observer.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/Observer.cpp.func.html create mode 100644 doc/coverageReport/src/module/Observer.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/Output.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/Output.cpp.func.html create mode 100644 doc/coverageReport/src/module/Output.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/OutputShell.cpp.func.html create mode 100644 doc/coverageReport/src/module/OutputShell.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/ParticleCollector.cpp.func.html create mode 100644 doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html create mode 100644 doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html create mode 100644 doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html create mode 100644 doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/PropagationBP.cpp.func.html create mode 100644 doc/coverageReport/src/module/PropagationBP.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/PropagationCK.cpp.func.html create mode 100644 doc/coverageReport/src/module/PropagationCK.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/Redshift.cpp.func.html create mode 100644 doc/coverageReport/src/module/Redshift.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/RestrictToRegion.cpp.func.html create mode 100644 doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/SimplePropagation.cpp.func.html create mode 100644 doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html create mode 100644 doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/TextOutput.cpp.func.html create mode 100644 doc/coverageReport/src/module/TextOutput.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/Tools.cpp.func-sort-c.html create mode 100644 doc/coverageReport/src/module/Tools.cpp.func.html create mode 100644 doc/coverageReport/src/module/Tools.cpp.gcov.html create mode 100644 doc/coverageReport/src/module/index-sort-f.html create mode 100644 doc/coverageReport/src/module/index-sort-l.html create mode 100644 doc/coverageReport/src/module/index.html create mode 100644 doc/coverageReport/test/index-sort-f.html create mode 100644 doc/coverageReport/test/index-sort-l.html create mode 100644 doc/coverageReport/test/index.html create mode 100644 doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testAdiabaticCooling.cpp.func.html create mode 100644 doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html create mode 100644 doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testAdvectionField.cpp.func.html create mode 100644 doc/coverageReport/test/testAdvectionField.cpp.gcov.html create mode 100644 doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testBreakCondition.cpp.func.html create mode 100644 doc/coverageReport/test/testBreakCondition.cpp.gcov.html create mode 100644 doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testCandidateSplitting.cpp.func.html create mode 100644 doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html create mode 100644 doc/coverageReport/test/testCore.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testCore.cpp.func.html create mode 100644 doc/coverageReport/test/testCore.cpp.gcov.html create mode 100644 doc/coverageReport/test/testDensity.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testDensity.cpp.func.html create mode 100644 doc/coverageReport/test/testDensity.cpp.gcov.html create mode 100644 doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testFunctionalGroups.cpp.func.html create mode 100644 doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html create mode 100644 doc/coverageReport/test/testInteraction.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testInteraction.cpp.func.html create mode 100644 doc/coverageReport/test/testInteraction.cpp.gcov.html create mode 100644 doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testMagneticField.cpp.func.html create mode 100644 doc/coverageReport/test/testMagneticField.cpp.gcov.html create mode 100644 doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testMagneticLens.cpp.func.html create mode 100644 doc/coverageReport/test/testMagneticLens.cpp.gcov.html create mode 100644 doc/coverageReport/test/testModuleList.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testModuleList.cpp.func.html create mode 100644 doc/coverageReport/test/testModuleList.cpp.gcov.html create mode 100644 doc/coverageReport/test/testOutput.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testOutput.cpp.func.html create mode 100644 doc/coverageReport/test/testOutput.cpp.gcov.html create mode 100644 doc/coverageReport/test/testPropagation.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testPropagation.cpp.func.html create mode 100644 doc/coverageReport/test/testPropagation.cpp.gcov.html create mode 100644 doc/coverageReport/test/testSource.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testSource.cpp.func.html create mode 100644 doc/coverageReport/test/testSource.cpp.gcov.html create mode 100644 doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testTurbulentField.cpp.func.html create mode 100644 doc/coverageReport/test/testTurbulentField.cpp.gcov.html create mode 100644 doc/coverageReport/test/testVector3.cpp.func-sort-c.html create mode 100644 doc/coverageReport/test/testVector3.cpp.func.html create mode 100644 doc/coverageReport/test/testVector3.cpp.gcov.html create mode 100644 doc/coverageReport/updown.png diff --git a/doc/coverageReport/amber.png b/doc/coverageReport/amber.png new file mode 100644 index 0000000000000000000000000000000000000000..2cab170d8359081983a4e343848dfe06bc490f12 GIT binary patch literal 141 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)ga>?NMQuI!iC1^G2tW}LqE04T&+ z;1OBOz`!j8!i<;h*8KqrvZOouIx;Y9?C1WI$O`1M1^9%x{(levWG?NMQuI!iC1^Jb!lvI6;R0X`wF(yt=9xVZRt1vCRixIA4P dLn>}1Cji+@42)0J?}79&c)I$ztaD0e0sy@GAL0N2 literal 0 HcmV?d00001 diff --git a/doc/coverageReport/gcov.css b/doc/coverageReport/gcov.css new file mode 100644 index 000000000..bfd0a83e1 --- /dev/null +++ b/doc/coverageReport/gcov.css @@ -0,0 +1,519 @@ +/* All views: initial background and text color */ +body +{ + color: #000000; + background-color: #FFFFFF; +} + +/* All views: standard link format*/ +a:link +{ + color: #284FA8; + text-decoration: underline; +} + +/* All views: standard link - visited format */ +a:visited +{ + color: #00CB40; + text-decoration: underline; +} + +/* All views: standard link - activated format */ +a:active +{ + color: #FF0040; + text-decoration: underline; +} + +/* All views: main title format */ +td.title +{ + text-align: center; + padding-bottom: 10px; + font-family: sans-serif; + font-size: 20pt; + font-style: italic; + font-weight: bold; +} + +/* All views: header item format */ +td.headerItem +{ + text-align: right; + padding-right: 6px; + font-family: sans-serif; + font-weight: bold; + vertical-align: top; + white-space: nowrap; +} + +/* All views: header item value format */ +td.headerValue +{ + text-align: left; + color: #284FA8; + font-family: sans-serif; + font-weight: bold; + white-space: nowrap; +} + +/* All views: header item coverage table heading */ +td.headerCovTableHead +{ + text-align: center; + padding-right: 6px; + padding-left: 6px; + padding-bottom: 0px; + font-family: sans-serif; + font-size: 80%; + white-space: nowrap; +} + +/* All views: header item coverage table entry */ +td.headerCovTableEntry +{ + text-align: right; + color: #284FA8; + font-family: sans-serif; + font-weight: bold; + white-space: nowrap; + padding-left: 12px; + padding-right: 4px; + background-color: #DAE7FE; +} + +/* All views: header item coverage table entry for high coverage rate */ +td.headerCovTableEntryHi +{ + text-align: right; + color: #000000; + font-family: sans-serif; + font-weight: bold; + white-space: nowrap; + padding-left: 12px; + padding-right: 4px; + background-color: #A7FC9D; +} + +/* All views: header item coverage table entry for medium coverage rate */ +td.headerCovTableEntryMed +{ + text-align: right; + color: #000000; + font-family: sans-serif; + font-weight: bold; + white-space: nowrap; + padding-left: 12px; + padding-right: 4px; + background-color: #FFEA20; +} + +/* All views: header item coverage table entry for ow coverage rate */ +td.headerCovTableEntryLo +{ + text-align: right; + color: #000000; + font-family: sans-serif; + font-weight: bold; + white-space: nowrap; + padding-left: 12px; + padding-right: 4px; + background-color: #FF0000; +} + +/* All views: header legend value for legend entry */ +td.headerValueLeg +{ + text-align: left; + color: #000000; + font-family: sans-serif; + font-size: 80%; + white-space: nowrap; + padding-top: 4px; +} + +/* All views: color of horizontal ruler */ +td.ruler +{ + background-color: #6688D4; +} + +/* All views: version string format */ +td.versionInfo +{ + text-align: center; + padding-top: 2px; + font-family: sans-serif; + font-style: italic; +} + +/* Directory view/File view (all)/Test case descriptions: + table headline format */ +td.tableHead +{ + text-align: center; + color: #FFFFFF; + background-color: #6688D4; + font-family: sans-serif; + font-size: 120%; + font-weight: bold; + white-space: nowrap; + padding-left: 4px; + padding-right: 4px; +} + +span.tableHeadSort +{ + padding-right: 4px; +} + +/* Directory view/File view (all): filename entry format */ +td.coverFile +{ + text-align: left; + padding-left: 10px; + padding-right: 20px; + color: #284FA8; + background-color: #DAE7FE; + font-family: monospace; +} + +/* Directory view/File view (all): bar-graph entry format*/ +td.coverBar +{ + padding-left: 10px; + padding-right: 10px; + background-color: #DAE7FE; +} + +/* Directory view/File view (all): bar-graph outline color */ +td.coverBarOutline +{ + background-color: #000000; +} + +/* Directory view/File view (all): percentage entry for files with + high coverage rate */ +td.coverPerHi +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #A7FC9D; + font-weight: bold; + font-family: sans-serif; +} + +/* Directory view/File view (all): line count entry for files with + high coverage rate */ +td.coverNumHi +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #A7FC9D; + white-space: nowrap; + font-family: sans-serif; +} + +/* Directory view/File view (all): percentage entry for files with + medium coverage rate */ +td.coverPerMed +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #FFEA20; + font-weight: bold; + font-family: sans-serif; +} + +/* Directory view/File view (all): line count entry for files with + medium coverage rate */ +td.coverNumMed +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #FFEA20; + white-space: nowrap; + font-family: sans-serif; +} + +/* Directory view/File view (all): percentage entry for files with + low coverage rate */ +td.coverPerLo +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #FF0000; + font-weight: bold; + font-family: sans-serif; +} + +/* Directory view/File view (all): line count entry for files with + low coverage rate */ +td.coverNumLo +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #FF0000; + white-space: nowrap; + font-family: sans-serif; +} + +/* File view (all): "show/hide details" link format */ +a.detail:link +{ + color: #B8D0FF; + font-size:80%; +} + +/* File view (all): "show/hide details" link - visited format */ +a.detail:visited +{ + color: #B8D0FF; + font-size:80%; +} + +/* File view (all): "show/hide details" link - activated format */ +a.detail:active +{ + color: #FFFFFF; + font-size:80%; +} + +/* File view (detail): test name entry */ +td.testName +{ + text-align: right; + padding-right: 10px; + background-color: #DAE7FE; + font-family: sans-serif; +} + +/* File view (detail): test percentage entry */ +td.testPer +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #DAE7FE; + font-family: sans-serif; +} + +/* File view (detail): test lines count entry */ +td.testNum +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #DAE7FE; + font-family: sans-serif; +} + +/* Test case descriptions: test name format*/ +dt +{ + font-family: sans-serif; + font-weight: bold; +} + +/* Test case descriptions: description table body */ +td.testDescription +{ + padding-top: 10px; + padding-left: 30px; + padding-bottom: 10px; + padding-right: 30px; + background-color: #DAE7FE; +} + +/* Source code view: function entry */ +td.coverFn +{ + text-align: left; + padding-left: 10px; + padding-right: 20px; + color: #284FA8; + background-color: #DAE7FE; + font-family: monospace; +} + +/* Source code view: function entry zero count*/ +td.coverFnLo +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #FF0000; + font-weight: bold; + font-family: sans-serif; +} + +/* Source code view: function entry nonzero count*/ +td.coverFnHi +{ + text-align: right; + padding-left: 10px; + padding-right: 10px; + background-color: #DAE7FE; + font-weight: bold; + font-family: sans-serif; +} + +/* Source code view: source code format */ +pre.source +{ + font-family: monospace; + white-space: pre; + margin-top: 2px; +} + +/* Source code view: line number format */ +span.lineNum +{ + background-color: #EFE383; +} + +/* Source code view: format for lines which were executed */ +td.lineCov, +span.lineCov +{ + background-color: #CAD7FE; +} + +/* Source code view: format for Cov legend */ +span.coverLegendCov +{ + padding-left: 10px; + padding-right: 10px; + padding-bottom: 2px; + background-color: #CAD7FE; +} + +/* Source code view: format for lines which were not executed */ +td.lineNoCov, +span.lineNoCov +{ + background-color: #FF6230; +} + +/* Source code view: format for NoCov legend */ +span.coverLegendNoCov +{ + padding-left: 10px; + padding-right: 10px; + padding-bottom: 2px; + background-color: #FF6230; +} + +/* Source code view (function table): standard link - visited format */ +td.lineNoCov > a:visited, +td.lineCov > a:visited +{ + color: black; + text-decoration: underline; +} + +/* Source code view: format for lines which were executed only in a + previous version */ +span.lineDiffCov +{ + background-color: #B5F7AF; +} + +/* Source code view: format for branches which were executed + * and taken */ +span.branchCov +{ + background-color: #CAD7FE; +} + +/* Source code view: format for branches which were executed + * but not taken */ +span.branchNoCov +{ + background-color: #FF6230; +} + +/* Source code view: format for branches which were not executed */ +span.branchNoExec +{ + background-color: #FF6230; +} + +/* Source code view: format for the source code heading line */ +pre.sourceHeading +{ + white-space: pre; + font-family: monospace; + font-weight: bold; + margin: 0px; +} + +/* All views: header legend value for low rate */ +td.headerValueLegL +{ + font-family: sans-serif; + text-align: center; + white-space: nowrap; + padding-left: 4px; + padding-right: 2px; + background-color: #FF0000; + font-size: 80%; +} + +/* All views: header legend value for med rate */ +td.headerValueLegM +{ + font-family: sans-serif; + text-align: center; + white-space: nowrap; + padding-left: 2px; + padding-right: 2px; + background-color: #FFEA20; + font-size: 80%; +} + +/* All views: header legend value for hi rate */ +td.headerValueLegH +{ + font-family: sans-serif; + text-align: center; + white-space: nowrap; + padding-left: 2px; + padding-right: 4px; + background-color: #A7FC9D; + font-size: 80%; +} + +/* All views except source code view: legend format for low coverage */ +span.coverLegendCovLo +{ + padding-left: 10px; + padding-right: 10px; + padding-top: 2px; + background-color: #FF0000; +} + +/* All views except source code view: legend format for med coverage */ +span.coverLegendCovMed +{ + padding-left: 10px; + padding-right: 10px; + padding-top: 2px; + background-color: #FFEA20; +} + +/* All views except source code view: legend format for hi coverage */ +span.coverLegendCovHi +{ + padding-left: 10px; + padding-right: 10px; + padding-top: 2px; + background-color: #A7FC9D; +} diff --git a/doc/coverageReport/glass.png b/doc/coverageReport/glass.png new file mode 100644 index 0000000000000000000000000000000000000000..e1abc00680a3093c49fdb775ae6bdb6764c95af2 GIT binary patch literal 167 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)gaEa{HEjtmSN`?>!lvI6;R0X`wF z|Ns97GD8ntt^-nxB|(0{3=Yq3q=7g|-tI089jvk*Kn`btM`SSr1Gf+eGhVt|_XjA* zUgGKN%6^Gmn4d%Ph(nkFP>9RZ#WAE}PI3Z}&BVayv3^M*kj3EX>gTe~DWM4f=_Dpv literal 0 HcmV?d00001 diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html new file mode 100644 index 000000000..0de34274a --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __multiarray_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:132748.1 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_import_array4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html new file mode 100644 index 000000000..6d2267253 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __multiarray_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:132748.1 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_import_array4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html new file mode 100644 index 000000000..5aee35675 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html @@ -0,0 +1,1642 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __multiarray_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:132748.1 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : 
+       2             : #if defined(_MULTIARRAYMODULE) || defined(WITH_CPYCHECKER_STEALS_REFERENCE_TO_ARG_ATTRIBUTE)
+       3             : 
+       4             : typedef struct {
+       5             :         PyObject_HEAD
+       6             :         npy_bool obval;
+       7             : } PyBoolScalarObject;
+       8             : 
+       9             : extern NPY_NO_EXPORT PyTypeObject PyArrayMapIter_Type;
+      10             : extern NPY_NO_EXPORT PyTypeObject PyArrayNeighborhoodIter_Type;
+      11             : extern NPY_NO_EXPORT PyBoolScalarObject _PyArrayScalar_BoolValues[2];
+      12             : 
+      13             : NPY_NO_EXPORT  unsigned int PyArray_GetNDArrayCVersion \
+      14             :        (void);
+      15             : extern NPY_NO_EXPORT PyTypeObject PyBigArray_Type;
+      16             : 
+      17             : extern NPY_NO_EXPORT PyTypeObject PyArray_Type;
+      18             : 
+      19             : extern NPY_NO_EXPORT PyArray_DTypeMeta PyArrayDescr_TypeFull;
+      20             : #define PyArrayDescr_Type (*(PyTypeObject *)(&PyArrayDescr_TypeFull))
+      21             : 
+      22             : extern NPY_NO_EXPORT PyTypeObject PyArrayFlags_Type;
+      23             : 
+      24             : extern NPY_NO_EXPORT PyTypeObject PyArrayIter_Type;
+      25             : 
+      26             : extern NPY_NO_EXPORT PyTypeObject PyArrayMultiIter_Type;
+      27             : 
+      28             : extern NPY_NO_EXPORT int NPY_NUMUSERTYPES;
+      29             : 
+      30             : extern NPY_NO_EXPORT PyTypeObject PyBoolArrType_Type;
+      31             : 
+      32             : extern NPY_NO_EXPORT PyBoolScalarObject _PyArrayScalar_BoolValues[2];
+      33             : 
+      34             : extern NPY_NO_EXPORT PyTypeObject PyGenericArrType_Type;
+      35             : 
+      36             : extern NPY_NO_EXPORT PyTypeObject PyNumberArrType_Type;
+      37             : 
+      38             : extern NPY_NO_EXPORT PyTypeObject PyIntegerArrType_Type;
+      39             : 
+      40             : extern NPY_NO_EXPORT PyTypeObject PySignedIntegerArrType_Type;
+      41             : 
+      42             : extern NPY_NO_EXPORT PyTypeObject PyUnsignedIntegerArrType_Type;
+      43             : 
+      44             : extern NPY_NO_EXPORT PyTypeObject PyInexactArrType_Type;
+      45             : 
+      46             : extern NPY_NO_EXPORT PyTypeObject PyFloatingArrType_Type;
+      47             : 
+      48             : extern NPY_NO_EXPORT PyTypeObject PyComplexFloatingArrType_Type;
+      49             : 
+      50             : extern NPY_NO_EXPORT PyTypeObject PyFlexibleArrType_Type;
+      51             : 
+      52             : extern NPY_NO_EXPORT PyTypeObject PyCharacterArrType_Type;
+      53             : 
+      54             : extern NPY_NO_EXPORT PyTypeObject PyByteArrType_Type;
+      55             : 
+      56             : extern NPY_NO_EXPORT PyTypeObject PyShortArrType_Type;
+      57             : 
+      58             : extern NPY_NO_EXPORT PyTypeObject PyIntArrType_Type;
+      59             : 
+      60             : extern NPY_NO_EXPORT PyTypeObject PyLongArrType_Type;
+      61             : 
+      62             : extern NPY_NO_EXPORT PyTypeObject PyLongLongArrType_Type;
+      63             : 
+      64             : extern NPY_NO_EXPORT PyTypeObject PyUByteArrType_Type;
+      65             : 
+      66             : extern NPY_NO_EXPORT PyTypeObject PyUShortArrType_Type;
+      67             : 
+      68             : extern NPY_NO_EXPORT PyTypeObject PyUIntArrType_Type;
+      69             : 
+      70             : extern NPY_NO_EXPORT PyTypeObject PyULongArrType_Type;
+      71             : 
+      72             : extern NPY_NO_EXPORT PyTypeObject PyULongLongArrType_Type;
+      73             : 
+      74             : extern NPY_NO_EXPORT PyTypeObject PyFloatArrType_Type;
+      75             : 
+      76             : extern NPY_NO_EXPORT PyTypeObject PyDoubleArrType_Type;
+      77             : 
+      78             : extern NPY_NO_EXPORT PyTypeObject PyLongDoubleArrType_Type;
+      79             : 
+      80             : extern NPY_NO_EXPORT PyTypeObject PyCFloatArrType_Type;
+      81             : 
+      82             : extern NPY_NO_EXPORT PyTypeObject PyCDoubleArrType_Type;
+      83             : 
+      84             : extern NPY_NO_EXPORT PyTypeObject PyCLongDoubleArrType_Type;
+      85             : 
+      86             : extern NPY_NO_EXPORT PyTypeObject PyObjectArrType_Type;
+      87             : 
+      88             : extern NPY_NO_EXPORT PyTypeObject PyStringArrType_Type;
+      89             : 
+      90             : extern NPY_NO_EXPORT PyTypeObject PyUnicodeArrType_Type;
+      91             : 
+      92             : extern NPY_NO_EXPORT PyTypeObject PyVoidArrType_Type;
+      93             : 
+      94             : NPY_NO_EXPORT  int PyArray_SetNumericOps \
+      95             :        (PyObject *);
+      96             : NPY_NO_EXPORT  PyObject * PyArray_GetNumericOps \
+      97             :        (void);
+      98             : NPY_NO_EXPORT  int PyArray_INCREF \
+      99             :        (PyArrayObject *);
+     100             : NPY_NO_EXPORT  int PyArray_XDECREF \
+     101             :        (PyArrayObject *);
+     102             : NPY_NO_EXPORT  void PyArray_SetStringFunction \
+     103             :        (PyObject *, int);
+     104             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromType \
+     105             :        (int);
+     106             : NPY_NO_EXPORT  PyObject * PyArray_TypeObjectFromType \
+     107             :        (int);
+     108             : NPY_NO_EXPORT  char * PyArray_Zero \
+     109             :        (PyArrayObject *);
+     110             : NPY_NO_EXPORT  char * PyArray_One \
+     111             :        (PyArrayObject *);
+     112             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_CastToType \
+     113             :        (PyArrayObject *, PyArray_Descr *, int);
+     114             : NPY_NO_EXPORT  int PyArray_CastTo \
+     115             :        (PyArrayObject *, PyArrayObject *);
+     116             : NPY_NO_EXPORT  int PyArray_CastAnyTo \
+     117             :        (PyArrayObject *, PyArrayObject *);
+     118             : NPY_NO_EXPORT  int PyArray_CanCastSafely \
+     119             :        (int, int);
+     120             : NPY_NO_EXPORT  npy_bool PyArray_CanCastTo \
+     121             :        (PyArray_Descr *, PyArray_Descr *);
+     122             : NPY_NO_EXPORT  int PyArray_ObjectType \
+     123             :        (PyObject *, int);
+     124             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromObject \
+     125             :        (PyObject *, PyArray_Descr *);
+     126             : NPY_NO_EXPORT  PyArrayObject ** PyArray_ConvertToCommonType \
+     127             :        (PyObject *, int *);
+     128             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromScalar \
+     129             :        (PyObject *);
+     130             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromTypeObject \
+     131             :        (PyObject *);
+     132             : NPY_NO_EXPORT  npy_intp PyArray_Size \
+     133             :        (PyObject *);
+     134             : NPY_NO_EXPORT  PyObject * PyArray_Scalar \
+     135             :        (void *, PyArray_Descr *, PyObject *);
+     136             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromScalar \
+     137             :        (PyObject *, PyArray_Descr *);
+     138             : NPY_NO_EXPORT  void PyArray_ScalarAsCtype \
+     139             :        (PyObject *, void *);
+     140             : NPY_NO_EXPORT  int PyArray_CastScalarToCtype \
+     141             :        (PyObject *, void *, PyArray_Descr *);
+     142             : NPY_NO_EXPORT  int PyArray_CastScalarDirect \
+     143             :        (PyObject *, PyArray_Descr *, void *, int);
+     144             : NPY_NO_EXPORT  PyObject * PyArray_ScalarFromObject \
+     145             :        (PyObject *);
+     146             : NPY_NO_EXPORT  PyArray_VectorUnaryFunc * PyArray_GetCastFunc \
+     147             :        (PyArray_Descr *, int);
+     148             : NPY_NO_EXPORT  PyObject * PyArray_FromDims \
+     149             :        (int NPY_UNUSED(nd), int *NPY_UNUSED(d), int NPY_UNUSED(type));
+     150             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_FromDimsAndDataAndDescr \
+     151             :        (int NPY_UNUSED(nd), int *NPY_UNUSED(d), PyArray_Descr *, char *NPY_UNUSED(data));
+     152             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromAny \
+     153             :        (PyObject *, PyArray_Descr *, int, int, int, PyObject *);
+     154             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(1) PyObject * PyArray_EnsureArray \
+     155             :        (PyObject *);
+     156             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(1) PyObject * PyArray_EnsureAnyArray \
+     157             :        (PyObject *);
+     158             : NPY_NO_EXPORT  PyObject * PyArray_FromFile \
+     159             :        (FILE *, PyArray_Descr *, npy_intp, char *);
+     160             : NPY_NO_EXPORT  PyObject * PyArray_FromString \
+     161             :        (char *, npy_intp, PyArray_Descr *, npy_intp, char *);
+     162             : NPY_NO_EXPORT  PyObject * PyArray_FromBuffer \
+     163             :        (PyObject *, PyArray_Descr *, npy_intp, npy_intp);
+     164             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromIter \
+     165             :        (PyObject *, PyArray_Descr *, npy_intp);
+     166             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(1) PyObject * PyArray_Return \
+     167             :        (PyArrayObject *);
+     168             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_GetField \
+     169             :        (PyArrayObject *, PyArray_Descr *, int);
+     170             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) int PyArray_SetField \
+     171             :        (PyArrayObject *, PyArray_Descr *, int, PyObject *);
+     172             : NPY_NO_EXPORT  PyObject * PyArray_Byteswap \
+     173             :        (PyArrayObject *, npy_bool);
+     174             : NPY_NO_EXPORT  PyObject * PyArray_Resize \
+     175             :        (PyArrayObject *, PyArray_Dims *, int, NPY_ORDER NPY_UNUSED(order));
+     176             : NPY_NO_EXPORT  int PyArray_MoveInto \
+     177             :        (PyArrayObject *, PyArrayObject *);
+     178             : NPY_NO_EXPORT  int PyArray_CopyInto \
+     179             :        (PyArrayObject *, PyArrayObject *);
+     180             : NPY_NO_EXPORT  int PyArray_CopyAnyInto \
+     181             :        (PyArrayObject *, PyArrayObject *);
+     182             : NPY_NO_EXPORT  int PyArray_CopyObject \
+     183             :        (PyArrayObject *, PyObject *);
+     184             : NPY_NO_EXPORT  PyObject * PyArray_NewCopy \
+     185             :        (PyArrayObject *, NPY_ORDER);
+     186             : NPY_NO_EXPORT  PyObject * PyArray_ToList \
+     187             :        (PyArrayObject *);
+     188             : NPY_NO_EXPORT  PyObject * PyArray_ToString \
+     189             :        (PyArrayObject *, NPY_ORDER);
+     190             : NPY_NO_EXPORT  int PyArray_ToFile \
+     191             :        (PyArrayObject *, FILE *, char *, char *);
+     192             : NPY_NO_EXPORT  int PyArray_Dump \
+     193             :        (PyObject *, PyObject *, int);
+     194             : NPY_NO_EXPORT  PyObject * PyArray_Dumps \
+     195             :        (PyObject *, int);
+     196             : NPY_NO_EXPORT  int PyArray_ValidType \
+     197             :        (int);
+     198             : NPY_NO_EXPORT  void PyArray_UpdateFlags \
+     199             :        (PyArrayObject *, int);
+     200             : NPY_NO_EXPORT  PyObject * PyArray_New \
+     201             :        (PyTypeObject *, int, npy_intp const *, int, npy_intp const *, void *, int, int, PyObject *);
+     202             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_NewFromDescr \
+     203             :        (PyTypeObject *, PyArray_Descr *, int, npy_intp const *, npy_intp const *, void *, int, PyObject *);
+     204             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrNew \
+     205             :        (PyArray_Descr *);
+     206             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrNewFromType \
+     207             :        (int);
+     208             : NPY_NO_EXPORT  double PyArray_GetPriority \
+     209             :        (PyObject *, double);
+     210             : NPY_NO_EXPORT  PyObject * PyArray_IterNew \
+     211             :        (PyObject *);
+     212             : NPY_NO_EXPORT  PyObject* PyArray_MultiIterNew \
+     213             :        (int, ...);
+     214             : NPY_NO_EXPORT  int PyArray_PyIntAsInt \
+     215             :        (PyObject *);
+     216             : NPY_NO_EXPORT  npy_intp PyArray_PyIntAsIntp \
+     217             :        (PyObject *);
+     218             : NPY_NO_EXPORT  int PyArray_Broadcast \
+     219             :        (PyArrayMultiIterObject *);
+     220             : NPY_NO_EXPORT  void PyArray_FillObjectArray \
+     221             :        (PyArrayObject *, PyObject *);
+     222             : NPY_NO_EXPORT  int PyArray_FillWithScalar \
+     223             :        (PyArrayObject *, PyObject *);
+     224             : NPY_NO_EXPORT  npy_bool PyArray_CheckStrides \
+     225             :        (int, int, npy_intp, npy_intp, npy_intp const *, npy_intp const *);
+     226             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrNewByteorder \
+     227             :        (PyArray_Descr *, char);
+     228             : NPY_NO_EXPORT  PyObject * PyArray_IterAllButAxis \
+     229             :        (PyObject *, int *);
+     230             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_CheckFromAny \
+     231             :        (PyObject *, PyArray_Descr *, int, int, int, PyObject *);
+     232             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromArray \
+     233             :        (PyArrayObject *, PyArray_Descr *, int);
+     234             : NPY_NO_EXPORT  PyObject * PyArray_FromInterface \
+     235             :        (PyObject *);
+     236             : NPY_NO_EXPORT  PyObject * PyArray_FromStructInterface \
+     237             :        (PyObject *);
+     238             : NPY_NO_EXPORT  PyObject * PyArray_FromArrayAttr \
+     239             :        (PyObject *, PyArray_Descr *, PyObject *);
+     240             : NPY_NO_EXPORT  NPY_SCALARKIND PyArray_ScalarKind \
+     241             :        (int, PyArrayObject **);
+     242             : NPY_NO_EXPORT  int PyArray_CanCoerceScalar \
+     243             :        (int, int, NPY_SCALARKIND);
+     244             : NPY_NO_EXPORT  PyObject * PyArray_NewFlagsObject \
+     245             :        (PyObject *);
+     246             : NPY_NO_EXPORT  npy_bool PyArray_CanCastScalar \
+     247             :        (PyTypeObject *, PyTypeObject *);
+     248             : NPY_NO_EXPORT  int PyArray_CompareUCS4 \
+     249             :        (npy_ucs4 const *, npy_ucs4 const *, size_t);
+     250             : NPY_NO_EXPORT  int PyArray_RemoveSmallest \
+     251             :        (PyArrayMultiIterObject *);
+     252             : NPY_NO_EXPORT  int PyArray_ElementStrides \
+     253             :        (PyObject *);
+     254             : NPY_NO_EXPORT  void PyArray_Item_INCREF \
+     255             :        (char *, PyArray_Descr *);
+     256             : NPY_NO_EXPORT  void PyArray_Item_XDECREF \
+     257             :        (char *, PyArray_Descr *);
+     258             : NPY_NO_EXPORT  PyObject * PyArray_FieldNames \
+     259             :        (PyObject *);
+     260             : NPY_NO_EXPORT  PyObject * PyArray_Transpose \
+     261             :        (PyArrayObject *, PyArray_Dims *);
+     262             : NPY_NO_EXPORT  PyObject * PyArray_TakeFrom \
+     263             :        (PyArrayObject *, PyObject *, int, PyArrayObject *, NPY_CLIPMODE);
+     264             : NPY_NO_EXPORT  PyObject * PyArray_PutTo \
+     265             :        (PyArrayObject *, PyObject*, PyObject *, NPY_CLIPMODE);
+     266             : NPY_NO_EXPORT  PyObject * PyArray_PutMask \
+     267             :        (PyArrayObject *, PyObject*, PyObject*);
+     268             : NPY_NO_EXPORT  PyObject * PyArray_Repeat \
+     269             :        (PyArrayObject *, PyObject *, int);
+     270             : NPY_NO_EXPORT  PyObject * PyArray_Choose \
+     271             :        (PyArrayObject *, PyObject *, PyArrayObject *, NPY_CLIPMODE);
+     272             : NPY_NO_EXPORT  int PyArray_Sort \
+     273             :        (PyArrayObject *, int, NPY_SORTKIND);
+     274             : NPY_NO_EXPORT  PyObject * PyArray_ArgSort \
+     275             :        (PyArrayObject *, int, NPY_SORTKIND);
+     276             : NPY_NO_EXPORT  PyObject * PyArray_SearchSorted \
+     277             :        (PyArrayObject *, PyObject *, NPY_SEARCHSIDE, PyObject *);
+     278             : NPY_NO_EXPORT  PyObject * PyArray_ArgMax \
+     279             :        (PyArrayObject *, int, PyArrayObject *);
+     280             : NPY_NO_EXPORT  PyObject * PyArray_ArgMin \
+     281             :        (PyArrayObject *, int, PyArrayObject *);
+     282             : NPY_NO_EXPORT  PyObject * PyArray_Reshape \
+     283             :        (PyArrayObject *, PyObject *);
+     284             : NPY_NO_EXPORT  PyObject * PyArray_Newshape \
+     285             :        (PyArrayObject *, PyArray_Dims *, NPY_ORDER);
+     286             : NPY_NO_EXPORT  PyObject * PyArray_Squeeze \
+     287             :        (PyArrayObject *);
+     288             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_View \
+     289             :        (PyArrayObject *, PyArray_Descr *, PyTypeObject *);
+     290             : NPY_NO_EXPORT  PyObject * PyArray_SwapAxes \
+     291             :        (PyArrayObject *, int, int);
+     292             : NPY_NO_EXPORT  PyObject * PyArray_Max \
+     293             :        (PyArrayObject *, int, PyArrayObject *);
+     294             : NPY_NO_EXPORT  PyObject * PyArray_Min \
+     295             :        (PyArrayObject *, int, PyArrayObject *);
+     296             : NPY_NO_EXPORT  PyObject * PyArray_Ptp \
+     297             :        (PyArrayObject *, int, PyArrayObject *);
+     298             : NPY_NO_EXPORT  PyObject * PyArray_Mean \
+     299             :        (PyArrayObject *, int, int, PyArrayObject *);
+     300             : NPY_NO_EXPORT  PyObject * PyArray_Trace \
+     301             :        (PyArrayObject *, int, int, int, int, PyArrayObject *);
+     302             : NPY_NO_EXPORT  PyObject * PyArray_Diagonal \
+     303             :        (PyArrayObject *, int, int, int);
+     304             : NPY_NO_EXPORT  PyObject * PyArray_Clip \
+     305             :        (PyArrayObject *, PyObject *, PyObject *, PyArrayObject *);
+     306             : NPY_NO_EXPORT  PyObject * PyArray_Conjugate \
+     307             :        (PyArrayObject *, PyArrayObject *);
+     308             : NPY_NO_EXPORT  PyObject * PyArray_Nonzero \
+     309             :        (PyArrayObject *);
+     310             : NPY_NO_EXPORT  PyObject * PyArray_Std \
+     311             :        (PyArrayObject *, int, int, PyArrayObject *, int);
+     312             : NPY_NO_EXPORT  PyObject * PyArray_Sum \
+     313             :        (PyArrayObject *, int, int, PyArrayObject *);
+     314             : NPY_NO_EXPORT  PyObject * PyArray_CumSum \
+     315             :        (PyArrayObject *, int, int, PyArrayObject *);
+     316             : NPY_NO_EXPORT  PyObject * PyArray_Prod \
+     317             :        (PyArrayObject *, int, int, PyArrayObject *);
+     318             : NPY_NO_EXPORT  PyObject * PyArray_CumProd \
+     319             :        (PyArrayObject *, int, int, PyArrayObject *);
+     320             : NPY_NO_EXPORT  PyObject * PyArray_All \
+     321             :        (PyArrayObject *, int, PyArrayObject *);
+     322             : NPY_NO_EXPORT  PyObject * PyArray_Any \
+     323             :        (PyArrayObject *, int, PyArrayObject *);
+     324             : NPY_NO_EXPORT  PyObject * PyArray_Compress \
+     325             :        (PyArrayObject *, PyObject *, int, PyArrayObject *);
+     326             : NPY_NO_EXPORT  PyObject * PyArray_Flatten \
+     327             :        (PyArrayObject *, NPY_ORDER);
+     328             : NPY_NO_EXPORT  PyObject * PyArray_Ravel \
+     329             :        (PyArrayObject *, NPY_ORDER);
+     330             : NPY_NO_EXPORT  npy_intp PyArray_MultiplyList \
+     331             :        (npy_intp const *, int);
+     332             : NPY_NO_EXPORT  int PyArray_MultiplyIntList \
+     333             :        (int const *, int);
+     334             : NPY_NO_EXPORT  void * PyArray_GetPtr \
+     335             :        (PyArrayObject *, npy_intp const*);
+     336             : NPY_NO_EXPORT  int PyArray_CompareLists \
+     337             :        (npy_intp const *, npy_intp const *, int);
+     338             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(5) int PyArray_AsCArray \
+     339             :        (PyObject **, void *, npy_intp *, int, PyArray_Descr*);
+     340             : NPY_NO_EXPORT  int PyArray_As1D \
+     341             :        (PyObject **NPY_UNUSED(op), char **NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int NPY_UNUSED(typecode));
+     342             : NPY_NO_EXPORT  int PyArray_As2D \
+     343             :        (PyObject **NPY_UNUSED(op), char ***NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int *NPY_UNUSED(d2), int NPY_UNUSED(typecode));
+     344             : NPY_NO_EXPORT  int PyArray_Free \
+     345             :        (PyObject *, void *);
+     346             : NPY_NO_EXPORT  int PyArray_Converter \
+     347             :        (PyObject *, PyObject **);
+     348             : NPY_NO_EXPORT  int PyArray_IntpFromSequence \
+     349             :        (PyObject *, npy_intp *, int);
+     350             : NPY_NO_EXPORT  PyObject * PyArray_Concatenate \
+     351             :        (PyObject *, int);
+     352             : NPY_NO_EXPORT  PyObject * PyArray_InnerProduct \
+     353             :        (PyObject *, PyObject *);
+     354             : NPY_NO_EXPORT  PyObject * PyArray_MatrixProduct \
+     355             :        (PyObject *, PyObject *);
+     356             : NPY_NO_EXPORT  PyObject * PyArray_CopyAndTranspose \
+     357             :        (PyObject *);
+     358             : NPY_NO_EXPORT  PyObject * PyArray_Correlate \
+     359             :        (PyObject *, PyObject *, int);
+     360             : NPY_NO_EXPORT  int PyArray_TypestrConvert \
+     361             :        (int, int);
+     362             : NPY_NO_EXPORT  int PyArray_DescrConverter \
+     363             :        (PyObject *, PyArray_Descr **);
+     364             : NPY_NO_EXPORT  int PyArray_DescrConverter2 \
+     365             :        (PyObject *, PyArray_Descr **);
+     366             : NPY_NO_EXPORT  int PyArray_IntpConverter \
+     367             :        (PyObject *, PyArray_Dims *);
+     368             : NPY_NO_EXPORT  int PyArray_BufferConverter \
+     369             :        (PyObject *, PyArray_Chunk *);
+     370             : NPY_NO_EXPORT  int PyArray_AxisConverter \
+     371             :        (PyObject *, int *);
+     372             : NPY_NO_EXPORT  int PyArray_BoolConverter \
+     373             :        (PyObject *, npy_bool *);
+     374             : NPY_NO_EXPORT  int PyArray_ByteorderConverter \
+     375             :        (PyObject *, char *);
+     376             : NPY_NO_EXPORT  int PyArray_OrderConverter \
+     377             :        (PyObject *, NPY_ORDER *);
+     378             : NPY_NO_EXPORT  unsigned char PyArray_EquivTypes \
+     379             :        (PyArray_Descr *, PyArray_Descr *);
+     380             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_Zeros \
+     381             :        (int, npy_intp const *, PyArray_Descr *, int);
+     382             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_Empty \
+     383             :        (int, npy_intp const *, PyArray_Descr *, int);
+     384             : NPY_NO_EXPORT  PyObject * PyArray_Where \
+     385             :        (PyObject *, PyObject *, PyObject *);
+     386             : NPY_NO_EXPORT  PyObject * PyArray_Arange \
+     387             :        (double, double, double, int);
+     388             : NPY_NO_EXPORT  PyObject * PyArray_ArangeObj \
+     389             :        (PyObject *, PyObject *, PyObject *, PyArray_Descr *);
+     390             : NPY_NO_EXPORT  int PyArray_SortkindConverter \
+     391             :        (PyObject *, NPY_SORTKIND *);
+     392             : NPY_NO_EXPORT  PyObject * PyArray_LexSort \
+     393             :        (PyObject *, int);
+     394             : NPY_NO_EXPORT  PyObject * PyArray_Round \
+     395             :        (PyArrayObject *, int, PyArrayObject *);
+     396             : NPY_NO_EXPORT  unsigned char PyArray_EquivTypenums \
+     397             :        (int, int);
+     398             : NPY_NO_EXPORT  int PyArray_RegisterDataType \
+     399             :        (PyArray_Descr *);
+     400             : NPY_NO_EXPORT  int PyArray_RegisterCastFunc \
+     401             :        (PyArray_Descr *, int, PyArray_VectorUnaryFunc *);
+     402             : NPY_NO_EXPORT  int PyArray_RegisterCanCast \
+     403             :        (PyArray_Descr *, int, NPY_SCALARKIND);
+     404             : NPY_NO_EXPORT  void PyArray_InitArrFuncs \
+     405             :        (PyArray_ArrFuncs *);
+     406             : NPY_NO_EXPORT  PyObject * PyArray_IntTupleFromIntp \
+     407             :        (int, npy_intp const *);
+     408             : NPY_NO_EXPORT  int PyArray_TypeNumFromName \
+     409             :        (char const *);
+     410             : NPY_NO_EXPORT  int PyArray_ClipmodeConverter \
+     411             :        (PyObject *, NPY_CLIPMODE *);
+     412             : NPY_NO_EXPORT  int PyArray_OutputConverter \
+     413             :        (PyObject *, PyArrayObject **);
+     414             : NPY_NO_EXPORT  PyObject * PyArray_BroadcastToShape \
+     415             :        (PyObject *, npy_intp *, int);
+     416             : NPY_NO_EXPORT  void _PyArray_SigintHandler \
+     417             :        (int);
+     418             : NPY_NO_EXPORT  void* _PyArray_GetSigintBuf \
+     419             :        (void);
+     420             : NPY_NO_EXPORT  int PyArray_DescrAlignConverter \
+     421             :        (PyObject *, PyArray_Descr **);
+     422             : NPY_NO_EXPORT  int PyArray_DescrAlignConverter2 \
+     423             :        (PyObject *, PyArray_Descr **);
+     424             : NPY_NO_EXPORT  int PyArray_SearchsideConverter \
+     425             :        (PyObject *, void *);
+     426             : NPY_NO_EXPORT  PyObject * PyArray_CheckAxis \
+     427             :        (PyArrayObject *, int *, int);
+     428             : NPY_NO_EXPORT  npy_intp PyArray_OverflowMultiplyList \
+     429             :        (npy_intp const *, int);
+     430             : NPY_NO_EXPORT  int PyArray_CompareString \
+     431             :        (const char *, const char *, size_t);
+     432             : NPY_NO_EXPORT  PyObject* PyArray_MultiIterFromObjects \
+     433             :        (PyObject **, int, int, ...);
+     434             : NPY_NO_EXPORT  int PyArray_GetEndianness \
+     435             :        (void);
+     436             : NPY_NO_EXPORT  unsigned int PyArray_GetNDArrayCFeatureVersion \
+     437             :        (void);
+     438             : NPY_NO_EXPORT  PyObject * PyArray_Correlate2 \
+     439             :        (PyObject *, PyObject *, int);
+     440             : NPY_NO_EXPORT  PyObject* PyArray_NeighborhoodIterNew \
+     441             :        (PyArrayIterObject *, const npy_intp *, int, PyArrayObject*);
+     442             : extern NPY_NO_EXPORT PyTypeObject PyTimeIntegerArrType_Type;
+     443             : 
+     444             : extern NPY_NO_EXPORT PyTypeObject PyDatetimeArrType_Type;
+     445             : 
+     446             : extern NPY_NO_EXPORT PyTypeObject PyTimedeltaArrType_Type;
+     447             : 
+     448             : extern NPY_NO_EXPORT PyTypeObject PyHalfArrType_Type;
+     449             : 
+     450             : extern NPY_NO_EXPORT PyTypeObject NpyIter_Type;
+     451             : 
+     452             : NPY_NO_EXPORT  void PyArray_SetDatetimeParseFunction \
+     453             :        (PyObject *NPY_UNUSED(op));
+     454             : NPY_NO_EXPORT  void PyArray_DatetimeToDatetimeStruct \
+     455             :        (npy_datetime NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *);
+     456             : NPY_NO_EXPORT  void PyArray_TimedeltaToTimedeltaStruct \
+     457             :        (npy_timedelta NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *);
+     458             : NPY_NO_EXPORT  npy_datetime PyArray_DatetimeStructToDatetime \
+     459             :        (NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *NPY_UNUSED(d));
+     460             : NPY_NO_EXPORT  npy_datetime PyArray_TimedeltaStructToTimedelta \
+     461             :        (NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *NPY_UNUSED(d));
+     462             : NPY_NO_EXPORT  NpyIter * NpyIter_New \
+     463             :        (PyArrayObject *, npy_uint32, NPY_ORDER, NPY_CASTING, PyArray_Descr*);
+     464             : NPY_NO_EXPORT  NpyIter * NpyIter_MultiNew \
+     465             :        (int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **);
+     466             : NPY_NO_EXPORT  NpyIter * NpyIter_AdvancedNew \
+     467             :        (int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **, int, int **, npy_intp *, npy_intp);
+     468             : NPY_NO_EXPORT  NpyIter * NpyIter_Copy \
+     469             :        (NpyIter *);
+     470             : NPY_NO_EXPORT  int NpyIter_Deallocate \
+     471             :        (NpyIter *);
+     472             : NPY_NO_EXPORT  npy_bool NpyIter_HasDelayedBufAlloc \
+     473             :        (NpyIter *);
+     474             : NPY_NO_EXPORT  npy_bool NpyIter_HasExternalLoop \
+     475             :        (NpyIter *);
+     476             : NPY_NO_EXPORT  int NpyIter_EnableExternalLoop \
+     477             :        (NpyIter *);
+     478             : NPY_NO_EXPORT  npy_intp * NpyIter_GetInnerStrideArray \
+     479             :        (NpyIter *);
+     480             : NPY_NO_EXPORT  npy_intp * NpyIter_GetInnerLoopSizePtr \
+     481             :        (NpyIter *);
+     482             : NPY_NO_EXPORT  int NpyIter_Reset \
+     483             :        (NpyIter *, char **);
+     484             : NPY_NO_EXPORT  int NpyIter_ResetBasePointers \
+     485             :        (NpyIter *, char **, char **);
+     486             : NPY_NO_EXPORT  int NpyIter_ResetToIterIndexRange \
+     487             :        (NpyIter *, npy_intp, npy_intp, char **);
+     488             : NPY_NO_EXPORT  int NpyIter_GetNDim \
+     489             :        (NpyIter *);
+     490             : NPY_NO_EXPORT  int NpyIter_GetNOp \
+     491             :        (NpyIter *);
+     492             : NPY_NO_EXPORT  NpyIter_IterNextFunc * NpyIter_GetIterNext \
+     493             :        (NpyIter *, char **);
+     494             : NPY_NO_EXPORT  npy_intp NpyIter_GetIterSize \
+     495             :        (NpyIter *);
+     496             : NPY_NO_EXPORT  void NpyIter_GetIterIndexRange \
+     497             :        (NpyIter *, npy_intp *, npy_intp *);
+     498             : NPY_NO_EXPORT  npy_intp NpyIter_GetIterIndex \
+     499             :        (NpyIter *);
+     500             : NPY_NO_EXPORT  int NpyIter_GotoIterIndex \
+     501             :        (NpyIter *, npy_intp);
+     502             : NPY_NO_EXPORT  npy_bool NpyIter_HasMultiIndex \
+     503             :        (NpyIter *);
+     504             : NPY_NO_EXPORT  int NpyIter_GetShape \
+     505             :        (NpyIter *, npy_intp *);
+     506             : NPY_NO_EXPORT  NpyIter_GetMultiIndexFunc * NpyIter_GetGetMultiIndex \
+     507             :        (NpyIter *, char **);
+     508             : NPY_NO_EXPORT  int NpyIter_GotoMultiIndex \
+     509             :        (NpyIter *, npy_intp const *);
+     510             : NPY_NO_EXPORT  int NpyIter_RemoveMultiIndex \
+     511             :        (NpyIter *);
+     512             : NPY_NO_EXPORT  npy_bool NpyIter_HasIndex \
+     513             :        (NpyIter *);
+     514             : NPY_NO_EXPORT  npy_bool NpyIter_IsBuffered \
+     515             :        (NpyIter *);
+     516             : NPY_NO_EXPORT  npy_bool NpyIter_IsGrowInner \
+     517             :        (NpyIter *);
+     518             : NPY_NO_EXPORT  npy_intp NpyIter_GetBufferSize \
+     519             :        (NpyIter *);
+     520             : NPY_NO_EXPORT  npy_intp * NpyIter_GetIndexPtr \
+     521             :        (NpyIter *);
+     522             : NPY_NO_EXPORT  int NpyIter_GotoIndex \
+     523             :        (NpyIter *, npy_intp);
+     524             : NPY_NO_EXPORT  char ** NpyIter_GetDataPtrArray \
+     525             :        (NpyIter *);
+     526             : NPY_NO_EXPORT  PyArray_Descr ** NpyIter_GetDescrArray \
+     527             :        (NpyIter *);
+     528             : NPY_NO_EXPORT  PyArrayObject ** NpyIter_GetOperandArray \
+     529             :        (NpyIter *);
+     530             : NPY_NO_EXPORT  PyArrayObject * NpyIter_GetIterView \
+     531             :        (NpyIter *, npy_intp);
+     532             : NPY_NO_EXPORT  void NpyIter_GetReadFlags \
+     533             :        (NpyIter *, char *);
+     534             : NPY_NO_EXPORT  void NpyIter_GetWriteFlags \
+     535             :        (NpyIter *, char *);
+     536             : NPY_NO_EXPORT  void NpyIter_DebugPrint \
+     537             :        (NpyIter *);
+     538             : NPY_NO_EXPORT  npy_bool NpyIter_IterationNeedsAPI \
+     539             :        (NpyIter *);
+     540             : NPY_NO_EXPORT  void NpyIter_GetInnerFixedStrideArray \
+     541             :        (NpyIter *, npy_intp *);
+     542             : NPY_NO_EXPORT  int NpyIter_RemoveAxis \
+     543             :        (NpyIter *, int);
+     544             : NPY_NO_EXPORT  npy_intp * NpyIter_GetAxisStrideArray \
+     545             :        (NpyIter *, int);
+     546             : NPY_NO_EXPORT  npy_bool NpyIter_RequiresBuffering \
+     547             :        (NpyIter *);
+     548             : NPY_NO_EXPORT  char ** NpyIter_GetInitialDataPtrArray \
+     549             :        (NpyIter *);
+     550             : NPY_NO_EXPORT  int NpyIter_CreateCompatibleStrides \
+     551             :        (NpyIter *, npy_intp, npy_intp *);
+     552             : NPY_NO_EXPORT  int PyArray_CastingConverter \
+     553             :        (PyObject *, NPY_CASTING *);
+     554             : NPY_NO_EXPORT  npy_intp PyArray_CountNonzero \
+     555             :        (PyArrayObject *);
+     556             : NPY_NO_EXPORT  PyArray_Descr * PyArray_PromoteTypes \
+     557             :        (PyArray_Descr *, PyArray_Descr *);
+     558             : NPY_NO_EXPORT  PyArray_Descr * PyArray_MinScalarType \
+     559             :        (PyArrayObject *);
+     560             : NPY_NO_EXPORT  PyArray_Descr * PyArray_ResultType \
+     561             :        (npy_intp, PyArrayObject *arrs[], npy_intp, PyArray_Descr *descrs[]);
+     562             : NPY_NO_EXPORT  npy_bool PyArray_CanCastArrayTo \
+     563             :        (PyArrayObject *, PyArray_Descr *, NPY_CASTING);
+     564             : NPY_NO_EXPORT  npy_bool PyArray_CanCastTypeTo \
+     565             :        (PyArray_Descr *, PyArray_Descr *, NPY_CASTING);
+     566             : NPY_NO_EXPORT  PyArrayObject * PyArray_EinsteinSum \
+     567             :        (char *, npy_intp, PyArrayObject **, PyArray_Descr *, NPY_ORDER, NPY_CASTING, PyArrayObject *);
+     568             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_NewLikeArray \
+     569             :        (PyArrayObject *, NPY_ORDER, PyArray_Descr *, int);
+     570             : NPY_NO_EXPORT  int PyArray_GetArrayParamsFromObject \
+     571             :        (PyObject *NPY_UNUSED(op), PyArray_Descr *NPY_UNUSED(requested_dtype), npy_bool NPY_UNUSED(writeable), PyArray_Descr **NPY_UNUSED(out_dtype), int *NPY_UNUSED(out_ndim), npy_intp *NPY_UNUSED(out_dims), PyArrayObject **NPY_UNUSED(out_arr), PyObject *NPY_UNUSED(context));
+     572             : NPY_NO_EXPORT  int PyArray_ConvertClipmodeSequence \
+     573             :        (PyObject *, NPY_CLIPMODE *, int);
+     574             : NPY_NO_EXPORT  PyObject * PyArray_MatrixProduct2 \
+     575             :        (PyObject *, PyObject *, PyArrayObject*);
+     576             : NPY_NO_EXPORT  npy_bool NpyIter_IsFirstVisit \
+     577             :        (NpyIter *, int);
+     578             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) int PyArray_SetBaseObject \
+     579             :        (PyArrayObject *, PyObject *);
+     580             : NPY_NO_EXPORT  void PyArray_CreateSortedStridePerm \
+     581             :        (int, npy_intp const *, npy_stride_sort_item *);
+     582             : NPY_NO_EXPORT  void PyArray_RemoveAxesInPlace \
+     583             :        (PyArrayObject *, const npy_bool *);
+     584             : NPY_NO_EXPORT  void PyArray_DebugPrint \
+     585             :        (PyArrayObject *);
+     586             : NPY_NO_EXPORT  int PyArray_FailUnlessWriteable \
+     587             :        (PyArrayObject *, const char *);
+     588             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) int PyArray_SetUpdateIfCopyBase \
+     589             :        (PyArrayObject *, PyArrayObject *);
+     590             : NPY_NO_EXPORT  void * PyDataMem_NEW \
+     591             :        (size_t);
+     592             : NPY_NO_EXPORT  void PyDataMem_FREE \
+     593             :        (void *);
+     594             : NPY_NO_EXPORT  void * PyDataMem_RENEW \
+     595             :        (void *, size_t);
+     596             : NPY_NO_EXPORT  PyDataMem_EventHookFunc * PyDataMem_SetEventHook \
+     597             :        (PyDataMem_EventHookFunc *, void *, void **);
+     598             : extern NPY_NO_EXPORT NPY_CASTING NPY_DEFAULT_ASSIGN_CASTING;
+     599             : 
+     600             : NPY_NO_EXPORT  void PyArray_MapIterSwapAxes \
+     601             :        (PyArrayMapIterObject *, PyArrayObject **, int);
+     602             : NPY_NO_EXPORT  PyObject * PyArray_MapIterArray \
+     603             :        (PyArrayObject *, PyObject *);
+     604             : NPY_NO_EXPORT  void PyArray_MapIterNext \
+     605             :        (PyArrayMapIterObject *);
+     606             : NPY_NO_EXPORT  int PyArray_Partition \
+     607             :        (PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND);
+     608             : NPY_NO_EXPORT  PyObject * PyArray_ArgPartition \
+     609             :        (PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND);
+     610             : NPY_NO_EXPORT  int PyArray_SelectkindConverter \
+     611             :        (PyObject *, NPY_SELECTKIND *);
+     612             : NPY_NO_EXPORT  void * PyDataMem_NEW_ZEROED \
+     613             :        (size_t, size_t);
+     614             : NPY_NO_EXPORT  int PyArray_CheckAnyScalarExact \
+     615             :        (PyObject *);
+     616             : NPY_NO_EXPORT  PyObject * PyArray_MapIterArrayCopyIfOverlap \
+     617             :        (PyArrayObject *, PyObject *, int, PyArrayObject *);
+     618             : NPY_NO_EXPORT  int PyArray_ResolveWritebackIfCopy \
+     619             :        (PyArrayObject *);
+     620             : NPY_NO_EXPORT  int PyArray_SetWritebackIfCopyBase \
+     621             :        (PyArrayObject *, PyArrayObject *);
+     622             : NPY_NO_EXPORT  PyObject * PyDataMem_SetHandler \
+     623             :        (PyObject *);
+     624             : NPY_NO_EXPORT  PyObject * PyDataMem_GetHandler \
+     625             :        (void);
+     626             : extern NPY_NO_EXPORT PyObject* PyDataMem_DefaultHandler;
+     627             : 
+     628             : 
+     629             : #else
+     630             : 
+     631             : #if defined(PY_ARRAY_UNIQUE_SYMBOL)
+     632             : #define PyArray_API PY_ARRAY_UNIQUE_SYMBOL
+     633             : #endif
+     634             : 
+     635             : #if defined(NO_IMPORT) || defined(NO_IMPORT_ARRAY)
+     636             : extern void **PyArray_API;
+     637             : #else
+     638             : #if defined(PY_ARRAY_UNIQUE_SYMBOL)
+     639             : void **PyArray_API;
+     640             : #else
+     641             : static void **PyArray_API=NULL;
+     642             : #endif
+     643             : #endif
+     644             : 
+     645             : #define PyArray_GetNDArrayCVersion \
+     646             :         (*(unsigned int (*)(void)) \
+     647             :     PyArray_API[0])
+     648             : #define PyBigArray_Type (*(PyTypeObject *)PyArray_API[1])
+     649             : #define PyArray_Type (*(PyTypeObject *)PyArray_API[2])
+     650             : #define PyArrayDescr_Type (*(PyTypeObject *)PyArray_API[3])
+     651             : #define PyArrayFlags_Type (*(PyTypeObject *)PyArray_API[4])
+     652             : #define PyArrayIter_Type (*(PyTypeObject *)PyArray_API[5])
+     653             : #define PyArrayMultiIter_Type (*(PyTypeObject *)PyArray_API[6])
+     654             : #define NPY_NUMUSERTYPES (*(int *)PyArray_API[7])
+     655             : #define PyBoolArrType_Type (*(PyTypeObject *)PyArray_API[8])
+     656             : #define _PyArrayScalar_BoolValues ((PyBoolScalarObject *)PyArray_API[9])
+     657             : #define PyGenericArrType_Type (*(PyTypeObject *)PyArray_API[10])
+     658             : #define PyNumberArrType_Type (*(PyTypeObject *)PyArray_API[11])
+     659             : #define PyIntegerArrType_Type (*(PyTypeObject *)PyArray_API[12])
+     660             : #define PySignedIntegerArrType_Type (*(PyTypeObject *)PyArray_API[13])
+     661             : #define PyUnsignedIntegerArrType_Type (*(PyTypeObject *)PyArray_API[14])
+     662             : #define PyInexactArrType_Type (*(PyTypeObject *)PyArray_API[15])
+     663             : #define PyFloatingArrType_Type (*(PyTypeObject *)PyArray_API[16])
+     664             : #define PyComplexFloatingArrType_Type (*(PyTypeObject *)PyArray_API[17])
+     665             : #define PyFlexibleArrType_Type (*(PyTypeObject *)PyArray_API[18])
+     666             : #define PyCharacterArrType_Type (*(PyTypeObject *)PyArray_API[19])
+     667             : #define PyByteArrType_Type (*(PyTypeObject *)PyArray_API[20])
+     668             : #define PyShortArrType_Type (*(PyTypeObject *)PyArray_API[21])
+     669             : #define PyIntArrType_Type (*(PyTypeObject *)PyArray_API[22])
+     670             : #define PyLongArrType_Type (*(PyTypeObject *)PyArray_API[23])
+     671             : #define PyLongLongArrType_Type (*(PyTypeObject *)PyArray_API[24])
+     672             : #define PyUByteArrType_Type (*(PyTypeObject *)PyArray_API[25])
+     673             : #define PyUShortArrType_Type (*(PyTypeObject *)PyArray_API[26])
+     674             : #define PyUIntArrType_Type (*(PyTypeObject *)PyArray_API[27])
+     675             : #define PyULongArrType_Type (*(PyTypeObject *)PyArray_API[28])
+     676             : #define PyULongLongArrType_Type (*(PyTypeObject *)PyArray_API[29])
+     677             : #define PyFloatArrType_Type (*(PyTypeObject *)PyArray_API[30])
+     678             : #define PyDoubleArrType_Type (*(PyTypeObject *)PyArray_API[31])
+     679             : #define PyLongDoubleArrType_Type (*(PyTypeObject *)PyArray_API[32])
+     680             : #define PyCFloatArrType_Type (*(PyTypeObject *)PyArray_API[33])
+     681             : #define PyCDoubleArrType_Type (*(PyTypeObject *)PyArray_API[34])
+     682             : #define PyCLongDoubleArrType_Type (*(PyTypeObject *)PyArray_API[35])
+     683             : #define PyObjectArrType_Type (*(PyTypeObject *)PyArray_API[36])
+     684             : #define PyStringArrType_Type (*(PyTypeObject *)PyArray_API[37])
+     685             : #define PyUnicodeArrType_Type (*(PyTypeObject *)PyArray_API[38])
+     686             : #define PyVoidArrType_Type (*(PyTypeObject *)PyArray_API[39])
+     687             : #define PyArray_SetNumericOps \
+     688             :         (*(int (*)(PyObject *)) \
+     689             :     PyArray_API[40])
+     690             : #define PyArray_GetNumericOps \
+     691             :         (*(PyObject * (*)(void)) \
+     692             :     PyArray_API[41])
+     693             : #define PyArray_INCREF \
+     694             :         (*(int (*)(PyArrayObject *)) \
+     695             :     PyArray_API[42])
+     696             : #define PyArray_XDECREF \
+     697             :         (*(int (*)(PyArrayObject *)) \
+     698             :     PyArray_API[43])
+     699             : #define PyArray_SetStringFunction \
+     700             :         (*(void (*)(PyObject *, int)) \
+     701             :     PyArray_API[44])
+     702             : #define PyArray_DescrFromType \
+     703             :         (*(PyArray_Descr * (*)(int)) \
+     704             :     PyArray_API[45])
+     705             : #define PyArray_TypeObjectFromType \
+     706             :         (*(PyObject * (*)(int)) \
+     707             :     PyArray_API[46])
+     708             : #define PyArray_Zero \
+     709             :         (*(char * (*)(PyArrayObject *)) \
+     710             :     PyArray_API[47])
+     711             : #define PyArray_One \
+     712             :         (*(char * (*)(PyArrayObject *)) \
+     713             :     PyArray_API[48])
+     714             : #define PyArray_CastToType \
+     715             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, int)) \
+     716             :     PyArray_API[49])
+     717             : #define PyArray_CastTo \
+     718             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
+     719             :     PyArray_API[50])
+     720             : #define PyArray_CastAnyTo \
+     721             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
+     722             :     PyArray_API[51])
+     723             : #define PyArray_CanCastSafely \
+     724             :         (*(int (*)(int, int)) \
+     725             :     PyArray_API[52])
+     726             : #define PyArray_CanCastTo \
+     727             :         (*(npy_bool (*)(PyArray_Descr *, PyArray_Descr *)) \
+     728             :     PyArray_API[53])
+     729             : #define PyArray_ObjectType \
+     730             :         (*(int (*)(PyObject *, int)) \
+     731             :     PyArray_API[54])
+     732             : #define PyArray_DescrFromObject \
+     733             :         (*(PyArray_Descr * (*)(PyObject *, PyArray_Descr *)) \
+     734             :     PyArray_API[55])
+     735             : #define PyArray_ConvertToCommonType \
+     736             :         (*(PyArrayObject ** (*)(PyObject *, int *)) \
+     737             :     PyArray_API[56])
+     738             : #define PyArray_DescrFromScalar \
+     739             :         (*(PyArray_Descr * (*)(PyObject *)) \
+     740             :     PyArray_API[57])
+     741             : #define PyArray_DescrFromTypeObject \
+     742             :         (*(PyArray_Descr * (*)(PyObject *)) \
+     743             :     PyArray_API[58])
+     744             : #define PyArray_Size \
+     745             :         (*(npy_intp (*)(PyObject *)) \
+     746             :     PyArray_API[59])
+     747             : #define PyArray_Scalar \
+     748             :         (*(PyObject * (*)(void *, PyArray_Descr *, PyObject *)) \
+     749             :     PyArray_API[60])
+     750             : #define PyArray_FromScalar \
+     751             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *)) \
+     752             :     PyArray_API[61])
+     753             : #define PyArray_ScalarAsCtype \
+     754             :         (*(void (*)(PyObject *, void *)) \
+     755             :     PyArray_API[62])
+     756             : #define PyArray_CastScalarToCtype \
+     757             :         (*(int (*)(PyObject *, void *, PyArray_Descr *)) \
+     758             :     PyArray_API[63])
+     759             : #define PyArray_CastScalarDirect \
+     760             :         (*(int (*)(PyObject *, PyArray_Descr *, void *, int)) \
+     761             :     PyArray_API[64])
+     762             : #define PyArray_ScalarFromObject \
+     763             :         (*(PyObject * (*)(PyObject *)) \
+     764             :     PyArray_API[65])
+     765             : #define PyArray_GetCastFunc \
+     766             :         (*(PyArray_VectorUnaryFunc * (*)(PyArray_Descr *, int)) \
+     767             :     PyArray_API[66])
+     768             : #define PyArray_FromDims \
+     769             :         (*(PyObject * (*)(int NPY_UNUSED(nd), int *NPY_UNUSED(d), int NPY_UNUSED(type))) \
+     770             :     PyArray_API[67])
+     771             : #define PyArray_FromDimsAndDataAndDescr \
+     772             :         (*(PyObject * (*)(int NPY_UNUSED(nd), int *NPY_UNUSED(d), PyArray_Descr *, char *NPY_UNUSED(data))) \
+     773             :     PyArray_API[68])
+     774             : #define PyArray_FromAny \
+     775             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, int, int, int, PyObject *)) \
+     776             :     PyArray_API[69])
+     777             : #define PyArray_EnsureArray \
+     778             :         (*(PyObject * (*)(PyObject *)) \
+     779             :     PyArray_API[70])
+     780             : #define PyArray_EnsureAnyArray \
+     781             :         (*(PyObject * (*)(PyObject *)) \
+     782             :     PyArray_API[71])
+     783             : #define PyArray_FromFile \
+     784             :         (*(PyObject * (*)(FILE *, PyArray_Descr *, npy_intp, char *)) \
+     785             :     PyArray_API[72])
+     786             : #define PyArray_FromString \
+     787             :         (*(PyObject * (*)(char *, npy_intp, PyArray_Descr *, npy_intp, char *)) \
+     788             :     PyArray_API[73])
+     789             : #define PyArray_FromBuffer \
+     790             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, npy_intp, npy_intp)) \
+     791             :     PyArray_API[74])
+     792             : #define PyArray_FromIter \
+     793             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, npy_intp)) \
+     794             :     PyArray_API[75])
+     795             : #define PyArray_Return \
+     796             :         (*(PyObject * (*)(PyArrayObject *)) \
+     797             :     PyArray_API[76])
+     798             : #define PyArray_GetField \
+     799             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, int)) \
+     800             :     PyArray_API[77])
+     801             : #define PyArray_SetField \
+     802             :         (*(int (*)(PyArrayObject *, PyArray_Descr *, int, PyObject *)) \
+     803             :     PyArray_API[78])
+     804             : #define PyArray_Byteswap \
+     805             :         (*(PyObject * (*)(PyArrayObject *, npy_bool)) \
+     806             :     PyArray_API[79])
+     807             : #define PyArray_Resize \
+     808             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Dims *, int, NPY_ORDER NPY_UNUSED(order))) \
+     809             :     PyArray_API[80])
+     810             : #define PyArray_MoveInto \
+     811             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
+     812             :     PyArray_API[81])
+     813             : #define PyArray_CopyInto \
+     814             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
+     815             :     PyArray_API[82])
+     816             : #define PyArray_CopyAnyInto \
+     817             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
+     818             :     PyArray_API[83])
+     819             : #define PyArray_CopyObject \
+     820             :         (*(int (*)(PyArrayObject *, PyObject *)) \
+     821             :     PyArray_API[84])
+     822             : #define PyArray_NewCopy \
+     823             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
+     824             :     PyArray_API[85])
+     825             : #define PyArray_ToList \
+     826             :         (*(PyObject * (*)(PyArrayObject *)) \
+     827             :     PyArray_API[86])
+     828             : #define PyArray_ToString \
+     829             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
+     830             :     PyArray_API[87])
+     831             : #define PyArray_ToFile \
+     832             :         (*(int (*)(PyArrayObject *, FILE *, char *, char *)) \
+     833             :     PyArray_API[88])
+     834             : #define PyArray_Dump \
+     835             :         (*(int (*)(PyObject *, PyObject *, int)) \
+     836             :     PyArray_API[89])
+     837             : #define PyArray_Dumps \
+     838             :         (*(PyObject * (*)(PyObject *, int)) \
+     839             :     PyArray_API[90])
+     840             : #define PyArray_ValidType \
+     841             :         (*(int (*)(int)) \
+     842             :     PyArray_API[91])
+     843             : #define PyArray_UpdateFlags \
+     844             :         (*(void (*)(PyArrayObject *, int)) \
+     845             :     PyArray_API[92])
+     846             : #define PyArray_New \
+     847             :         (*(PyObject * (*)(PyTypeObject *, int, npy_intp const *, int, npy_intp const *, void *, int, int, PyObject *)) \
+     848             :     PyArray_API[93])
+     849             : #define PyArray_NewFromDescr \
+     850             :         (*(PyObject * (*)(PyTypeObject *, PyArray_Descr *, int, npy_intp const *, npy_intp const *, void *, int, PyObject *)) \
+     851             :     PyArray_API[94])
+     852             : #define PyArray_DescrNew \
+     853             :         (*(PyArray_Descr * (*)(PyArray_Descr *)) \
+     854             :     PyArray_API[95])
+     855             : #define PyArray_DescrNewFromType \
+     856             :         (*(PyArray_Descr * (*)(int)) \
+     857             :     PyArray_API[96])
+     858             : #define PyArray_GetPriority \
+     859             :         (*(double (*)(PyObject *, double)) \
+     860             :     PyArray_API[97])
+     861             : #define PyArray_IterNew \
+     862             :         (*(PyObject * (*)(PyObject *)) \
+     863             :     PyArray_API[98])
+     864             : #define PyArray_MultiIterNew \
+     865             :         (*(PyObject* (*)(int, ...)) \
+     866             :     PyArray_API[99])
+     867             : #define PyArray_PyIntAsInt \
+     868             :         (*(int (*)(PyObject *)) \
+     869             :     PyArray_API[100])
+     870             : #define PyArray_PyIntAsIntp \
+     871             :         (*(npy_intp (*)(PyObject *)) \
+     872             :     PyArray_API[101])
+     873             : #define PyArray_Broadcast \
+     874             :         (*(int (*)(PyArrayMultiIterObject *)) \
+     875             :     PyArray_API[102])
+     876             : #define PyArray_FillObjectArray \
+     877             :         (*(void (*)(PyArrayObject *, PyObject *)) \
+     878             :     PyArray_API[103])
+     879             : #define PyArray_FillWithScalar \
+     880             :         (*(int (*)(PyArrayObject *, PyObject *)) \
+     881             :     PyArray_API[104])
+     882             : #define PyArray_CheckStrides \
+     883             :         (*(npy_bool (*)(int, int, npy_intp, npy_intp, npy_intp const *, npy_intp const *)) \
+     884             :     PyArray_API[105])
+     885             : #define PyArray_DescrNewByteorder \
+     886             :         (*(PyArray_Descr * (*)(PyArray_Descr *, char)) \
+     887             :     PyArray_API[106])
+     888             : #define PyArray_IterAllButAxis \
+     889             :         (*(PyObject * (*)(PyObject *, int *)) \
+     890             :     PyArray_API[107])
+     891             : #define PyArray_CheckFromAny \
+     892             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, int, int, int, PyObject *)) \
+     893             :     PyArray_API[108])
+     894             : #define PyArray_FromArray \
+     895             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, int)) \
+     896             :     PyArray_API[109])
+     897             : #define PyArray_FromInterface \
+     898             :         (*(PyObject * (*)(PyObject *)) \
+     899             :     PyArray_API[110])
+     900             : #define PyArray_FromStructInterface \
+     901             :         (*(PyObject * (*)(PyObject *)) \
+     902             :     PyArray_API[111])
+     903             : #define PyArray_FromArrayAttr \
+     904             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, PyObject *)) \
+     905             :     PyArray_API[112])
+     906             : #define PyArray_ScalarKind \
+     907             :         (*(NPY_SCALARKIND (*)(int, PyArrayObject **)) \
+     908             :     PyArray_API[113])
+     909             : #define PyArray_CanCoerceScalar \
+     910             :         (*(int (*)(int, int, NPY_SCALARKIND)) \
+     911             :     PyArray_API[114])
+     912             : #define PyArray_NewFlagsObject \
+     913             :         (*(PyObject * (*)(PyObject *)) \
+     914             :     PyArray_API[115])
+     915             : #define PyArray_CanCastScalar \
+     916             :         (*(npy_bool (*)(PyTypeObject *, PyTypeObject *)) \
+     917             :     PyArray_API[116])
+     918             : #define PyArray_CompareUCS4 \
+     919             :         (*(int (*)(npy_ucs4 const *, npy_ucs4 const *, size_t)) \
+     920             :     PyArray_API[117])
+     921             : #define PyArray_RemoveSmallest \
+     922             :         (*(int (*)(PyArrayMultiIterObject *)) \
+     923             :     PyArray_API[118])
+     924             : #define PyArray_ElementStrides \
+     925             :         (*(int (*)(PyObject *)) \
+     926             :     PyArray_API[119])
+     927             : #define PyArray_Item_INCREF \
+     928             :         (*(void (*)(char *, PyArray_Descr *)) \
+     929             :     PyArray_API[120])
+     930             : #define PyArray_Item_XDECREF \
+     931             :         (*(void (*)(char *, PyArray_Descr *)) \
+     932             :     PyArray_API[121])
+     933             : #define PyArray_FieldNames \
+     934             :         (*(PyObject * (*)(PyObject *)) \
+     935             :     PyArray_API[122])
+     936             : #define PyArray_Transpose \
+     937             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Dims *)) \
+     938             :     PyArray_API[123])
+     939             : #define PyArray_TakeFrom \
+     940             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int, PyArrayObject *, NPY_CLIPMODE)) \
+     941             :     PyArray_API[124])
+     942             : #define PyArray_PutTo \
+     943             :         (*(PyObject * (*)(PyArrayObject *, PyObject*, PyObject *, NPY_CLIPMODE)) \
+     944             :     PyArray_API[125])
+     945             : #define PyArray_PutMask \
+     946             :         (*(PyObject * (*)(PyArrayObject *, PyObject*, PyObject*)) \
+     947             :     PyArray_API[126])
+     948             : #define PyArray_Repeat \
+     949             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int)) \
+     950             :     PyArray_API[127])
+     951             : #define PyArray_Choose \
+     952             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, PyArrayObject *, NPY_CLIPMODE)) \
+     953             :     PyArray_API[128])
+     954             : #define PyArray_Sort \
+     955             :         (*(int (*)(PyArrayObject *, int, NPY_SORTKIND)) \
+     956             :     PyArray_API[129])
+     957             : #define PyArray_ArgSort \
+     958             :         (*(PyObject * (*)(PyArrayObject *, int, NPY_SORTKIND)) \
+     959             :     PyArray_API[130])
+     960             : #define PyArray_SearchSorted \
+     961             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, NPY_SEARCHSIDE, PyObject *)) \
+     962             :     PyArray_API[131])
+     963             : #define PyArray_ArgMax \
+     964             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+     965             :     PyArray_API[132])
+     966             : #define PyArray_ArgMin \
+     967             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+     968             :     PyArray_API[133])
+     969             : #define PyArray_Reshape \
+     970             :         (*(PyObject * (*)(PyArrayObject *, PyObject *)) \
+     971             :     PyArray_API[134])
+     972             : #define PyArray_Newshape \
+     973             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Dims *, NPY_ORDER)) \
+     974             :     PyArray_API[135])
+     975             : #define PyArray_Squeeze \
+     976             :         (*(PyObject * (*)(PyArrayObject *)) \
+     977             :     PyArray_API[136])
+     978             : #define PyArray_View \
+     979             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, PyTypeObject *)) \
+     980             :     PyArray_API[137])
+     981             : #define PyArray_SwapAxes \
+     982             :         (*(PyObject * (*)(PyArrayObject *, int, int)) \
+     983             :     PyArray_API[138])
+     984             : #define PyArray_Max \
+     985             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+     986             :     PyArray_API[139])
+     987             : #define PyArray_Min \
+     988             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+     989             :     PyArray_API[140])
+     990             : #define PyArray_Ptp \
+     991             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+     992             :     PyArray_API[141])
+     993             : #define PyArray_Mean \
+     994             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
+     995             :     PyArray_API[142])
+     996             : #define PyArray_Trace \
+     997             :         (*(PyObject * (*)(PyArrayObject *, int, int, int, int, PyArrayObject *)) \
+     998             :     PyArray_API[143])
+     999             : #define PyArray_Diagonal \
+    1000             :         (*(PyObject * (*)(PyArrayObject *, int, int, int)) \
+    1001             :     PyArray_API[144])
+    1002             : #define PyArray_Clip \
+    1003             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, PyObject *, PyArrayObject *)) \
+    1004             :     PyArray_API[145])
+    1005             : #define PyArray_Conjugate \
+    1006             :         (*(PyObject * (*)(PyArrayObject *, PyArrayObject *)) \
+    1007             :     PyArray_API[146])
+    1008             : #define PyArray_Nonzero \
+    1009             :         (*(PyObject * (*)(PyArrayObject *)) \
+    1010             :     PyArray_API[147])
+    1011             : #define PyArray_Std \
+    1012             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *, int)) \
+    1013             :     PyArray_API[148])
+    1014             : #define PyArray_Sum \
+    1015             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
+    1016             :     PyArray_API[149])
+    1017             : #define PyArray_CumSum \
+    1018             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
+    1019             :     PyArray_API[150])
+    1020             : #define PyArray_Prod \
+    1021             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
+    1022             :     PyArray_API[151])
+    1023             : #define PyArray_CumProd \
+    1024             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
+    1025             :     PyArray_API[152])
+    1026             : #define PyArray_All \
+    1027             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+    1028             :     PyArray_API[153])
+    1029             : #define PyArray_Any \
+    1030             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+    1031             :     PyArray_API[154])
+    1032             : #define PyArray_Compress \
+    1033             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int, PyArrayObject *)) \
+    1034             :     PyArray_API[155])
+    1035             : #define PyArray_Flatten \
+    1036             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
+    1037             :     PyArray_API[156])
+    1038             : #define PyArray_Ravel \
+    1039             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
+    1040             :     PyArray_API[157])
+    1041             : #define PyArray_MultiplyList \
+    1042             :         (*(npy_intp (*)(npy_intp const *, int)) \
+    1043             :     PyArray_API[158])
+    1044             : #define PyArray_MultiplyIntList \
+    1045             :         (*(int (*)(int const *, int)) \
+    1046             :     PyArray_API[159])
+    1047             : #define PyArray_GetPtr \
+    1048             :         (*(void * (*)(PyArrayObject *, npy_intp const*)) \
+    1049             :     PyArray_API[160])
+    1050             : #define PyArray_CompareLists \
+    1051             :         (*(int (*)(npy_intp const *, npy_intp const *, int)) \
+    1052             :     PyArray_API[161])
+    1053             : #define PyArray_AsCArray \
+    1054             :         (*(int (*)(PyObject **, void *, npy_intp *, int, PyArray_Descr*)) \
+    1055             :     PyArray_API[162])
+    1056             : #define PyArray_As1D \
+    1057             :         (*(int (*)(PyObject **NPY_UNUSED(op), char **NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int NPY_UNUSED(typecode))) \
+    1058             :     PyArray_API[163])
+    1059             : #define PyArray_As2D \
+    1060             :         (*(int (*)(PyObject **NPY_UNUSED(op), char ***NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int *NPY_UNUSED(d2), int NPY_UNUSED(typecode))) \
+    1061             :     PyArray_API[164])
+    1062             : #define PyArray_Free \
+    1063             :         (*(int (*)(PyObject *, void *)) \
+    1064             :     PyArray_API[165])
+    1065             : #define PyArray_Converter \
+    1066             :         (*(int (*)(PyObject *, PyObject **)) \
+    1067             :     PyArray_API[166])
+    1068             : #define PyArray_IntpFromSequence \
+    1069             :         (*(int (*)(PyObject *, npy_intp *, int)) \
+    1070             :     PyArray_API[167])
+    1071             : #define PyArray_Concatenate \
+    1072             :         (*(PyObject * (*)(PyObject *, int)) \
+    1073             :     PyArray_API[168])
+    1074             : #define PyArray_InnerProduct \
+    1075             :         (*(PyObject * (*)(PyObject *, PyObject *)) \
+    1076             :     PyArray_API[169])
+    1077             : #define PyArray_MatrixProduct \
+    1078             :         (*(PyObject * (*)(PyObject *, PyObject *)) \
+    1079             :     PyArray_API[170])
+    1080             : #define PyArray_CopyAndTranspose \
+    1081             :         (*(PyObject * (*)(PyObject *)) \
+    1082             :     PyArray_API[171])
+    1083             : #define PyArray_Correlate \
+    1084             :         (*(PyObject * (*)(PyObject *, PyObject *, int)) \
+    1085             :     PyArray_API[172])
+    1086             : #define PyArray_TypestrConvert \
+    1087             :         (*(int (*)(int, int)) \
+    1088             :     PyArray_API[173])
+    1089             : #define PyArray_DescrConverter \
+    1090             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
+    1091             :     PyArray_API[174])
+    1092             : #define PyArray_DescrConverter2 \
+    1093             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
+    1094             :     PyArray_API[175])
+    1095             : #define PyArray_IntpConverter \
+    1096             :         (*(int (*)(PyObject *, PyArray_Dims *)) \
+    1097             :     PyArray_API[176])
+    1098             : #define PyArray_BufferConverter \
+    1099             :         (*(int (*)(PyObject *, PyArray_Chunk *)) \
+    1100             :     PyArray_API[177])
+    1101             : #define PyArray_AxisConverter \
+    1102             :         (*(int (*)(PyObject *, int *)) \
+    1103             :     PyArray_API[178])
+    1104             : #define PyArray_BoolConverter \
+    1105             :         (*(int (*)(PyObject *, npy_bool *)) \
+    1106             :     PyArray_API[179])
+    1107             : #define PyArray_ByteorderConverter \
+    1108             :         (*(int (*)(PyObject *, char *)) \
+    1109             :     PyArray_API[180])
+    1110             : #define PyArray_OrderConverter \
+    1111             :         (*(int (*)(PyObject *, NPY_ORDER *)) \
+    1112             :     PyArray_API[181])
+    1113             : #define PyArray_EquivTypes \
+    1114             :         (*(unsigned char (*)(PyArray_Descr *, PyArray_Descr *)) \
+    1115             :     PyArray_API[182])
+    1116             : #define PyArray_Zeros \
+    1117             :         (*(PyObject * (*)(int, npy_intp const *, PyArray_Descr *, int)) \
+    1118             :     PyArray_API[183])
+    1119             : #define PyArray_Empty \
+    1120             :         (*(PyObject * (*)(int, npy_intp const *, PyArray_Descr *, int)) \
+    1121             :     PyArray_API[184])
+    1122             : #define PyArray_Where \
+    1123             :         (*(PyObject * (*)(PyObject *, PyObject *, PyObject *)) \
+    1124             :     PyArray_API[185])
+    1125             : #define PyArray_Arange \
+    1126             :         (*(PyObject * (*)(double, double, double, int)) \
+    1127             :     PyArray_API[186])
+    1128             : #define PyArray_ArangeObj \
+    1129             :         (*(PyObject * (*)(PyObject *, PyObject *, PyObject *, PyArray_Descr *)) \
+    1130             :     PyArray_API[187])
+    1131             : #define PyArray_SortkindConverter \
+    1132             :         (*(int (*)(PyObject *, NPY_SORTKIND *)) \
+    1133             :     PyArray_API[188])
+    1134             : #define PyArray_LexSort \
+    1135             :         (*(PyObject * (*)(PyObject *, int)) \
+    1136             :     PyArray_API[189])
+    1137             : #define PyArray_Round \
+    1138             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
+    1139             :     PyArray_API[190])
+    1140             : #define PyArray_EquivTypenums \
+    1141             :         (*(unsigned char (*)(int, int)) \
+    1142             :     PyArray_API[191])
+    1143             : #define PyArray_RegisterDataType \
+    1144             :         (*(int (*)(PyArray_Descr *)) \
+    1145             :     PyArray_API[192])
+    1146             : #define PyArray_RegisterCastFunc \
+    1147             :         (*(int (*)(PyArray_Descr *, int, PyArray_VectorUnaryFunc *)) \
+    1148             :     PyArray_API[193])
+    1149             : #define PyArray_RegisterCanCast \
+    1150             :         (*(int (*)(PyArray_Descr *, int, NPY_SCALARKIND)) \
+    1151             :     PyArray_API[194])
+    1152             : #define PyArray_InitArrFuncs \
+    1153             :         (*(void (*)(PyArray_ArrFuncs *)) \
+    1154             :     PyArray_API[195])
+    1155             : #define PyArray_IntTupleFromIntp \
+    1156             :         (*(PyObject * (*)(int, npy_intp const *)) \
+    1157             :     PyArray_API[196])
+    1158             : #define PyArray_TypeNumFromName \
+    1159             :         (*(int (*)(char const *)) \
+    1160             :     PyArray_API[197])
+    1161             : #define PyArray_ClipmodeConverter \
+    1162             :         (*(int (*)(PyObject *, NPY_CLIPMODE *)) \
+    1163             :     PyArray_API[198])
+    1164             : #define PyArray_OutputConverter \
+    1165             :         (*(int (*)(PyObject *, PyArrayObject **)) \
+    1166             :     PyArray_API[199])
+    1167             : #define PyArray_BroadcastToShape \
+    1168             :         (*(PyObject * (*)(PyObject *, npy_intp *, int)) \
+    1169             :     PyArray_API[200])
+    1170             : #define _PyArray_SigintHandler \
+    1171             :         (*(void (*)(int)) \
+    1172             :     PyArray_API[201])
+    1173             : #define _PyArray_GetSigintBuf \
+    1174             :         (*(void* (*)(void)) \
+    1175             :     PyArray_API[202])
+    1176             : #define PyArray_DescrAlignConverter \
+    1177             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
+    1178             :     PyArray_API[203])
+    1179             : #define PyArray_DescrAlignConverter2 \
+    1180             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
+    1181             :     PyArray_API[204])
+    1182             : #define PyArray_SearchsideConverter \
+    1183             :         (*(int (*)(PyObject *, void *)) \
+    1184             :     PyArray_API[205])
+    1185             : #define PyArray_CheckAxis \
+    1186             :         (*(PyObject * (*)(PyArrayObject *, int *, int)) \
+    1187             :     PyArray_API[206])
+    1188             : #define PyArray_OverflowMultiplyList \
+    1189             :         (*(npy_intp (*)(npy_intp const *, int)) \
+    1190             :     PyArray_API[207])
+    1191             : #define PyArray_CompareString \
+    1192             :         (*(int (*)(const char *, const char *, size_t)) \
+    1193             :     PyArray_API[208])
+    1194             : #define PyArray_MultiIterFromObjects \
+    1195             :         (*(PyObject* (*)(PyObject **, int, int, ...)) \
+    1196             :     PyArray_API[209])
+    1197             : #define PyArray_GetEndianness \
+    1198             :         (*(int (*)(void)) \
+    1199             :     PyArray_API[210])
+    1200             : #define PyArray_GetNDArrayCFeatureVersion \
+    1201             :         (*(unsigned int (*)(void)) \
+    1202             :     PyArray_API[211])
+    1203             : #define PyArray_Correlate2 \
+    1204             :         (*(PyObject * (*)(PyObject *, PyObject *, int)) \
+    1205             :     PyArray_API[212])
+    1206             : #define PyArray_NeighborhoodIterNew \
+    1207             :         (*(PyObject* (*)(PyArrayIterObject *, const npy_intp *, int, PyArrayObject*)) \
+    1208             :     PyArray_API[213])
+    1209             : #define PyTimeIntegerArrType_Type (*(PyTypeObject *)PyArray_API[214])
+    1210             : #define PyDatetimeArrType_Type (*(PyTypeObject *)PyArray_API[215])
+    1211             : #define PyTimedeltaArrType_Type (*(PyTypeObject *)PyArray_API[216])
+    1212             : #define PyHalfArrType_Type (*(PyTypeObject *)PyArray_API[217])
+    1213             : #define NpyIter_Type (*(PyTypeObject *)PyArray_API[218])
+    1214             : #define PyArray_SetDatetimeParseFunction \
+    1215             :         (*(void (*)(PyObject *NPY_UNUSED(op))) \
+    1216             :     PyArray_API[219])
+    1217             : #define PyArray_DatetimeToDatetimeStruct \
+    1218             :         (*(void (*)(npy_datetime NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *)) \
+    1219             :     PyArray_API[220])
+    1220             : #define PyArray_TimedeltaToTimedeltaStruct \
+    1221             :         (*(void (*)(npy_timedelta NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *)) \
+    1222             :     PyArray_API[221])
+    1223             : #define PyArray_DatetimeStructToDatetime \
+    1224             :         (*(npy_datetime (*)(NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *NPY_UNUSED(d))) \
+    1225             :     PyArray_API[222])
+    1226             : #define PyArray_TimedeltaStructToTimedelta \
+    1227             :         (*(npy_datetime (*)(NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *NPY_UNUSED(d))) \
+    1228             :     PyArray_API[223])
+    1229             : #define NpyIter_New \
+    1230             :         (*(NpyIter * (*)(PyArrayObject *, npy_uint32, NPY_ORDER, NPY_CASTING, PyArray_Descr*)) \
+    1231             :     PyArray_API[224])
+    1232             : #define NpyIter_MultiNew \
+    1233             :         (*(NpyIter * (*)(int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **)) \
+    1234             :     PyArray_API[225])
+    1235             : #define NpyIter_AdvancedNew \
+    1236             :         (*(NpyIter * (*)(int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **, int, int **, npy_intp *, npy_intp)) \
+    1237             :     PyArray_API[226])
+    1238             : #define NpyIter_Copy \
+    1239             :         (*(NpyIter * (*)(NpyIter *)) \
+    1240             :     PyArray_API[227])
+    1241             : #define NpyIter_Deallocate \
+    1242             :         (*(int (*)(NpyIter *)) \
+    1243             :     PyArray_API[228])
+    1244             : #define NpyIter_HasDelayedBufAlloc \
+    1245             :         (*(npy_bool (*)(NpyIter *)) \
+    1246             :     PyArray_API[229])
+    1247             : #define NpyIter_HasExternalLoop \
+    1248             :         (*(npy_bool (*)(NpyIter *)) \
+    1249             :     PyArray_API[230])
+    1250             : #define NpyIter_EnableExternalLoop \
+    1251             :         (*(int (*)(NpyIter *)) \
+    1252             :     PyArray_API[231])
+    1253             : #define NpyIter_GetInnerStrideArray \
+    1254             :         (*(npy_intp * (*)(NpyIter *)) \
+    1255             :     PyArray_API[232])
+    1256             : #define NpyIter_GetInnerLoopSizePtr \
+    1257             :         (*(npy_intp * (*)(NpyIter *)) \
+    1258             :     PyArray_API[233])
+    1259             : #define NpyIter_Reset \
+    1260             :         (*(int (*)(NpyIter *, char **)) \
+    1261             :     PyArray_API[234])
+    1262             : #define NpyIter_ResetBasePointers \
+    1263             :         (*(int (*)(NpyIter *, char **, char **)) \
+    1264             :     PyArray_API[235])
+    1265             : #define NpyIter_ResetToIterIndexRange \
+    1266             :         (*(int (*)(NpyIter *, npy_intp, npy_intp, char **)) \
+    1267             :     PyArray_API[236])
+    1268             : #define NpyIter_GetNDim \
+    1269             :         (*(int (*)(NpyIter *)) \
+    1270             :     PyArray_API[237])
+    1271             : #define NpyIter_GetNOp \
+    1272             :         (*(int (*)(NpyIter *)) \
+    1273             :     PyArray_API[238])
+    1274             : #define NpyIter_GetIterNext \
+    1275             :         (*(NpyIter_IterNextFunc * (*)(NpyIter *, char **)) \
+    1276             :     PyArray_API[239])
+    1277             : #define NpyIter_GetIterSize \
+    1278             :         (*(npy_intp (*)(NpyIter *)) \
+    1279             :     PyArray_API[240])
+    1280             : #define NpyIter_GetIterIndexRange \
+    1281             :         (*(void (*)(NpyIter *, npy_intp *, npy_intp *)) \
+    1282             :     PyArray_API[241])
+    1283             : #define NpyIter_GetIterIndex \
+    1284             :         (*(npy_intp (*)(NpyIter *)) \
+    1285             :     PyArray_API[242])
+    1286             : #define NpyIter_GotoIterIndex \
+    1287             :         (*(int (*)(NpyIter *, npy_intp)) \
+    1288             :     PyArray_API[243])
+    1289             : #define NpyIter_HasMultiIndex \
+    1290             :         (*(npy_bool (*)(NpyIter *)) \
+    1291             :     PyArray_API[244])
+    1292             : #define NpyIter_GetShape \
+    1293             :         (*(int (*)(NpyIter *, npy_intp *)) \
+    1294             :     PyArray_API[245])
+    1295             : #define NpyIter_GetGetMultiIndex \
+    1296             :         (*(NpyIter_GetMultiIndexFunc * (*)(NpyIter *, char **)) \
+    1297             :     PyArray_API[246])
+    1298             : #define NpyIter_GotoMultiIndex \
+    1299             :         (*(int (*)(NpyIter *, npy_intp const *)) \
+    1300             :     PyArray_API[247])
+    1301             : #define NpyIter_RemoveMultiIndex \
+    1302             :         (*(int (*)(NpyIter *)) \
+    1303             :     PyArray_API[248])
+    1304             : #define NpyIter_HasIndex \
+    1305             :         (*(npy_bool (*)(NpyIter *)) \
+    1306             :     PyArray_API[249])
+    1307             : #define NpyIter_IsBuffered \
+    1308             :         (*(npy_bool (*)(NpyIter *)) \
+    1309             :     PyArray_API[250])
+    1310             : #define NpyIter_IsGrowInner \
+    1311             :         (*(npy_bool (*)(NpyIter *)) \
+    1312             :     PyArray_API[251])
+    1313             : #define NpyIter_GetBufferSize \
+    1314             :         (*(npy_intp (*)(NpyIter *)) \
+    1315             :     PyArray_API[252])
+    1316             : #define NpyIter_GetIndexPtr \
+    1317             :         (*(npy_intp * (*)(NpyIter *)) \
+    1318             :     PyArray_API[253])
+    1319             : #define NpyIter_GotoIndex \
+    1320             :         (*(int (*)(NpyIter *, npy_intp)) \
+    1321             :     PyArray_API[254])
+    1322             : #define NpyIter_GetDataPtrArray \
+    1323             :         (*(char ** (*)(NpyIter *)) \
+    1324             :     PyArray_API[255])
+    1325             : #define NpyIter_GetDescrArray \
+    1326             :         (*(PyArray_Descr ** (*)(NpyIter *)) \
+    1327             :     PyArray_API[256])
+    1328             : #define NpyIter_GetOperandArray \
+    1329             :         (*(PyArrayObject ** (*)(NpyIter *)) \
+    1330             :     PyArray_API[257])
+    1331             : #define NpyIter_GetIterView \
+    1332             :         (*(PyArrayObject * (*)(NpyIter *, npy_intp)) \
+    1333             :     PyArray_API[258])
+    1334             : #define NpyIter_GetReadFlags \
+    1335             :         (*(void (*)(NpyIter *, char *)) \
+    1336             :     PyArray_API[259])
+    1337             : #define NpyIter_GetWriteFlags \
+    1338             :         (*(void (*)(NpyIter *, char *)) \
+    1339             :     PyArray_API[260])
+    1340             : #define NpyIter_DebugPrint \
+    1341             :         (*(void (*)(NpyIter *)) \
+    1342             :     PyArray_API[261])
+    1343             : #define NpyIter_IterationNeedsAPI \
+    1344             :         (*(npy_bool (*)(NpyIter *)) \
+    1345             :     PyArray_API[262])
+    1346             : #define NpyIter_GetInnerFixedStrideArray \
+    1347             :         (*(void (*)(NpyIter *, npy_intp *)) \
+    1348             :     PyArray_API[263])
+    1349             : #define NpyIter_RemoveAxis \
+    1350             :         (*(int (*)(NpyIter *, int)) \
+    1351             :     PyArray_API[264])
+    1352             : #define NpyIter_GetAxisStrideArray \
+    1353             :         (*(npy_intp * (*)(NpyIter *, int)) \
+    1354             :     PyArray_API[265])
+    1355             : #define NpyIter_RequiresBuffering \
+    1356             :         (*(npy_bool (*)(NpyIter *)) \
+    1357             :     PyArray_API[266])
+    1358             : #define NpyIter_GetInitialDataPtrArray \
+    1359             :         (*(char ** (*)(NpyIter *)) \
+    1360             :     PyArray_API[267])
+    1361             : #define NpyIter_CreateCompatibleStrides \
+    1362             :         (*(int (*)(NpyIter *, npy_intp, npy_intp *)) \
+    1363             :     PyArray_API[268])
+    1364             : #define PyArray_CastingConverter \
+    1365             :         (*(int (*)(PyObject *, NPY_CASTING *)) \
+    1366             :     PyArray_API[269])
+    1367             : #define PyArray_CountNonzero \
+    1368             :         (*(npy_intp (*)(PyArrayObject *)) \
+    1369             :     PyArray_API[270])
+    1370             : #define PyArray_PromoteTypes \
+    1371             :         (*(PyArray_Descr * (*)(PyArray_Descr *, PyArray_Descr *)) \
+    1372             :     PyArray_API[271])
+    1373             : #define PyArray_MinScalarType \
+    1374             :         (*(PyArray_Descr * (*)(PyArrayObject *)) \
+    1375             :     PyArray_API[272])
+    1376             : #define PyArray_ResultType \
+    1377             :         (*(PyArray_Descr * (*)(npy_intp, PyArrayObject *arrs[], npy_intp, PyArray_Descr *descrs[])) \
+    1378             :     PyArray_API[273])
+    1379             : #define PyArray_CanCastArrayTo \
+    1380             :         (*(npy_bool (*)(PyArrayObject *, PyArray_Descr *, NPY_CASTING)) \
+    1381             :     PyArray_API[274])
+    1382             : #define PyArray_CanCastTypeTo \
+    1383             :         (*(npy_bool (*)(PyArray_Descr *, PyArray_Descr *, NPY_CASTING)) \
+    1384             :     PyArray_API[275])
+    1385             : #define PyArray_EinsteinSum \
+    1386             :         (*(PyArrayObject * (*)(char *, npy_intp, PyArrayObject **, PyArray_Descr *, NPY_ORDER, NPY_CASTING, PyArrayObject *)) \
+    1387             :     PyArray_API[276])
+    1388             : #define PyArray_NewLikeArray \
+    1389             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER, PyArray_Descr *, int)) \
+    1390             :     PyArray_API[277])
+    1391             : #define PyArray_GetArrayParamsFromObject \
+    1392             :         (*(int (*)(PyObject *NPY_UNUSED(op), PyArray_Descr *NPY_UNUSED(requested_dtype), npy_bool NPY_UNUSED(writeable), PyArray_Descr **NPY_UNUSED(out_dtype), int *NPY_UNUSED(out_ndim), npy_intp *NPY_UNUSED(out_dims), PyArrayObject **NPY_UNUSED(out_arr), PyObject *NPY_UNUSED(context))) \
+    1393             :     PyArray_API[278])
+    1394             : #define PyArray_ConvertClipmodeSequence \
+    1395             :         (*(int (*)(PyObject *, NPY_CLIPMODE *, int)) \
+    1396             :     PyArray_API[279])
+    1397             : #define PyArray_MatrixProduct2 \
+    1398             :         (*(PyObject * (*)(PyObject *, PyObject *, PyArrayObject*)) \
+    1399             :     PyArray_API[280])
+    1400             : #define NpyIter_IsFirstVisit \
+    1401             :         (*(npy_bool (*)(NpyIter *, int)) \
+    1402             :     PyArray_API[281])
+    1403             : #define PyArray_SetBaseObject \
+    1404             :         (*(int (*)(PyArrayObject *, PyObject *)) \
+    1405             :     PyArray_API[282])
+    1406             : #define PyArray_CreateSortedStridePerm \
+    1407             :         (*(void (*)(int, npy_intp const *, npy_stride_sort_item *)) \
+    1408             :     PyArray_API[283])
+    1409             : #define PyArray_RemoveAxesInPlace \
+    1410             :         (*(void (*)(PyArrayObject *, const npy_bool *)) \
+    1411             :     PyArray_API[284])
+    1412             : #define PyArray_DebugPrint \
+    1413             :         (*(void (*)(PyArrayObject *)) \
+    1414             :     PyArray_API[285])
+    1415             : #define PyArray_FailUnlessWriteable \
+    1416             :         (*(int (*)(PyArrayObject *, const char *)) \
+    1417             :     PyArray_API[286])
+    1418             : #define PyArray_SetUpdateIfCopyBase \
+    1419             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
+    1420             :     PyArray_API[287])
+    1421             : #define PyDataMem_NEW \
+    1422             :         (*(void * (*)(size_t)) \
+    1423             :     PyArray_API[288])
+    1424             : #define PyDataMem_FREE \
+    1425             :         (*(void (*)(void *)) \
+    1426             :     PyArray_API[289])
+    1427             : #define PyDataMem_RENEW \
+    1428             :         (*(void * (*)(void *, size_t)) \
+    1429             :     PyArray_API[290])
+    1430             : #define PyDataMem_SetEventHook \
+    1431             :         (*(PyDataMem_EventHookFunc * (*)(PyDataMem_EventHookFunc *, void *, void **)) \
+    1432             :     PyArray_API[291])
+    1433             : #define NPY_DEFAULT_ASSIGN_CASTING (*(NPY_CASTING *)PyArray_API[292])
+    1434             : #define PyArray_MapIterSwapAxes \
+    1435             :         (*(void (*)(PyArrayMapIterObject *, PyArrayObject **, int)) \
+    1436             :     PyArray_API[293])
+    1437             : #define PyArray_MapIterArray \
+    1438             :         (*(PyObject * (*)(PyArrayObject *, PyObject *)) \
+    1439             :     PyArray_API[294])
+    1440             : #define PyArray_MapIterNext \
+    1441             :         (*(void (*)(PyArrayMapIterObject *)) \
+    1442             :     PyArray_API[295])
+    1443             : #define PyArray_Partition \
+    1444             :         (*(int (*)(PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND)) \
+    1445             :     PyArray_API[296])
+    1446             : #define PyArray_ArgPartition \
+    1447             :         (*(PyObject * (*)(PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND)) \
+    1448             :     PyArray_API[297])
+    1449             : #define PyArray_SelectkindConverter \
+    1450             :         (*(int (*)(PyObject *, NPY_SELECTKIND *)) \
+    1451             :     PyArray_API[298])
+    1452             : #define PyDataMem_NEW_ZEROED \
+    1453             :         (*(void * (*)(size_t, size_t)) \
+    1454             :     PyArray_API[299])
+    1455             : #define PyArray_CheckAnyScalarExact \
+    1456             :         (*(int (*)(PyObject *)) \
+    1457             :     PyArray_API[300])
+    1458             : #define PyArray_MapIterArrayCopyIfOverlap \
+    1459             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int, PyArrayObject *)) \
+    1460             :     PyArray_API[301])
+    1461             : #define PyArray_ResolveWritebackIfCopy \
+    1462             :         (*(int (*)(PyArrayObject *)) \
+    1463             :     PyArray_API[302])
+    1464             : #define PyArray_SetWritebackIfCopyBase \
+    1465             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
+    1466             :     PyArray_API[303])
+    1467             : 
+    1468             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
+    1469             : #define PyDataMem_SetHandler \
+    1470             :         (*(PyObject * (*)(PyObject *)) \
+    1471             :     PyArray_API[304])
+    1472             : #endif
+    1473             : 
+    1474             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
+    1475             : #define PyDataMem_GetHandler \
+    1476             :         (*(PyObject * (*)(void)) \
+    1477             :     PyArray_API[305])
+    1478             : #endif
+    1479             : #define PyDataMem_DefaultHandler (*(PyObject* *)PyArray_API[306])
+    1480             : 
+    1481             : #if !defined(NO_IMPORT_ARRAY) && !defined(NO_IMPORT)
+    1482             : static int
+    1483           4 : _import_array(void)
+    1484             : {
+    1485             :   int st;
+    1486           4 :   PyObject *numpy = PyImport_ImportModule("numpy.core._multiarray_umath");
+    1487             :   PyObject *c_api = NULL;
+    1488             : 
+    1489           4 :   if (numpy == NULL) {
+    1490             :       return -1;
+    1491             :   }
+    1492           4 :   c_api = PyObject_GetAttrString(numpy, "_ARRAY_API");
+    1493             :   Py_DECREF(numpy);
+    1494           4 :   if (c_api == NULL) {
+    1495             :       return -1;
+    1496             :   }
+    1497             : 
+    1498           4 :   if (!PyCapsule_CheckExact(c_api)) {
+    1499           0 :       PyErr_SetString(PyExc_RuntimeError, "_ARRAY_API is not PyCapsule object");
+    1500             :       Py_DECREF(c_api);
+    1501           0 :       return -1;
+    1502             :   }
+    1503           4 :   PyArray_API = (void **)PyCapsule_GetPointer(c_api, NULL);
+    1504             :   Py_DECREF(c_api);
+    1505           4 :   if (PyArray_API == NULL) {
+    1506           0 :       PyErr_SetString(PyExc_RuntimeError, "_ARRAY_API is NULL pointer");
+    1507           0 :       return -1;
+    1508             :   }
+    1509             : 
+    1510             :   /* Perform runtime check of C API version */
+    1511           4 :   if (NPY_VERSION != PyArray_GetNDArrayCVersion()) {
+    1512           0 :       PyErr_Format(PyExc_RuntimeError, "module compiled against "\
+    1513             :              "ABI version 0x%x but this version of numpy is 0x%x", \
+    1514           0 :              (int) NPY_VERSION, (int) PyArray_GetNDArrayCVersion());
+    1515           0 :       return -1;
+    1516             :   }
+    1517           4 :   if (NPY_FEATURE_VERSION > PyArray_GetNDArrayCFeatureVersion()) {
+    1518           0 :       PyErr_Format(PyExc_RuntimeError, "module compiled against "\
+    1519             :              "API version 0x%x but this version of numpy is 0x%x . "\
+    1520             :              "Check the section C-API incompatibility at the "\
+    1521             :              "Troubleshooting ImportError section at "\
+    1522             :              "https://numpy.org/devdocs/user/troubleshooting-importerror.html"\
+    1523             :              "#c-api-incompatibility "\
+    1524             :               "for indications on how to solve this problem .", \
+    1525           0 :              (int) NPY_FEATURE_VERSION, (int) PyArray_GetNDArrayCFeatureVersion());
+    1526           0 :       return -1;
+    1527             :   }
+    1528             : 
+    1529             :   /*
+    1530             :    * Perform runtime check of endianness and check it matches the one set by
+    1531             :    * the headers (npy_endian.h) as a safeguard
+    1532             :    */
+    1533           4 :   st = PyArray_GetEndianness();
+    1534           4 :   if (st == NPY_CPU_UNKNOWN_ENDIAN) {
+    1535           0 :       PyErr_SetString(PyExc_RuntimeError,
+    1536             :                       "FATAL: module compiled as unknown endian");
+    1537           0 :       return -1;
+    1538             :   }
+    1539             : #if NPY_BYTE_ORDER == NPY_BIG_ENDIAN
+    1540             :   if (st != NPY_CPU_BIG) {
+    1541             :       PyErr_SetString(PyExc_RuntimeError,
+    1542             :                       "FATAL: module compiled as big endian, but "
+    1543             :                       "detected different endianness at runtime");
+    1544             :       return -1;
+    1545             :   }
+    1546             : #elif NPY_BYTE_ORDER == NPY_LITTLE_ENDIAN
+    1547           4 :   if (st != NPY_CPU_LITTLE) {
+    1548           0 :       PyErr_SetString(PyExc_RuntimeError,
+    1549             :                       "FATAL: module compiled as little endian, but "
+    1550             :                       "detected different endianness at runtime");
+    1551           0 :       return -1;
+    1552             :   }
+    1553             : #endif
+    1554             : 
+    1555             :   return 0;
+    1556             : }
+    1557             : 
+    1558             : #define import_array() {if (_import_array() < 0) {PyErr_Print(); PyErr_SetString(PyExc_ImportError, "numpy.core.multiarray failed to import"); return NULL; } }
+    1559             : 
+    1560             : #define import_array1(ret) {if (_import_array() < 0) {PyErr_Print(); PyErr_SetString(PyExc_ImportError, "numpy.core.multiarray failed to import"); return ret; } }
+    1561             : 
+    1562             : #define import_array2(msg, ret) {if (_import_array() < 0) {PyErr_Print(); PyErr_SetString(PyExc_ImportError, msg); return ret; } }
+    1563             : 
+    1564             : #endif
+    1565             : 
+    1566             : #endif
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html new file mode 100644 index 000000000..1e4f8aa99 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __ufunc_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81650.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_import_umath4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html new file mode 100644 index 000000000..093ab6873 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __ufunc_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81650.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_import_umath4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html new file mode 100644 index 000000000..da3452463 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html @@ -0,0 +1,390 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __ufunc_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81650.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : 
+       2             : #ifdef _UMATHMODULE
+       3             : 
+       4             : extern NPY_NO_EXPORT PyTypeObject PyUFunc_Type;
+       5             : 
+       6             : extern NPY_NO_EXPORT PyTypeObject PyUFunc_Type;
+       7             : 
+       8             : NPY_NO_EXPORT  PyObject * PyUFunc_FromFuncAndData \
+       9             :        (PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int);
+      10             : NPY_NO_EXPORT  int PyUFunc_RegisterLoopForType \
+      11             :        (PyUFuncObject *, int, PyUFuncGenericFunction, const int *, void *);
+      12             : NPY_NO_EXPORT  int PyUFunc_GenericFunction \
+      13             :        (PyUFuncObject *NPY_UNUSED(ufunc), PyObject *NPY_UNUSED(args), PyObject *NPY_UNUSED(kwds), PyArrayObject **NPY_UNUSED(op));
+      14             : NPY_NO_EXPORT  void PyUFunc_f_f_As_d_d \
+      15             :        (char **, npy_intp const *, npy_intp const *, void *);
+      16             : NPY_NO_EXPORT  void PyUFunc_d_d \
+      17             :        (char **, npy_intp const *, npy_intp const *, void *);
+      18             : NPY_NO_EXPORT  void PyUFunc_f_f \
+      19             :        (char **, npy_intp const *, npy_intp const *, void *);
+      20             : NPY_NO_EXPORT  void PyUFunc_g_g \
+      21             :        (char **, npy_intp const *, npy_intp const *, void *);
+      22             : NPY_NO_EXPORT  void PyUFunc_F_F_As_D_D \
+      23             :        (char **, npy_intp const *, npy_intp const *, void *);
+      24             : NPY_NO_EXPORT  void PyUFunc_F_F \
+      25             :        (char **, npy_intp const *, npy_intp const *, void *);
+      26             : NPY_NO_EXPORT  void PyUFunc_D_D \
+      27             :        (char **, npy_intp const *, npy_intp const *, void *);
+      28             : NPY_NO_EXPORT  void PyUFunc_G_G \
+      29             :        (char **, npy_intp const *, npy_intp const *, void *);
+      30             : NPY_NO_EXPORT  void PyUFunc_O_O \
+      31             :        (char **, npy_intp const *, npy_intp const *, void *);
+      32             : NPY_NO_EXPORT  void PyUFunc_ff_f_As_dd_d \
+      33             :        (char **, npy_intp const *, npy_intp const *, void *);
+      34             : NPY_NO_EXPORT  void PyUFunc_ff_f \
+      35             :        (char **, npy_intp const *, npy_intp const *, void *);
+      36             : NPY_NO_EXPORT  void PyUFunc_dd_d \
+      37             :        (char **, npy_intp const *, npy_intp const *, void *);
+      38             : NPY_NO_EXPORT  void PyUFunc_gg_g \
+      39             :        (char **, npy_intp const *, npy_intp const *, void *);
+      40             : NPY_NO_EXPORT  void PyUFunc_FF_F_As_DD_D \
+      41             :        (char **, npy_intp const *, npy_intp const *, void *);
+      42             : NPY_NO_EXPORT  void PyUFunc_DD_D \
+      43             :        (char **, npy_intp const *, npy_intp const *, void *);
+      44             : NPY_NO_EXPORT  void PyUFunc_FF_F \
+      45             :        (char **, npy_intp const *, npy_intp const *, void *);
+      46             : NPY_NO_EXPORT  void PyUFunc_GG_G \
+      47             :        (char **, npy_intp const *, npy_intp const *, void *);
+      48             : NPY_NO_EXPORT  void PyUFunc_OO_O \
+      49             :        (char **, npy_intp const *, npy_intp const *, void *);
+      50             : NPY_NO_EXPORT  void PyUFunc_O_O_method \
+      51             :        (char **, npy_intp const *, npy_intp const *, void *);
+      52             : NPY_NO_EXPORT  void PyUFunc_OO_O_method \
+      53             :        (char **, npy_intp const *, npy_intp const *, void *);
+      54             : NPY_NO_EXPORT  void PyUFunc_On_Om \
+      55             :        (char **, npy_intp const *, npy_intp const *, void *);
+      56             : NPY_NO_EXPORT  int PyUFunc_GetPyValues \
+      57             :        (char *, int *, int *, PyObject **);
+      58             : NPY_NO_EXPORT  int PyUFunc_checkfperr \
+      59             :        (int, PyObject *, int *);
+      60             : NPY_NO_EXPORT  void PyUFunc_clearfperr \
+      61             :        (void);
+      62             : NPY_NO_EXPORT  int PyUFunc_getfperr \
+      63             :        (void);
+      64             : NPY_NO_EXPORT  int PyUFunc_handlefperr \
+      65             :        (int, PyObject *, int, int *);
+      66             : NPY_NO_EXPORT  int PyUFunc_ReplaceLoopBySignature \
+      67             :        (PyUFuncObject *, PyUFuncGenericFunction, const int *, PyUFuncGenericFunction *);
+      68             : NPY_NO_EXPORT  PyObject * PyUFunc_FromFuncAndDataAndSignature \
+      69             :        (PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int, const char *);
+      70             : NPY_NO_EXPORT  int PyUFunc_SetUsesArraysAsData \
+      71             :        (void **NPY_UNUSED(data), size_t NPY_UNUSED(i));
+      72             : NPY_NO_EXPORT  void PyUFunc_e_e \
+      73             :        (char **, npy_intp const *, npy_intp const *, void *);
+      74             : NPY_NO_EXPORT  void PyUFunc_e_e_As_f_f \
+      75             :        (char **, npy_intp const *, npy_intp const *, void *);
+      76             : NPY_NO_EXPORT  void PyUFunc_e_e_As_d_d \
+      77             :        (char **, npy_intp const *, npy_intp const *, void *);
+      78             : NPY_NO_EXPORT  void PyUFunc_ee_e \
+      79             :        (char **, npy_intp const *, npy_intp const *, void *);
+      80             : NPY_NO_EXPORT  void PyUFunc_ee_e_As_ff_f \
+      81             :        (char **, npy_intp const *, npy_intp const *, void *);
+      82             : NPY_NO_EXPORT  void PyUFunc_ee_e_As_dd_d \
+      83             :        (char **, npy_intp const *, npy_intp const *, void *);
+      84             : NPY_NO_EXPORT  int PyUFunc_DefaultTypeResolver \
+      85             :        (PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyObject *, PyArray_Descr **);
+      86             : NPY_NO_EXPORT  int PyUFunc_ValidateCasting \
+      87             :        (PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyArray_Descr **);
+      88             : NPY_NO_EXPORT  int PyUFunc_RegisterLoopForDescr \
+      89             :        (PyUFuncObject *, PyArray_Descr *, PyUFuncGenericFunction, PyArray_Descr **, void *);
+      90             : NPY_NO_EXPORT  PyObject * PyUFunc_FromFuncAndDataAndSignatureAndIdentity \
+      91             :        (PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, const int, const char *, PyObject *);
+      92             : 
+      93             : #else
+      94             : 
+      95             : #if defined(PY_UFUNC_UNIQUE_SYMBOL)
+      96             : #define PyUFunc_API PY_UFUNC_UNIQUE_SYMBOL
+      97             : #endif
+      98             : 
+      99             : #if defined(NO_IMPORT) || defined(NO_IMPORT_UFUNC)
+     100             : extern void **PyUFunc_API;
+     101             : #else
+     102             : #if defined(PY_UFUNC_UNIQUE_SYMBOL)
+     103             : void **PyUFunc_API;
+     104             : #else
+     105             : static void **PyUFunc_API=NULL;
+     106             : #endif
+     107             : #endif
+     108             : 
+     109             : #define PyUFunc_Type (*(PyTypeObject *)PyUFunc_API[0])
+     110             : #define PyUFunc_FromFuncAndData \
+     111             :         (*(PyObject * (*)(PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int)) \
+     112             :     PyUFunc_API[1])
+     113             : #define PyUFunc_RegisterLoopForType \
+     114             :         (*(int (*)(PyUFuncObject *, int, PyUFuncGenericFunction, const int *, void *)) \
+     115             :     PyUFunc_API[2])
+     116             : #define PyUFunc_GenericFunction \
+     117             :         (*(int (*)(PyUFuncObject *NPY_UNUSED(ufunc), PyObject *NPY_UNUSED(args), PyObject *NPY_UNUSED(kwds), PyArrayObject **NPY_UNUSED(op))) \
+     118             :     PyUFunc_API[3])
+     119             : #define PyUFunc_f_f_As_d_d \
+     120             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     121             :     PyUFunc_API[4])
+     122             : #define PyUFunc_d_d \
+     123             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     124             :     PyUFunc_API[5])
+     125             : #define PyUFunc_f_f \
+     126             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     127             :     PyUFunc_API[6])
+     128             : #define PyUFunc_g_g \
+     129             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     130             :     PyUFunc_API[7])
+     131             : #define PyUFunc_F_F_As_D_D \
+     132             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     133             :     PyUFunc_API[8])
+     134             : #define PyUFunc_F_F \
+     135             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     136             :     PyUFunc_API[9])
+     137             : #define PyUFunc_D_D \
+     138             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     139             :     PyUFunc_API[10])
+     140             : #define PyUFunc_G_G \
+     141             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     142             :     PyUFunc_API[11])
+     143             : #define PyUFunc_O_O \
+     144             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     145             :     PyUFunc_API[12])
+     146             : #define PyUFunc_ff_f_As_dd_d \
+     147             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     148             :     PyUFunc_API[13])
+     149             : #define PyUFunc_ff_f \
+     150             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     151             :     PyUFunc_API[14])
+     152             : #define PyUFunc_dd_d \
+     153             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     154             :     PyUFunc_API[15])
+     155             : #define PyUFunc_gg_g \
+     156             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     157             :     PyUFunc_API[16])
+     158             : #define PyUFunc_FF_F_As_DD_D \
+     159             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     160             :     PyUFunc_API[17])
+     161             : #define PyUFunc_DD_D \
+     162             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     163             :     PyUFunc_API[18])
+     164             : #define PyUFunc_FF_F \
+     165             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     166             :     PyUFunc_API[19])
+     167             : #define PyUFunc_GG_G \
+     168             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     169             :     PyUFunc_API[20])
+     170             : #define PyUFunc_OO_O \
+     171             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     172             :     PyUFunc_API[21])
+     173             : #define PyUFunc_O_O_method \
+     174             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     175             :     PyUFunc_API[22])
+     176             : #define PyUFunc_OO_O_method \
+     177             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     178             :     PyUFunc_API[23])
+     179             : #define PyUFunc_On_Om \
+     180             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     181             :     PyUFunc_API[24])
+     182             : #define PyUFunc_GetPyValues \
+     183             :         (*(int (*)(char *, int *, int *, PyObject **)) \
+     184             :     PyUFunc_API[25])
+     185             : #define PyUFunc_checkfperr \
+     186             :         (*(int (*)(int, PyObject *, int *)) \
+     187             :     PyUFunc_API[26])
+     188             : #define PyUFunc_clearfperr \
+     189             :         (*(void (*)(void)) \
+     190             :     PyUFunc_API[27])
+     191             : #define PyUFunc_getfperr \
+     192             :         (*(int (*)(void)) \
+     193             :     PyUFunc_API[28])
+     194             : #define PyUFunc_handlefperr \
+     195             :         (*(int (*)(int, PyObject *, int, int *)) \
+     196             :     PyUFunc_API[29])
+     197             : #define PyUFunc_ReplaceLoopBySignature \
+     198             :         (*(int (*)(PyUFuncObject *, PyUFuncGenericFunction, const int *, PyUFuncGenericFunction *)) \
+     199             :     PyUFunc_API[30])
+     200             : #define PyUFunc_FromFuncAndDataAndSignature \
+     201             :         (*(PyObject * (*)(PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int, const char *)) \
+     202             :     PyUFunc_API[31])
+     203             : #define PyUFunc_SetUsesArraysAsData \
+     204             :         (*(int (*)(void **NPY_UNUSED(data), size_t NPY_UNUSED(i))) \
+     205             :     PyUFunc_API[32])
+     206             : #define PyUFunc_e_e \
+     207             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     208             :     PyUFunc_API[33])
+     209             : #define PyUFunc_e_e_As_f_f \
+     210             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     211             :     PyUFunc_API[34])
+     212             : #define PyUFunc_e_e_As_d_d \
+     213             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     214             :     PyUFunc_API[35])
+     215             : #define PyUFunc_ee_e \
+     216             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     217             :     PyUFunc_API[36])
+     218             : #define PyUFunc_ee_e_As_ff_f \
+     219             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     220             :     PyUFunc_API[37])
+     221             : #define PyUFunc_ee_e_As_dd_d \
+     222             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
+     223             :     PyUFunc_API[38])
+     224             : #define PyUFunc_DefaultTypeResolver \
+     225             :         (*(int (*)(PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyObject *, PyArray_Descr **)) \
+     226             :     PyUFunc_API[39])
+     227             : #define PyUFunc_ValidateCasting \
+     228             :         (*(int (*)(PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyArray_Descr **)) \
+     229             :     PyUFunc_API[40])
+     230             : #define PyUFunc_RegisterLoopForDescr \
+     231             :         (*(int (*)(PyUFuncObject *, PyArray_Descr *, PyUFuncGenericFunction, PyArray_Descr **, void *)) \
+     232             :     PyUFunc_API[41])
+     233             : 
+     234             : #if NPY_FEATURE_VERSION >= NPY_1_16_API_VERSION
+     235             : #define PyUFunc_FromFuncAndDataAndSignatureAndIdentity \
+     236             :         (*(PyObject * (*)(PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, const int, const char *, PyObject *)) \
+     237             :     PyUFunc_API[42])
+     238             : #endif
+     239             : 
+     240             : static inline int
+     241           4 : _import_umath(void)
+     242             : {
+     243           4 :   PyObject *numpy = PyImport_ImportModule("numpy.core._multiarray_umath");
+     244             :   PyObject *c_api = NULL;
+     245             : 
+     246           4 :   if (numpy == NULL) {
+     247           0 :       PyErr_SetString(PyExc_ImportError,
+     248             :                       "numpy.core._multiarray_umath failed to import");
+     249           0 :       return -1;
+     250             :   }
+     251           4 :   c_api = PyObject_GetAttrString(numpy, "_UFUNC_API");
+     252             :   Py_DECREF(numpy);
+     253           4 :   if (c_api == NULL) {
+     254           0 :       PyErr_SetString(PyExc_AttributeError, "_UFUNC_API not found");
+     255           0 :       return -1;
+     256             :   }
+     257             : 
+     258           4 :   if (!PyCapsule_CheckExact(c_api)) {
+     259           0 :       PyErr_SetString(PyExc_RuntimeError, "_UFUNC_API is not PyCapsule object");
+     260             :       Py_DECREF(c_api);
+     261           0 :       return -1;
+     262             :   }
+     263           4 :   PyUFunc_API = (void **)PyCapsule_GetPointer(c_api, NULL);
+     264             :   Py_DECREF(c_api);
+     265           4 :   if (PyUFunc_API == NULL) {
+     266           0 :       PyErr_SetString(PyExc_RuntimeError, "_UFUNC_API is NULL pointer");
+     267           0 :       return -1;
+     268             :   }
+     269             :   return 0;
+     270             : }
+     271             : 
+     272             : #define import_umath() \
+     273             :     do {\
+     274             :         UFUNC_NOFPE\
+     275             :         if (_import_umath() < 0) {\
+     276             :             PyErr_Print();\
+     277             :             PyErr_SetString(PyExc_ImportError,\
+     278             :                     "numpy.core.umath failed to import");\
+     279             :             return NULL;\
+     280             :         }\
+     281             :     } while(0)
+     282             : 
+     283             : #define import_umath1(ret) \
+     284             :     do {\
+     285             :         UFUNC_NOFPE\
+     286             :         if (_import_umath() < 0) {\
+     287             :             PyErr_Print();\
+     288             :             PyErr_SetString(PyExc_ImportError,\
+     289             :                     "numpy.core.umath failed to import");\
+     290             :             return ret;\
+     291             :         }\
+     292             :     } while(0)
+     293             : 
+     294             : #define import_umath2(ret, msg) \
+     295             :     do {\
+     296             :         UFUNC_NOFPE\
+     297             :         if (_import_umath() < 0) {\
+     298             :             PyErr_Print();\
+     299             :             PyErr_SetString(PyExc_ImportError, msg);\
+     300             :             return ret;\
+     301             :         }\
+     302             :     } while(0)
+     303             : 
+     304             : #define import_ufunc() \
+     305             :     do {\
+     306             :         UFUNC_NOFPE\
+     307             :         if (_import_umath() < 0) {\
+     308             :             PyErr_Print();\
+     309             :             PyErr_SetString(PyExc_ImportError,\
+     310             :                     "numpy.core.umath failed to import");\
+     311             :         }\
+     312             :     } while(0)
+     313             : 
+     314             : #endif
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html new file mode 100644 index 000000000..2686fc849 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpyHitTotalCoverage
Test:coverage.info.cleanedLines:214843.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ndarraytypes.h +
0.0%
+
0.0 %0 / 5-0 / 0
__ufunc_api.h +
50.0%50.0%
+
50.0 %8 / 16100.0 %1 / 1
__multiarray_api.h +
48.1%48.1%
+
48.1 %13 / 27100.0 %1 / 1
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html new file mode 100644 index 000000000..80f238d04 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpyHitTotalCoverage
Test:coverage.info.cleanedLines:214843.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ndarraytypes.h +
0.0%
+
0.0 %0 / 5-0 / 0
__multiarray_api.h +
48.1%48.1%
+
48.1 %13 / 27100.0 %1 / 1
__ufunc_api.h +
50.0%50.0%
+
50.0 %8 / 16100.0 %1 / 1
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html new file mode 100644 index 000000000..124271195 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpyHitTotalCoverage
Test:coverage.info.cleanedLines:214843.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
__multiarray_api.h +
48.1%48.1%
+
48.1 %13 / 27100.0 %1 / 1
__ufunc_api.h +
50.0%50.0%
+
50.0 %8 / 16100.0 %1 / 1
ndarraytypes.h +
0.0%
+
0.0 %0 / 5-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html new file mode 100644 index 000000000..84a09fcbb --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - ndarraytypes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html new file mode 100644 index 000000000..ebd0e1b6a --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - ndarraytypes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html new file mode 100644 index 000000000..c960b1d11 --- /dev/null +++ b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html @@ -0,0 +1,2021 @@ + + + + + + + LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - ndarraytypes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef NUMPY_CORE_INCLUDE_NUMPY_NDARRAYTYPES_H_
+       2             : #define NUMPY_CORE_INCLUDE_NUMPY_NDARRAYTYPES_H_
+       3             : 
+       4             : #include "npy_common.h"
+       5             : #include "npy_endian.h"
+       6             : #include "npy_cpu.h"
+       7             : #include "utils.h"
+       8             : 
+       9             : #define NPY_NO_EXPORT NPY_VISIBILITY_HIDDEN
+      10             : 
+      11             : /* Only use thread if configured in config and python supports it */
+      12             : #if defined WITH_THREAD && !NPY_NO_SMP
+      13             :         #define NPY_ALLOW_THREADS 1
+      14             : #else
+      15             :         #define NPY_ALLOW_THREADS 0
+      16             : #endif
+      17             : 
+      18             : #ifndef __has_extension
+      19             : #define __has_extension(x) 0
+      20             : #endif
+      21             : 
+      22             : #if !defined(_NPY_NO_DEPRECATIONS) && \
+      23             :     ((defined(__GNUC__)&& __GNUC__ >= 6) || \
+      24             :      __has_extension(attribute_deprecated_with_message))
+      25             : #define NPY_ATTR_DEPRECATE(text) __attribute__ ((deprecated (text)))
+      26             : #else
+      27             : #define NPY_ATTR_DEPRECATE(text)
+      28             : #endif
+      29             : 
+      30             : /*
+      31             :  * There are several places in the code where an array of dimensions
+      32             :  * is allocated statically.  This is the size of that static
+      33             :  * allocation.
+      34             :  *
+      35             :  * The array creation itself could have arbitrary dimensions but all
+      36             :  * the places where static allocation is used would need to be changed
+      37             :  * to dynamic (including inside of several structures)
+      38             :  */
+      39             : 
+      40             : #define NPY_MAXDIMS 32
+      41             : #define NPY_MAXARGS 32
+      42             : 
+      43             : /* Used for Converter Functions "O&" code in ParseTuple */
+      44             : #define NPY_FAIL 0
+      45             : #define NPY_SUCCEED 1
+      46             : 
+      47             : 
+      48             : enum NPY_TYPES {    NPY_BOOL=0,
+      49             :                     NPY_BYTE, NPY_UBYTE,
+      50             :                     NPY_SHORT, NPY_USHORT,
+      51             :                     NPY_INT, NPY_UINT,
+      52             :                     NPY_LONG, NPY_ULONG,
+      53             :                     NPY_LONGLONG, NPY_ULONGLONG,
+      54             :                     NPY_FLOAT, NPY_DOUBLE, NPY_LONGDOUBLE,
+      55             :                     NPY_CFLOAT, NPY_CDOUBLE, NPY_CLONGDOUBLE,
+      56             :                     NPY_OBJECT=17,
+      57             :                     NPY_STRING, NPY_UNICODE,
+      58             :                     NPY_VOID,
+      59             :                     /*
+      60             :                      * New 1.6 types appended, may be integrated
+      61             :                      * into the above in 2.0.
+      62             :                      */
+      63             :                     NPY_DATETIME, NPY_TIMEDELTA, NPY_HALF,
+      64             : 
+      65             :                     NPY_NTYPES,
+      66             :                     NPY_NOTYPE,
+      67             :                     NPY_CHAR NPY_ATTR_DEPRECATE("Use NPY_STRING"),
+      68             :                     NPY_USERDEF=256,  /* leave room for characters */
+      69             : 
+      70             :                     /* The number of types not including the new 1.6 types */
+      71             :                     NPY_NTYPES_ABI_COMPATIBLE=21
+      72             : };
+      73             : #if defined(_MSC_VER) && !defined(__clang__)
+      74             : #pragma deprecated(NPY_CHAR)
+      75             : #endif
+      76             : 
+      77             : /* basetype array priority */
+      78             : #define NPY_PRIORITY 0.0
+      79             : 
+      80             : /* default subtype priority */
+      81             : #define NPY_SUBTYPE_PRIORITY 1.0
+      82             : 
+      83             : /* default scalar priority */
+      84             : #define NPY_SCALAR_PRIORITY -1000000.0
+      85             : 
+      86             : /* How many floating point types are there (excluding half) */
+      87             : #define NPY_NUM_FLOATTYPE 3
+      88             : 
+      89             : /*
+      90             :  * These characters correspond to the array type and the struct
+      91             :  * module
+      92             :  */
+      93             : 
+      94             : enum NPY_TYPECHAR {
+      95             :         NPY_BOOLLTR = '?',
+      96             :         NPY_BYTELTR = 'b',
+      97             :         NPY_UBYTELTR = 'B',
+      98             :         NPY_SHORTLTR = 'h',
+      99             :         NPY_USHORTLTR = 'H',
+     100             :         NPY_INTLTR = 'i',
+     101             :         NPY_UINTLTR = 'I',
+     102             :         NPY_LONGLTR = 'l',
+     103             :         NPY_ULONGLTR = 'L',
+     104             :         NPY_LONGLONGLTR = 'q',
+     105             :         NPY_ULONGLONGLTR = 'Q',
+     106             :         NPY_HALFLTR = 'e',
+     107             :         NPY_FLOATLTR = 'f',
+     108             :         NPY_DOUBLELTR = 'd',
+     109             :         NPY_LONGDOUBLELTR = 'g',
+     110             :         NPY_CFLOATLTR = 'F',
+     111             :         NPY_CDOUBLELTR = 'D',
+     112             :         NPY_CLONGDOUBLELTR = 'G',
+     113             :         NPY_OBJECTLTR = 'O',
+     114             :         NPY_STRINGLTR = 'S',
+     115             :         NPY_STRINGLTR2 = 'a',
+     116             :         NPY_UNICODELTR = 'U',
+     117             :         NPY_VOIDLTR = 'V',
+     118             :         NPY_DATETIMELTR = 'M',
+     119             :         NPY_TIMEDELTALTR = 'm',
+     120             :         NPY_CHARLTR = 'c',
+     121             : 
+     122             :         /*
+     123             :          * No Descriptor, just a define -- this let's
+     124             :          * Python users specify an array of integers
+     125             :          * large enough to hold a pointer on the
+     126             :          * platform
+     127             :          */
+     128             :         NPY_INTPLTR = 'p',
+     129             :         NPY_UINTPLTR = 'P',
+     130             : 
+     131             :         /*
+     132             :          * These are for dtype 'kinds', not dtype 'typecodes'
+     133             :          * as the above are for.
+     134             :          */
+     135             :         NPY_GENBOOLLTR ='b',
+     136             :         NPY_SIGNEDLTR = 'i',
+     137             :         NPY_UNSIGNEDLTR = 'u',
+     138             :         NPY_FLOATINGLTR = 'f',
+     139             :         NPY_COMPLEXLTR = 'c'
+     140             : };
+     141             : 
+     142             : /*
+     143             :  * Changing this may break Numpy API compatibility
+     144             :  * due to changing offsets in PyArray_ArrFuncs, so be
+     145             :  * careful. Here we have reused the mergesort slot for
+     146             :  * any kind of stable sort, the actual implementation will
+     147             :  * depend on the data type.
+     148             :  */
+     149             : typedef enum {
+     150             :         NPY_QUICKSORT=0,
+     151             :         NPY_HEAPSORT=1,
+     152             :         NPY_MERGESORT=2,
+     153             :         NPY_STABLESORT=2,
+     154             : } NPY_SORTKIND;
+     155             : #define NPY_NSORTS (NPY_STABLESORT + 1)
+     156             : 
+     157             : 
+     158             : typedef enum {
+     159             :         NPY_INTROSELECT=0
+     160             : } NPY_SELECTKIND;
+     161             : #define NPY_NSELECTS (NPY_INTROSELECT + 1)
+     162             : 
+     163             : 
+     164             : typedef enum {
+     165             :         NPY_SEARCHLEFT=0,
+     166             :         NPY_SEARCHRIGHT=1
+     167             : } NPY_SEARCHSIDE;
+     168             : #define NPY_NSEARCHSIDES (NPY_SEARCHRIGHT + 1)
+     169             : 
+     170             : 
+     171             : typedef enum {
+     172             :         NPY_NOSCALAR=-1,
+     173             :         NPY_BOOL_SCALAR,
+     174             :         NPY_INTPOS_SCALAR,
+     175             :         NPY_INTNEG_SCALAR,
+     176             :         NPY_FLOAT_SCALAR,
+     177             :         NPY_COMPLEX_SCALAR,
+     178             :         NPY_OBJECT_SCALAR
+     179             : } NPY_SCALARKIND;
+     180             : #define NPY_NSCALARKINDS (NPY_OBJECT_SCALAR + 1)
+     181             : 
+     182             : /* For specifying array memory layout or iteration order */
+     183             : typedef enum {
+     184             :         /* Fortran order if inputs are all Fortran, C otherwise */
+     185             :         NPY_ANYORDER=-1,
+     186             :         /* C order */
+     187             :         NPY_CORDER=0,
+     188             :         /* Fortran order */
+     189             :         NPY_FORTRANORDER=1,
+     190             :         /* An order as close to the inputs as possible */
+     191             :         NPY_KEEPORDER=2
+     192             : } NPY_ORDER;
+     193             : 
+     194             : /* For specifying allowed casting in operations which support it */
+     195             : typedef enum {
+     196             :         _NPY_ERROR_OCCURRED_IN_CAST = -1,
+     197             :         /* Only allow identical types */
+     198             :         NPY_NO_CASTING=0,
+     199             :         /* Allow identical and byte swapped types */
+     200             :         NPY_EQUIV_CASTING=1,
+     201             :         /* Only allow safe casts */
+     202             :         NPY_SAFE_CASTING=2,
+     203             :         /* Allow safe casts or casts within the same kind */
+     204             :         NPY_SAME_KIND_CASTING=3,
+     205             :         /* Allow any casts */
+     206             :         NPY_UNSAFE_CASTING=4,
+     207             : } NPY_CASTING;
+     208             : 
+     209             : typedef enum {
+     210             :         NPY_CLIP=0,
+     211             :         NPY_WRAP=1,
+     212             :         NPY_RAISE=2
+     213             : } NPY_CLIPMODE;
+     214             : 
+     215             : typedef enum {
+     216             :         NPY_VALID=0,
+     217             :         NPY_SAME=1,
+     218             :         NPY_FULL=2
+     219             : } NPY_CORRELATEMODE;
+     220             : 
+     221             : /* The special not-a-time (NaT) value */
+     222             : #define NPY_DATETIME_NAT NPY_MIN_INT64
+     223             : 
+     224             : /*
+     225             :  * Upper bound on the length of a DATETIME ISO 8601 string
+     226             :  *   YEAR: 21 (64-bit year)
+     227             :  *   MONTH: 3
+     228             :  *   DAY: 3
+     229             :  *   HOURS: 3
+     230             :  *   MINUTES: 3
+     231             :  *   SECONDS: 3
+     232             :  *   ATTOSECONDS: 1 + 3*6
+     233             :  *   TIMEZONE: 5
+     234             :  *   NULL TERMINATOR: 1
+     235             :  */
+     236             : #define NPY_DATETIME_MAX_ISO8601_STRLEN (21 + 3*5 + 1 + 3*6 + 6 + 1)
+     237             : 
+     238             : /* The FR in the unit names stands for frequency */
+     239             : typedef enum {
+     240             :         /* Force signed enum type, must be -1 for code compatibility */
+     241             :         NPY_FR_ERROR = -1,      /* error or undetermined */
+     242             : 
+     243             :         /* Start of valid units */
+     244             :         NPY_FR_Y = 0,           /* Years */
+     245             :         NPY_FR_M = 1,           /* Months */
+     246             :         NPY_FR_W = 2,           /* Weeks */
+     247             :         /* Gap where 1.6 NPY_FR_B (value 3) was */
+     248             :         NPY_FR_D = 4,           /* Days */
+     249             :         NPY_FR_h = 5,           /* hours */
+     250             :         NPY_FR_m = 6,           /* minutes */
+     251             :         NPY_FR_s = 7,           /* seconds */
+     252             :         NPY_FR_ms = 8,          /* milliseconds */
+     253             :         NPY_FR_us = 9,          /* microseconds */
+     254             :         NPY_FR_ns = 10,         /* nanoseconds */
+     255             :         NPY_FR_ps = 11,         /* picoseconds */
+     256             :         NPY_FR_fs = 12,         /* femtoseconds */
+     257             :         NPY_FR_as = 13,         /* attoseconds */
+     258             :         NPY_FR_GENERIC = 14     /* unbound units, can convert to anything */
+     259             : } NPY_DATETIMEUNIT;
+     260             : 
+     261             : /*
+     262             :  * NOTE: With the NPY_FR_B gap for 1.6 ABI compatibility, NPY_DATETIME_NUMUNITS
+     263             :  * is technically one more than the actual number of units.
+     264             :  */
+     265             : #define NPY_DATETIME_NUMUNITS (NPY_FR_GENERIC + 1)
+     266             : #define NPY_DATETIME_DEFAULTUNIT NPY_FR_GENERIC
+     267             : 
+     268             : /*
+     269             :  * Business day conventions for mapping invalid business
+     270             :  * days to valid business days.
+     271             :  */
+     272             : typedef enum {
+     273             :     /* Go forward in time to the following business day. */
+     274             :     NPY_BUSDAY_FORWARD,
+     275             :     NPY_BUSDAY_FOLLOWING = NPY_BUSDAY_FORWARD,
+     276             :     /* Go backward in time to the preceding business day. */
+     277             :     NPY_BUSDAY_BACKWARD,
+     278             :     NPY_BUSDAY_PRECEDING = NPY_BUSDAY_BACKWARD,
+     279             :     /*
+     280             :      * Go forward in time to the following business day, unless it
+     281             :      * crosses a month boundary, in which case go backward
+     282             :      */
+     283             :     NPY_BUSDAY_MODIFIEDFOLLOWING,
+     284             :     /*
+     285             :      * Go backward in time to the preceding business day, unless it
+     286             :      * crosses a month boundary, in which case go forward.
+     287             :      */
+     288             :     NPY_BUSDAY_MODIFIEDPRECEDING,
+     289             :     /* Produce a NaT for non-business days. */
+     290             :     NPY_BUSDAY_NAT,
+     291             :     /* Raise an exception for non-business days. */
+     292             :     NPY_BUSDAY_RAISE
+     293             : } NPY_BUSDAY_ROLL;
+     294             : 
+     295             : /************************************************************
+     296             :  * NumPy Auxiliary Data for inner loops, sort functions, etc.
+     297             :  ************************************************************/
+     298             : 
+     299             : /*
+     300             :  * When creating an auxiliary data struct, this should always appear
+     301             :  * as the first member, like this:
+     302             :  *
+     303             :  * typedef struct {
+     304             :  *     NpyAuxData base;
+     305             :  *     double constant;
+     306             :  * } constant_multiplier_aux_data;
+     307             :  */
+     308             : typedef struct NpyAuxData_tag NpyAuxData;
+     309             : 
+     310             : /* Function pointers for freeing or cloning auxiliary data */
+     311             : typedef void (NpyAuxData_FreeFunc) (NpyAuxData *);
+     312             : typedef NpyAuxData *(NpyAuxData_CloneFunc) (NpyAuxData *);
+     313             : 
+     314             : struct NpyAuxData_tag {
+     315             :     NpyAuxData_FreeFunc *free;
+     316             :     NpyAuxData_CloneFunc *clone;
+     317             :     /* To allow for a bit of expansion without breaking the ABI */
+     318             :     void *reserved[2];
+     319             : };
+     320             : 
+     321             : /* Macros to use for freeing and cloning auxiliary data */
+     322             : #define NPY_AUXDATA_FREE(auxdata) \
+     323             :     do { \
+     324             :         if ((auxdata) != NULL) { \
+     325             :             (auxdata)->free(auxdata); \
+     326             :         } \
+     327             :     } while(0)
+     328             : #define NPY_AUXDATA_CLONE(auxdata) \
+     329             :     ((auxdata)->clone(auxdata))
+     330             : 
+     331             : #define NPY_ERR(str) fprintf(stderr, #str); fflush(stderr);
+     332             : #define NPY_ERR2(str) fprintf(stderr, str); fflush(stderr);
+     333             : 
+     334             : /*
+     335             : * Macros to define how array, and dimension/strides data is
+     336             : * allocated. These should be made private
+     337             : */
+     338             : 
+     339             : #define NPY_USE_PYMEM 1
+     340             : 
+     341             : 
+     342             : #if NPY_USE_PYMEM == 1
+     343             : /* use the Raw versions which are safe to call with the GIL released */
+     344             : #define PyArray_malloc PyMem_RawMalloc
+     345             : #define PyArray_free PyMem_RawFree
+     346             : #define PyArray_realloc PyMem_RawRealloc
+     347             : #else
+     348             : #define PyArray_malloc malloc
+     349             : #define PyArray_free free
+     350             : #define PyArray_realloc realloc
+     351             : #endif
+     352             : 
+     353             : /* Dimensions and strides */
+     354             : #define PyDimMem_NEW(size)                                         \
+     355             :     ((npy_intp *)PyArray_malloc(size*sizeof(npy_intp)))
+     356             : 
+     357             : #define PyDimMem_FREE(ptr) PyArray_free(ptr)
+     358             : 
+     359             : #define PyDimMem_RENEW(ptr,size)                                   \
+     360             :         ((npy_intp *)PyArray_realloc(ptr,size*sizeof(npy_intp)))
+     361             : 
+     362             : /* forward declaration */
+     363             : struct _PyArray_Descr;
+     364             : 
+     365             : /* These must deal with unaligned and swapped data if necessary */
+     366             : typedef PyObject * (PyArray_GetItemFunc) (void *, void *);
+     367             : typedef int (PyArray_SetItemFunc)(PyObject *, void *, void *);
+     368             : 
+     369             : typedef void (PyArray_CopySwapNFunc)(void *, npy_intp, void *, npy_intp,
+     370             :                                      npy_intp, int, void *);
+     371             : 
+     372             : typedef void (PyArray_CopySwapFunc)(void *, void *, int, void *);
+     373             : typedef npy_bool (PyArray_NonzeroFunc)(void *, void *);
+     374             : 
+     375             : 
+     376             : /*
+     377             :  * These assume aligned and notswapped data -- a buffer will be used
+     378             :  * before or contiguous data will be obtained
+     379             :  */
+     380             : 
+     381             : typedef int (PyArray_CompareFunc)(const void *, const void *, void *);
+     382             : typedef int (PyArray_ArgFunc)(void*, npy_intp, npy_intp*, void *);
+     383             : 
+     384             : typedef void (PyArray_DotFunc)(void *, npy_intp, void *, npy_intp, void *,
+     385             :                                npy_intp, void *);
+     386             : 
+     387             : typedef void (PyArray_VectorUnaryFunc)(void *, void *, npy_intp, void *,
+     388             :                                        void *);
+     389             : 
+     390             : /*
+     391             :  * XXX the ignore argument should be removed next time the API version
+     392             :  * is bumped. It used to be the separator.
+     393             :  */
+     394             : typedef int (PyArray_ScanFunc)(FILE *fp, void *dptr,
+     395             :                                char *ignore, struct _PyArray_Descr *);
+     396             : typedef int (PyArray_FromStrFunc)(char *s, void *dptr, char **endptr,
+     397             :                                   struct _PyArray_Descr *);
+     398             : 
+     399             : typedef int (PyArray_FillFunc)(void *, npy_intp, void *);
+     400             : 
+     401             : typedef int (PyArray_SortFunc)(void *, npy_intp, void *);
+     402             : typedef int (PyArray_ArgSortFunc)(void *, npy_intp *, npy_intp, void *);
+     403             : typedef int (PyArray_PartitionFunc)(void *, npy_intp, npy_intp,
+     404             :                                     npy_intp *, npy_intp *,
+     405             :                                     void *);
+     406             : typedef int (PyArray_ArgPartitionFunc)(void *, npy_intp *, npy_intp, npy_intp,
+     407             :                                        npy_intp *, npy_intp *,
+     408             :                                        void *);
+     409             : 
+     410             : typedef int (PyArray_FillWithScalarFunc)(void *, npy_intp, void *, void *);
+     411             : 
+     412             : typedef int (PyArray_ScalarKindFunc)(void *);
+     413             : 
+     414             : typedef void (PyArray_FastClipFunc)(void *in, npy_intp n_in, void *min,
+     415             :                                     void *max, void *out);
+     416             : typedef void (PyArray_FastPutmaskFunc)(void *in, void *mask, npy_intp n_in,
+     417             :                                        void *values, npy_intp nv);
+     418             : typedef int  (PyArray_FastTakeFunc)(void *dest, void *src, npy_intp *indarray,
+     419             :                                        npy_intp nindarray, npy_intp n_outer,
+     420             :                                        npy_intp m_middle, npy_intp nelem,
+     421             :                                        NPY_CLIPMODE clipmode);
+     422             : 
+     423             : typedef struct {
+     424             :         npy_intp *ptr;
+     425             :         int len;
+     426             : } PyArray_Dims;
+     427             : 
+     428             : typedef struct {
+     429             :         /*
+     430             :          * Functions to cast to most other standard types
+     431             :          * Can have some NULL entries. The types
+     432             :          * DATETIME, TIMEDELTA, and HALF go into the castdict
+     433             :          * even though they are built-in.
+     434             :          */
+     435             :         PyArray_VectorUnaryFunc *cast[NPY_NTYPES_ABI_COMPATIBLE];
+     436             : 
+     437             :         /* The next four functions *cannot* be NULL */
+     438             : 
+     439             :         /*
+     440             :          * Functions to get and set items with standard Python types
+     441             :          * -- not array scalars
+     442             :          */
+     443             :         PyArray_GetItemFunc *getitem;
+     444             :         PyArray_SetItemFunc *setitem;
+     445             : 
+     446             :         /*
+     447             :          * Copy and/or swap data.  Memory areas may not overlap
+     448             :          * Use memmove first if they might
+     449             :          */
+     450             :         PyArray_CopySwapNFunc *copyswapn;
+     451             :         PyArray_CopySwapFunc *copyswap;
+     452             : 
+     453             :         /*
+     454             :          * Function to compare items
+     455             :          * Can be NULL
+     456             :          */
+     457             :         PyArray_CompareFunc *compare;
+     458             : 
+     459             :         /*
+     460             :          * Function to select largest
+     461             :          * Can be NULL
+     462             :          */
+     463             :         PyArray_ArgFunc *argmax;
+     464             : 
+     465             :         /*
+     466             :          * Function to compute dot product
+     467             :          * Can be NULL
+     468             :          */
+     469             :         PyArray_DotFunc *dotfunc;
+     470             : 
+     471             :         /*
+     472             :          * Function to scan an ASCII file and
+     473             :          * place a single value plus possible separator
+     474             :          * Can be NULL
+     475             :          */
+     476             :         PyArray_ScanFunc *scanfunc;
+     477             : 
+     478             :         /*
+     479             :          * Function to read a single value from a string
+     480             :          * and adjust the pointer; Can be NULL
+     481             :          */
+     482             :         PyArray_FromStrFunc *fromstr;
+     483             : 
+     484             :         /*
+     485             :          * Function to determine if data is zero or not
+     486             :          * If NULL a default version is
+     487             :          * used at Registration time.
+     488             :          */
+     489             :         PyArray_NonzeroFunc *nonzero;
+     490             : 
+     491             :         /*
+     492             :          * Used for arange. Should return 0 on success
+     493             :          * and -1 on failure.
+     494             :          * Can be NULL.
+     495             :          */
+     496             :         PyArray_FillFunc *fill;
+     497             : 
+     498             :         /*
+     499             :          * Function to fill arrays with scalar values
+     500             :          * Can be NULL
+     501             :          */
+     502             :         PyArray_FillWithScalarFunc *fillwithscalar;
+     503             : 
+     504             :         /*
+     505             :          * Sorting functions
+     506             :          * Can be NULL
+     507             :          */
+     508             :         PyArray_SortFunc *sort[NPY_NSORTS];
+     509             :         PyArray_ArgSortFunc *argsort[NPY_NSORTS];
+     510             : 
+     511             :         /*
+     512             :          * Dictionary of additional casting functions
+     513             :          * PyArray_VectorUnaryFuncs
+     514             :          * which can be populated to support casting
+     515             :          * to other registered types. Can be NULL
+     516             :          */
+     517             :         PyObject *castdict;
+     518             : 
+     519             :         /*
+     520             :          * Functions useful for generalizing
+     521             :          * the casting rules.
+     522             :          * Can be NULL;
+     523             :          */
+     524             :         PyArray_ScalarKindFunc *scalarkind;
+     525             :         int **cancastscalarkindto;
+     526             :         int *cancastto;
+     527             : 
+     528             :         PyArray_FastClipFunc *fastclip;
+     529             :         PyArray_FastPutmaskFunc *fastputmask;
+     530             :         PyArray_FastTakeFunc *fasttake;
+     531             : 
+     532             :         /*
+     533             :          * Function to select smallest
+     534             :          * Can be NULL
+     535             :          */
+     536             :         PyArray_ArgFunc *argmin;
+     537             : 
+     538             : } PyArray_ArrFuncs;
+     539             : 
+     540             : /* The item must be reference counted when it is inserted or extracted. */
+     541             : #define NPY_ITEM_REFCOUNT   0x01
+     542             : /* Same as needing REFCOUNT */
+     543             : #define NPY_ITEM_HASOBJECT  0x01
+     544             : /* Convert to list for pickling */
+     545             : #define NPY_LIST_PICKLE     0x02
+     546             : /* The item is a POINTER  */
+     547             : #define NPY_ITEM_IS_POINTER 0x04
+     548             : /* memory needs to be initialized for this data-type */
+     549             : #define NPY_NEEDS_INIT      0x08
+     550             : /* operations need Python C-API so don't give-up thread. */
+     551             : #define NPY_NEEDS_PYAPI     0x10
+     552             : /* Use f.getitem when extracting elements of this data-type */
+     553             : #define NPY_USE_GETITEM     0x20
+     554             : /* Use f.setitem when setting creating 0-d array from this data-type.*/
+     555             : #define NPY_USE_SETITEM     0x40
+     556             : /* A sticky flag specifically for structured arrays */
+     557             : #define NPY_ALIGNED_STRUCT  0x80
+     558             : 
+     559             : /*
+     560             :  *These are inherited for global data-type if any data-types in the
+     561             :  * field have them
+     562             :  */
+     563             : #define NPY_FROM_FIELDS    (NPY_NEEDS_INIT | NPY_LIST_PICKLE | \
+     564             :                             NPY_ITEM_REFCOUNT | NPY_NEEDS_PYAPI)
+     565             : 
+     566             : #define NPY_OBJECT_DTYPE_FLAGS (NPY_LIST_PICKLE | NPY_USE_GETITEM | \
+     567             :                                 NPY_ITEM_IS_POINTER | NPY_ITEM_REFCOUNT | \
+     568             :                                 NPY_NEEDS_INIT | NPY_NEEDS_PYAPI)
+     569             : 
+     570             : #define PyDataType_FLAGCHK(dtype, flag) \
+     571             :         (((dtype)->flags & (flag)) == (flag))
+     572             : 
+     573             : #define PyDataType_REFCHK(dtype) \
+     574             :         PyDataType_FLAGCHK(dtype, NPY_ITEM_REFCOUNT)
+     575             : 
+     576             : typedef struct _PyArray_Descr {
+     577             :         PyObject_HEAD
+     578             :         /*
+     579             :          * the type object representing an
+     580             :          * instance of this type -- should not
+     581             :          * be two type_numbers with the same type
+     582             :          * object.
+     583             :          */
+     584             :         PyTypeObject *typeobj;
+     585             :         /* kind for this type */
+     586             :         char kind;
+     587             :         /* unique-character representing this type */
+     588             :         char type;
+     589             :         /*
+     590             :          * '>' (big), '<' (little), '|'
+     591             :          * (not-applicable), or '=' (native).
+     592             :          */
+     593             :         char byteorder;
+     594             :         /* flags describing data type */
+     595             :         char flags;
+     596             :         /* number representing this type */
+     597             :         int type_num;
+     598             :         /* element size (itemsize) for this type */
+     599             :         int elsize;
+     600             :         /* alignment needed for this type */
+     601             :         int alignment;
+     602             :         /*
+     603             :          * Non-NULL if this type is
+     604             :          * is an array (C-contiguous)
+     605             :          * of some other type
+     606             :          */
+     607             :         struct _arr_descr *subarray;
+     608             :         /*
+     609             :          * The fields dictionary for this type
+     610             :          * For statically defined descr this
+     611             :          * is always Py_None
+     612             :          */
+     613             :         PyObject *fields;
+     614             :         /*
+     615             :          * An ordered tuple of field names or NULL
+     616             :          * if no fields are defined
+     617             :          */
+     618             :         PyObject *names;
+     619             :         /*
+     620             :          * a table of functions specific for each
+     621             :          * basic data descriptor
+     622             :          */
+     623             :         PyArray_ArrFuncs *f;
+     624             :         /* Metadata about this dtype */
+     625             :         PyObject *metadata;
+     626             :         /*
+     627             :          * Metadata specific to the C implementation
+     628             :          * of the particular dtype. This was added
+     629             :          * for NumPy 1.7.0.
+     630             :          */
+     631             :         NpyAuxData *c_metadata;
+     632             :         /* Cached hash value (-1 if not yet computed).
+     633             :          * This was added for NumPy 2.0.0.
+     634             :          */
+     635             :         npy_hash_t hash;
+     636             : } PyArray_Descr;
+     637             : 
+     638             : typedef struct _arr_descr {
+     639             :         PyArray_Descr *base;
+     640             :         PyObject *shape;       /* a tuple */
+     641             : } PyArray_ArrayDescr;
+     642             : 
+     643             : /*
+     644             :  * Memory handler structure for array data.
+     645             :  */
+     646             : /* The declaration of free differs from PyMemAllocatorEx */
+     647             : typedef struct {
+     648             :     void *ctx;
+     649             :     void* (*malloc) (void *ctx, size_t size);
+     650             :     void* (*calloc) (void *ctx, size_t nelem, size_t elsize);
+     651             :     void* (*realloc) (void *ctx, void *ptr, size_t new_size);
+     652             :     void (*free) (void *ctx, void *ptr, size_t size);
+     653             :     /*
+     654             :      * This is the end of the version=1 struct. Only add new fields after
+     655             :      * this line
+     656             :      */
+     657             : } PyDataMemAllocator;
+     658             : 
+     659             : typedef struct {
+     660             :     char name[127];  /* multiple of 64 to keep the struct aligned */
+     661             :     uint8_t version; /* currently 1 */
+     662             :     PyDataMemAllocator allocator;
+     663             : } PyDataMem_Handler;
+     664             : 
+     665             : 
+     666             : /*
+     667             :  * The main array object structure.
+     668             :  *
+     669             :  * It has been recommended to use the inline functions defined below
+     670             :  * (PyArray_DATA and friends) to access fields here for a number of
+     671             :  * releases. Direct access to the members themselves is deprecated.
+     672             :  * To ensure that your code does not use deprecated access,
+     673             :  * #define NPY_NO_DEPRECATED_API NPY_1_7_API_VERSION
+     674             :  * (or NPY_1_8_API_VERSION or higher as required).
+     675             :  */
+     676             : /* This struct will be moved to a private header in a future release */
+     677             : typedef struct tagPyArrayObject_fields {
+     678             :     PyObject_HEAD
+     679             :     /* Pointer to the raw data buffer */
+     680             :     char *data;
+     681             :     /* The number of dimensions, also called 'ndim' */
+     682             :     int nd;
+     683             :     /* The size in each dimension, also called 'shape' */
+     684             :     npy_intp *dimensions;
+     685             :     /*
+     686             :      * Number of bytes to jump to get to the
+     687             :      * next element in each dimension
+     688             :      */
+     689             :     npy_intp *strides;
+     690             :     /*
+     691             :      * This object is decref'd upon
+     692             :      * deletion of array. Except in the
+     693             :      * case of WRITEBACKIFCOPY which has
+     694             :      * special handling.
+     695             :      *
+     696             :      * For views it points to the original
+     697             :      * array, collapsed so no chains of
+     698             :      * views occur.
+     699             :      *
+     700             :      * For creation from buffer object it
+     701             :      * points to an object that should be
+     702             :      * decref'd on deletion
+     703             :      *
+     704             :      * For WRITEBACKIFCOPY flag this is an
+     705             :      * array to-be-updated upon calling
+     706             :      * PyArray_ResolveWritebackIfCopy
+     707             :      */
+     708             :     PyObject *base;
+     709             :     /* Pointer to type structure */
+     710             :     PyArray_Descr *descr;
+     711             :     /* Flags describing array -- see below */
+     712             :     int flags;
+     713             :     /* For weak references */
+     714             :     PyObject *weakreflist;
+     715             : #if NPY_FEATURE_VERSION >= NPY_1_20_API_VERSION
+     716             :     void *_buffer_info;  /* private buffer info, tagged to allow warning */
+     717             : #endif
+     718             :     /*
+     719             :      * For malloc/calloc/realloc/free per object
+     720             :      */
+     721             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
+     722             :     PyObject *mem_handler;
+     723             : #endif
+     724             : } PyArrayObject_fields;
+     725             : 
+     726             : /*
+     727             :  * To hide the implementation details, we only expose
+     728             :  * the Python struct HEAD.
+     729             :  */
+     730             : #if !defined(NPY_NO_DEPRECATED_API) || \
+     731             :     (NPY_NO_DEPRECATED_API < NPY_1_7_API_VERSION)
+     732             : /*
+     733             :  * Can't put this in npy_deprecated_api.h like the others.
+     734             :  * PyArrayObject field access is deprecated as of NumPy 1.7.
+     735             :  */
+     736             : typedef PyArrayObject_fields PyArrayObject;
+     737             : #else
+     738             : typedef struct tagPyArrayObject {
+     739             :         PyObject_HEAD
+     740             : } PyArrayObject;
+     741             : #endif
+     742             : 
+     743             : /*
+     744             :  * Removed 2020-Nov-25, NumPy 1.20
+     745             :  * #define NPY_SIZEOF_PYARRAYOBJECT (sizeof(PyArrayObject_fields))
+     746             :  *
+     747             :  * The above macro was removed as it gave a false sense of a stable ABI
+     748             :  * with respect to the structures size.  If you require a runtime constant,
+     749             :  * you can use `PyArray_Type.tp_basicsize` instead.  Otherwise, please
+     750             :  * see the PyArrayObject documentation or ask the NumPy developers for
+     751             :  * information on how to correctly replace the macro in a way that is
+     752             :  * compatible with multiple NumPy versions.
+     753             :  */
+     754             : 
+     755             : 
+     756             : /* Array Flags Object */
+     757             : typedef struct PyArrayFlagsObject {
+     758             :         PyObject_HEAD
+     759             :         PyObject *arr;
+     760             :         int flags;
+     761             : } PyArrayFlagsObject;
+     762             : 
+     763             : /* Mirrors buffer object to ptr */
+     764             : 
+     765             : typedef struct {
+     766             :         PyObject_HEAD
+     767             :         PyObject *base;
+     768             :         void *ptr;
+     769             :         npy_intp len;
+     770             :         int flags;
+     771             : } PyArray_Chunk;
+     772             : 
+     773             : typedef struct {
+     774             :     NPY_DATETIMEUNIT base;
+     775             :     int num;
+     776             : } PyArray_DatetimeMetaData;
+     777             : 
+     778             : typedef struct {
+     779             :     NpyAuxData base;
+     780             :     PyArray_DatetimeMetaData meta;
+     781             : } PyArray_DatetimeDTypeMetaData;
+     782             : 
+     783             : /*
+     784             :  * This structure contains an exploded view of a date-time value.
+     785             :  * NaT is represented by year == NPY_DATETIME_NAT.
+     786             :  */
+     787             : typedef struct {
+     788             :         npy_int64 year;
+     789             :         npy_int32 month, day, hour, min, sec, us, ps, as;
+     790             : } npy_datetimestruct;
+     791             : 
+     792             : /* This is not used internally. */
+     793             : typedef struct {
+     794             :         npy_int64 day;
+     795             :         npy_int32 sec, us, ps, as;
+     796             : } npy_timedeltastruct;
+     797             : 
+     798             : typedef int (PyArray_FinalizeFunc)(PyArrayObject *, PyObject *);
+     799             : 
+     800             : /*
+     801             :  * Means c-style contiguous (last index varies the fastest). The data
+     802             :  * elements right after each other.
+     803             :  *
+     804             :  * This flag may be requested in constructor functions.
+     805             :  * This flag may be tested for in PyArray_FLAGS(arr).
+     806             :  */
+     807             : #define NPY_ARRAY_C_CONTIGUOUS    0x0001
+     808             : 
+     809             : /*
+     810             :  * Set if array is a contiguous Fortran array: the first index varies
+     811             :  * the fastest in memory (strides array is reverse of C-contiguous
+     812             :  * array)
+     813             :  *
+     814             :  * This flag may be requested in constructor functions.
+     815             :  * This flag may be tested for in PyArray_FLAGS(arr).
+     816             :  */
+     817             : #define NPY_ARRAY_F_CONTIGUOUS    0x0002
+     818             : 
+     819             : /*
+     820             :  * Note: all 0-d arrays are C_CONTIGUOUS and F_CONTIGUOUS. If a
+     821             :  * 1-d array is C_CONTIGUOUS it is also F_CONTIGUOUS. Arrays with
+     822             :  * more then one dimension can be C_CONTIGUOUS and F_CONTIGUOUS
+     823             :  * at the same time if they have either zero or one element.
+     824             :  * A higher dimensional array always has the same contiguity flags as
+     825             :  * `array.squeeze()`; dimensions with `array.shape[dimension] == 1` are
+     826             :  * effectively ignored when checking for contiguity.
+     827             :  */
+     828             : 
+     829             : /*
+     830             :  * If set, the array owns the data: it will be free'd when the array
+     831             :  * is deleted.
+     832             :  *
+     833             :  * This flag may be tested for in PyArray_FLAGS(arr).
+     834             :  */
+     835             : #define NPY_ARRAY_OWNDATA         0x0004
+     836             : 
+     837             : /*
+     838             :  * An array never has the next four set; they're only used as parameter
+     839             :  * flags to the various FromAny functions
+     840             :  *
+     841             :  * This flag may be requested in constructor functions.
+     842             :  */
+     843             : 
+     844             : /* Cause a cast to occur regardless of whether or not it is safe. */
+     845             : #define NPY_ARRAY_FORCECAST       0x0010
+     846             : 
+     847             : /*
+     848             :  * Always copy the array. Returned arrays are always CONTIGUOUS,
+     849             :  * ALIGNED, and WRITEABLE. See also: NPY_ARRAY_ENSURENOCOPY = 0x4000.
+     850             :  *
+     851             :  * This flag may be requested in constructor functions.
+     852             :  */
+     853             : #define NPY_ARRAY_ENSURECOPY      0x0020
+     854             : 
+     855             : /*
+     856             :  * Make sure the returned array is a base-class ndarray
+     857             :  *
+     858             :  * This flag may be requested in constructor functions.
+     859             :  */
+     860             : #define NPY_ARRAY_ENSUREARRAY     0x0040
+     861             : 
+     862             : /*
+     863             :  * Make sure that the strides are in units of the element size Needed
+     864             :  * for some operations with record-arrays.
+     865             :  *
+     866             :  * This flag may be requested in constructor functions.
+     867             :  */
+     868             : #define NPY_ARRAY_ELEMENTSTRIDES  0x0080
+     869             : 
+     870             : /*
+     871             :  * Array data is aligned on the appropriate memory address for the type
+     872             :  * stored according to how the compiler would align things (e.g., an
+     873             :  * array of integers (4 bytes each) starts on a memory address that's
+     874             :  * a multiple of 4)
+     875             :  *
+     876             :  * This flag may be requested in constructor functions.
+     877             :  * This flag may be tested for in PyArray_FLAGS(arr).
+     878             :  */
+     879             : #define NPY_ARRAY_ALIGNED         0x0100
+     880             : 
+     881             : /*
+     882             :  * Array data has the native endianness
+     883             :  *
+     884             :  * This flag may be requested in constructor functions.
+     885             :  */
+     886             : #define NPY_ARRAY_NOTSWAPPED      0x0200
+     887             : 
+     888             : /*
+     889             :  * Array data is writeable
+     890             :  *
+     891             :  * This flag may be requested in constructor functions.
+     892             :  * This flag may be tested for in PyArray_FLAGS(arr).
+     893             :  */
+     894             : #define NPY_ARRAY_WRITEABLE       0x0400
+     895             : 
+     896             : /*
+     897             :  * If this flag is set, then base contains a pointer to an array of
+     898             :  * the same size that should be updated with the current contents of
+     899             :  * this array when PyArray_ResolveWritebackIfCopy is called.
+     900             :  *
+     901             :  * This flag may be requested in constructor functions.
+     902             :  * This flag may be tested for in PyArray_FLAGS(arr).
+     903             :  */
+     904             : #define NPY_ARRAY_WRITEBACKIFCOPY 0x2000
+     905             : 
+     906             : /*
+     907             :  * No copy may be made while converting from an object/array (result is a view)
+     908             :  *
+     909             :  * This flag may be requested in constructor functions.
+     910             :  */
+     911             : #define NPY_ARRAY_ENSURENOCOPY 0x4000
+     912             : 
+     913             : /*
+     914             :  * NOTE: there are also internal flags defined in multiarray/arrayobject.h,
+     915             :  * which start at bit 31 and work down.
+     916             :  */
+     917             : 
+     918             : #define NPY_ARRAY_BEHAVED      (NPY_ARRAY_ALIGNED | \
+     919             :                                 NPY_ARRAY_WRITEABLE)
+     920             : #define NPY_ARRAY_BEHAVED_NS   (NPY_ARRAY_ALIGNED | \
+     921             :                                 NPY_ARRAY_WRITEABLE | \
+     922             :                                 NPY_ARRAY_NOTSWAPPED)
+     923             : #define NPY_ARRAY_CARRAY       (NPY_ARRAY_C_CONTIGUOUS | \
+     924             :                                 NPY_ARRAY_BEHAVED)
+     925             : #define NPY_ARRAY_CARRAY_RO    (NPY_ARRAY_C_CONTIGUOUS | \
+     926             :                                 NPY_ARRAY_ALIGNED)
+     927             : #define NPY_ARRAY_FARRAY       (NPY_ARRAY_F_CONTIGUOUS | \
+     928             :                                 NPY_ARRAY_BEHAVED)
+     929             : #define NPY_ARRAY_FARRAY_RO    (NPY_ARRAY_F_CONTIGUOUS | \
+     930             :                                 NPY_ARRAY_ALIGNED)
+     931             : #define NPY_ARRAY_DEFAULT      (NPY_ARRAY_CARRAY)
+     932             : #define NPY_ARRAY_IN_ARRAY     (NPY_ARRAY_CARRAY_RO)
+     933             : #define NPY_ARRAY_OUT_ARRAY    (NPY_ARRAY_CARRAY)
+     934             : #define NPY_ARRAY_INOUT_ARRAY  (NPY_ARRAY_CARRAY)
+     935             : #define NPY_ARRAY_INOUT_ARRAY2 (NPY_ARRAY_CARRAY | \
+     936             :                                 NPY_ARRAY_WRITEBACKIFCOPY)
+     937             : #define NPY_ARRAY_IN_FARRAY    (NPY_ARRAY_FARRAY_RO)
+     938             : #define NPY_ARRAY_OUT_FARRAY   (NPY_ARRAY_FARRAY)
+     939             : #define NPY_ARRAY_INOUT_FARRAY (NPY_ARRAY_FARRAY)
+     940             : #define NPY_ARRAY_INOUT_FARRAY2 (NPY_ARRAY_FARRAY | \
+     941             :                                 NPY_ARRAY_WRITEBACKIFCOPY)
+     942             : 
+     943             : #define NPY_ARRAY_UPDATE_ALL   (NPY_ARRAY_C_CONTIGUOUS | \
+     944             :                                 NPY_ARRAY_F_CONTIGUOUS | \
+     945             :                                 NPY_ARRAY_ALIGNED)
+     946             : 
+     947             : /* This flag is for the array interface, not PyArrayObject */
+     948             : #define NPY_ARR_HAS_DESCR  0x0800
+     949             : 
+     950             : 
+     951             : 
+     952             : 
+     953             : /*
+     954             :  * Size of internal buffers used for alignment Make BUFSIZE a multiple
+     955             :  * of sizeof(npy_cdouble) -- usually 16 so that ufunc buffers are aligned
+     956             :  */
+     957             : #define NPY_MIN_BUFSIZE ((int)sizeof(npy_cdouble))
+     958             : #define NPY_MAX_BUFSIZE (((int)sizeof(npy_cdouble))*1000000)
+     959             : #define NPY_BUFSIZE 8192
+     960             : /* buffer stress test size: */
+     961             : /*#define NPY_BUFSIZE 17*/
+     962             : 
+     963             : #define PyArray_MAX(a,b) (((a)>(b))?(a):(b))
+     964             : #define PyArray_MIN(a,b) (((a)<(b))?(a):(b))
+     965             : #define PyArray_CLT(p,q) ((((p).real==(q).real) ? ((p).imag < (q).imag) : \
+     966             :                                ((p).real < (q).real)))
+     967             : #define PyArray_CGT(p,q) ((((p).real==(q).real) ? ((p).imag > (q).imag) : \
+     968             :                                ((p).real > (q).real)))
+     969             : #define PyArray_CLE(p,q) ((((p).real==(q).real) ? ((p).imag <= (q).imag) : \
+     970             :                                ((p).real <= (q).real)))
+     971             : #define PyArray_CGE(p,q) ((((p).real==(q).real) ? ((p).imag >= (q).imag) : \
+     972             :                                ((p).real >= (q).real)))
+     973             : #define PyArray_CEQ(p,q) (((p).real==(q).real) && ((p).imag == (q).imag))
+     974             : #define PyArray_CNE(p,q) (((p).real!=(q).real) || ((p).imag != (q).imag))
+     975             : 
+     976             : /*
+     977             :  * C API: consists of Macros and functions.  The MACROS are defined
+     978             :  * here.
+     979             :  */
+     980             : 
+     981             : 
+     982             : #define PyArray_ISCONTIGUOUS(m) PyArray_CHKFLAGS((m), NPY_ARRAY_C_CONTIGUOUS)
+     983             : #define PyArray_ISWRITEABLE(m) PyArray_CHKFLAGS((m), NPY_ARRAY_WRITEABLE)
+     984             : #define PyArray_ISALIGNED(m) PyArray_CHKFLAGS((m), NPY_ARRAY_ALIGNED)
+     985             : 
+     986             : #define PyArray_IS_C_CONTIGUOUS(m) PyArray_CHKFLAGS((m), NPY_ARRAY_C_CONTIGUOUS)
+     987             : #define PyArray_IS_F_CONTIGUOUS(m) PyArray_CHKFLAGS((m), NPY_ARRAY_F_CONTIGUOUS)
+     988             : 
+     989             : /* the variable is used in some places, so always define it */
+     990             : #define NPY_BEGIN_THREADS_DEF PyThreadState *_save=NULL;
+     991             : #if NPY_ALLOW_THREADS
+     992             : #define NPY_BEGIN_ALLOW_THREADS Py_BEGIN_ALLOW_THREADS
+     993             : #define NPY_END_ALLOW_THREADS Py_END_ALLOW_THREADS
+     994             : #define NPY_BEGIN_THREADS do {_save = PyEval_SaveThread();} while (0);
+     995             : #define NPY_END_THREADS   do { if (_save) \
+     996             :                 { PyEval_RestoreThread(_save); _save = NULL;} } while (0);
+     997             : #define NPY_BEGIN_THREADS_THRESHOLDED(loop_size) do { if ((loop_size) > 500) \
+     998             :                 { _save = PyEval_SaveThread();} } while (0);
+     999             : 
+    1000             : #define NPY_BEGIN_THREADS_DESCR(dtype) \
+    1001             :         do {if (!(PyDataType_FLAGCHK((dtype), NPY_NEEDS_PYAPI))) \
+    1002             :                 NPY_BEGIN_THREADS;} while (0);
+    1003             : 
+    1004             : #define NPY_END_THREADS_DESCR(dtype) \
+    1005             :         do {if (!(PyDataType_FLAGCHK((dtype), NPY_NEEDS_PYAPI))) \
+    1006             :                 NPY_END_THREADS; } while (0);
+    1007             : 
+    1008             : #define NPY_ALLOW_C_API_DEF  PyGILState_STATE __save__;
+    1009             : #define NPY_ALLOW_C_API      do {__save__ = PyGILState_Ensure();} while (0);
+    1010             : #define NPY_DISABLE_C_API    do {PyGILState_Release(__save__);} while (0);
+    1011             : #else
+    1012             : #define NPY_BEGIN_ALLOW_THREADS
+    1013             : #define NPY_END_ALLOW_THREADS
+    1014             : #define NPY_BEGIN_THREADS
+    1015             : #define NPY_END_THREADS
+    1016             : #define NPY_BEGIN_THREADS_THRESHOLDED(loop_size)
+    1017             : #define NPY_BEGIN_THREADS_DESCR(dtype)
+    1018             : #define NPY_END_THREADS_DESCR(dtype)
+    1019             : #define NPY_ALLOW_C_API_DEF
+    1020             : #define NPY_ALLOW_C_API
+    1021             : #define NPY_DISABLE_C_API
+    1022             : #endif
+    1023             : 
+    1024             : /**********************************
+    1025             :  * The nditer object, added in 1.6
+    1026             :  **********************************/
+    1027             : 
+    1028             : /* The actual structure of the iterator is an internal detail */
+    1029             : typedef struct NpyIter_InternalOnly NpyIter;
+    1030             : 
+    1031             : /* Iterator function pointers that may be specialized */
+    1032             : typedef int (NpyIter_IterNextFunc)(NpyIter *iter);
+    1033             : typedef void (NpyIter_GetMultiIndexFunc)(NpyIter *iter,
+    1034             :                                       npy_intp *outcoords);
+    1035             : 
+    1036             : /*** Global flags that may be passed to the iterator constructors ***/
+    1037             : 
+    1038             : /* Track an index representing C order */
+    1039             : #define NPY_ITER_C_INDEX                    0x00000001
+    1040             : /* Track an index representing Fortran order */
+    1041             : #define NPY_ITER_F_INDEX                    0x00000002
+    1042             : /* Track a multi-index */
+    1043             : #define NPY_ITER_MULTI_INDEX                0x00000004
+    1044             : /* User code external to the iterator does the 1-dimensional innermost loop */
+    1045             : #define NPY_ITER_EXTERNAL_LOOP              0x00000008
+    1046             : /* Convert all the operands to a common data type */
+    1047             : #define NPY_ITER_COMMON_DTYPE               0x00000010
+    1048             : /* Operands may hold references, requiring API access during iteration */
+    1049             : #define NPY_ITER_REFS_OK                    0x00000020
+    1050             : /* Zero-sized operands should be permitted, iteration checks IterSize for 0 */
+    1051             : #define NPY_ITER_ZEROSIZE_OK                0x00000040
+    1052             : /* Permits reductions (size-0 stride with dimension size > 1) */
+    1053             : #define NPY_ITER_REDUCE_OK                  0x00000080
+    1054             : /* Enables sub-range iteration */
+    1055             : #define NPY_ITER_RANGED                     0x00000100
+    1056             : /* Enables buffering */
+    1057             : #define NPY_ITER_BUFFERED                   0x00000200
+    1058             : /* When buffering is enabled, grows the inner loop if possible */
+    1059             : #define NPY_ITER_GROWINNER                  0x00000400
+    1060             : /* Delay allocation of buffers until first Reset* call */
+    1061             : #define NPY_ITER_DELAY_BUFALLOC             0x00000800
+    1062             : /* When NPY_KEEPORDER is specified, disable reversing negative-stride axes */
+    1063             : #define NPY_ITER_DONT_NEGATE_STRIDES        0x00001000
+    1064             : /*
+    1065             :  * If output operands overlap with other operands (based on heuristics that
+    1066             :  * has false positives but no false negatives), make temporary copies to
+    1067             :  * eliminate overlap.
+    1068             :  */
+    1069             : #define NPY_ITER_COPY_IF_OVERLAP            0x00002000
+    1070             : 
+    1071             : /*** Per-operand flags that may be passed to the iterator constructors ***/
+    1072             : 
+    1073             : /* The operand will be read from and written to */
+    1074             : #define NPY_ITER_READWRITE                  0x00010000
+    1075             : /* The operand will only be read from */
+    1076             : #define NPY_ITER_READONLY                   0x00020000
+    1077             : /* The operand will only be written to */
+    1078             : #define NPY_ITER_WRITEONLY                  0x00040000
+    1079             : /* The operand's data must be in native byte order */
+    1080             : #define NPY_ITER_NBO                        0x00080000
+    1081             : /* The operand's data must be aligned */
+    1082             : #define NPY_ITER_ALIGNED                    0x00100000
+    1083             : /* The operand's data must be contiguous (within the inner loop) */
+    1084             : #define NPY_ITER_CONTIG                     0x00200000
+    1085             : /* The operand may be copied to satisfy requirements */
+    1086             : #define NPY_ITER_COPY                       0x00400000
+    1087             : /* The operand may be copied with WRITEBACKIFCOPY to satisfy requirements */
+    1088             : #define NPY_ITER_UPDATEIFCOPY               0x00800000
+    1089             : /* Allocate the operand if it is NULL */
+    1090             : #define NPY_ITER_ALLOCATE                   0x01000000
+    1091             : /* If an operand is allocated, don't use any subtype */
+    1092             : #define NPY_ITER_NO_SUBTYPE                 0x02000000
+    1093             : /* This is a virtual array slot, operand is NULL but temporary data is there */
+    1094             : #define NPY_ITER_VIRTUAL                    0x04000000
+    1095             : /* Require that the dimension match the iterator dimensions exactly */
+    1096             : #define NPY_ITER_NO_BROADCAST               0x08000000
+    1097             : /* A mask is being used on this array, affects buffer -> array copy */
+    1098             : #define NPY_ITER_WRITEMASKED                0x10000000
+    1099             : /* This array is the mask for all WRITEMASKED operands */
+    1100             : #define NPY_ITER_ARRAYMASK                  0x20000000
+    1101             : /* Assume iterator order data access for COPY_IF_OVERLAP */
+    1102             : #define NPY_ITER_OVERLAP_ASSUME_ELEMENTWISE 0x40000000
+    1103             : 
+    1104             : #define NPY_ITER_GLOBAL_FLAGS               0x0000ffff
+    1105             : #define NPY_ITER_PER_OP_FLAGS               0xffff0000
+    1106             : 
+    1107             : 
+    1108             : /*****************************
+    1109             :  * Basic iterator object
+    1110             :  *****************************/
+    1111             : 
+    1112             : /* FWD declaration */
+    1113             : typedef struct PyArrayIterObject_tag PyArrayIterObject;
+    1114             : 
+    1115             : /*
+    1116             :  * type of the function which translates a set of coordinates to a
+    1117             :  * pointer to the data
+    1118             :  */
+    1119             : typedef char* (*npy_iter_get_dataptr_t)(
+    1120             :         PyArrayIterObject* iter, const npy_intp*);
+    1121             : 
+    1122             : struct PyArrayIterObject_tag {
+    1123             :         PyObject_HEAD
+    1124             :         int               nd_m1;            /* number of dimensions - 1 */
+    1125             :         npy_intp          index, size;
+    1126             :         npy_intp          coordinates[NPY_MAXDIMS];/* N-dimensional loop */
+    1127             :         npy_intp          dims_m1[NPY_MAXDIMS];    /* ao->dimensions - 1 */
+    1128             :         npy_intp          strides[NPY_MAXDIMS];    /* ao->strides or fake */
+    1129             :         npy_intp          backstrides[NPY_MAXDIMS];/* how far to jump back */
+    1130             :         npy_intp          factors[NPY_MAXDIMS];     /* shape factors */
+    1131             :         PyArrayObject     *ao;
+    1132             :         char              *dataptr;        /* pointer to current item*/
+    1133             :         npy_bool          contiguous;
+    1134             : 
+    1135             :         npy_intp          bounds[NPY_MAXDIMS][2];
+    1136             :         npy_intp          limits[NPY_MAXDIMS][2];
+    1137             :         npy_intp          limits_sizes[NPY_MAXDIMS];
+    1138             :         npy_iter_get_dataptr_t translate;
+    1139             : } ;
+    1140             : 
+    1141             : 
+    1142             : /* Iterator API */
+    1143             : #define PyArrayIter_Check(op) PyObject_TypeCheck((op), &PyArrayIter_Type)
+    1144             : 
+    1145             : #define _PyAIT(it) ((PyArrayIterObject *)(it))
+    1146             : #define PyArray_ITER_RESET(it) do { \
+    1147             :         _PyAIT(it)->index = 0; \
+    1148             :         _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao); \
+    1149             :         memset(_PyAIT(it)->coordinates, 0, \
+    1150             :                (_PyAIT(it)->nd_m1+1)*sizeof(npy_intp)); \
+    1151             : } while (0)
+    1152             : 
+    1153             : #define _PyArray_ITER_NEXT1(it) do { \
+    1154             :         (it)->dataptr += _PyAIT(it)->strides[0]; \
+    1155             :         (it)->coordinates[0]++; \
+    1156             : } while (0)
+    1157             : 
+    1158             : #define _PyArray_ITER_NEXT2(it) do { \
+    1159             :         if ((it)->coordinates[1] < (it)->dims_m1[1]) { \
+    1160             :                 (it)->coordinates[1]++; \
+    1161             :                 (it)->dataptr += (it)->strides[1]; \
+    1162             :         } \
+    1163             :         else { \
+    1164             :                 (it)->coordinates[1] = 0; \
+    1165             :                 (it)->coordinates[0]++; \
+    1166             :                 (it)->dataptr += (it)->strides[0] - \
+    1167             :                         (it)->backstrides[1]; \
+    1168             :         } \
+    1169             : } while (0)
+    1170             : 
+    1171             : #define PyArray_ITER_NEXT(it) do { \
+    1172             :         _PyAIT(it)->index++; \
+    1173             :         if (_PyAIT(it)->nd_m1 == 0) { \
+    1174             :                 _PyArray_ITER_NEXT1(_PyAIT(it)); \
+    1175             :         } \
+    1176             :         else if (_PyAIT(it)->contiguous) \
+    1177             :                 _PyAIT(it)->dataptr += PyArray_DESCR(_PyAIT(it)->ao)->elsize; \
+    1178             :         else if (_PyAIT(it)->nd_m1 == 1) { \
+    1179             :                 _PyArray_ITER_NEXT2(_PyAIT(it)); \
+    1180             :         } \
+    1181             :         else { \
+    1182             :                 int __npy_i; \
+    1183             :                 for (__npy_i=_PyAIT(it)->nd_m1; __npy_i >= 0; __npy_i--) { \
+    1184             :                         if (_PyAIT(it)->coordinates[__npy_i] < \
+    1185             :                             _PyAIT(it)->dims_m1[__npy_i]) { \
+    1186             :                                 _PyAIT(it)->coordinates[__npy_i]++; \
+    1187             :                                 _PyAIT(it)->dataptr += \
+    1188             :                                         _PyAIT(it)->strides[__npy_i]; \
+    1189             :                                 break; \
+    1190             :                         } \
+    1191             :                         else { \
+    1192             :                                 _PyAIT(it)->coordinates[__npy_i] = 0; \
+    1193             :                                 _PyAIT(it)->dataptr -= \
+    1194             :                                         _PyAIT(it)->backstrides[__npy_i]; \
+    1195             :                         } \
+    1196             :                 } \
+    1197             :         } \
+    1198             : } while (0)
+    1199             : 
+    1200             : #define PyArray_ITER_GOTO(it, destination) do { \
+    1201             :         int __npy_i; \
+    1202             :         _PyAIT(it)->index = 0; \
+    1203             :         _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao); \
+    1204             :         for (__npy_i = _PyAIT(it)->nd_m1; __npy_i>=0; __npy_i--) { \
+    1205             :                 if (destination[__npy_i] < 0) { \
+    1206             :                         destination[__npy_i] += \
+    1207             :                                 _PyAIT(it)->dims_m1[__npy_i]+1; \
+    1208             :                 } \
+    1209             :                 _PyAIT(it)->dataptr += destination[__npy_i] * \
+    1210             :                         _PyAIT(it)->strides[__npy_i]; \
+    1211             :                 _PyAIT(it)->coordinates[__npy_i] = \
+    1212             :                         destination[__npy_i]; \
+    1213             :                 _PyAIT(it)->index += destination[__npy_i] * \
+    1214             :                         ( __npy_i==_PyAIT(it)->nd_m1 ? 1 : \
+    1215             :                           _PyAIT(it)->dims_m1[__npy_i+1]+1) ; \
+    1216             :         } \
+    1217             : } while (0)
+    1218             : 
+    1219             : #define PyArray_ITER_GOTO1D(it, ind) do { \
+    1220             :         int __npy_i; \
+    1221             :         npy_intp __npy_ind = (npy_intp)(ind); \
+    1222             :         if (__npy_ind < 0) __npy_ind += _PyAIT(it)->size; \
+    1223             :         _PyAIT(it)->index = __npy_ind; \
+    1224             :         if (_PyAIT(it)->nd_m1 == 0) { \
+    1225             :                 _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao) + \
+    1226             :                         __npy_ind * _PyAIT(it)->strides[0]; \
+    1227             :         } \
+    1228             :         else if (_PyAIT(it)->contiguous) \
+    1229             :                 _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao) + \
+    1230             :                         __npy_ind * PyArray_DESCR(_PyAIT(it)->ao)->elsize; \
+    1231             :         else { \
+    1232             :                 _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao); \
+    1233             :                 for (__npy_i = 0; __npy_i<=_PyAIT(it)->nd_m1; \
+    1234             :                      __npy_i++) { \
+    1235             :                         _PyAIT(it)->coordinates[__npy_i] = \
+    1236             :                                 (__npy_ind / _PyAIT(it)->factors[__npy_i]); \
+    1237             :                         _PyAIT(it)->dataptr += \
+    1238             :                                 (__npy_ind / _PyAIT(it)->factors[__npy_i]) \
+    1239             :                                 * _PyAIT(it)->strides[__npy_i]; \
+    1240             :                         __npy_ind %= _PyAIT(it)->factors[__npy_i]; \
+    1241             :                 } \
+    1242             :         } \
+    1243             : } while (0)
+    1244             : 
+    1245             : #define PyArray_ITER_DATA(it) ((void *)(_PyAIT(it)->dataptr))
+    1246             : 
+    1247             : #define PyArray_ITER_NOTDONE(it) (_PyAIT(it)->index < _PyAIT(it)->size)
+    1248             : 
+    1249             : 
+    1250             : /*
+    1251             :  * Any object passed to PyArray_Broadcast must be binary compatible
+    1252             :  * with this structure.
+    1253             :  */
+    1254             : 
+    1255             : typedef struct {
+    1256             :         PyObject_HEAD
+    1257             :         int                  numiter;                 /* number of iters */
+    1258             :         npy_intp             size;                    /* broadcasted size */
+    1259             :         npy_intp             index;                   /* current index */
+    1260             :         int                  nd;                      /* number of dims */
+    1261             :         npy_intp             dimensions[NPY_MAXDIMS]; /* dimensions */
+    1262             :         PyArrayIterObject    *iters[NPY_MAXARGS];     /* iterators */
+    1263             : } PyArrayMultiIterObject;
+    1264             : 
+    1265             : #define _PyMIT(m) ((PyArrayMultiIterObject *)(m))
+    1266             : #define PyArray_MultiIter_RESET(multi) do {                                   \
+    1267             :         int __npy_mi;                                                         \
+    1268             :         _PyMIT(multi)->index = 0;                                             \
+    1269             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter;  __npy_mi++) {    \
+    1270             :                 PyArray_ITER_RESET(_PyMIT(multi)->iters[__npy_mi]);           \
+    1271             :         }                                                                     \
+    1272             : } while (0)
+    1273             : 
+    1274             : #define PyArray_MultiIter_NEXT(multi) do {                                    \
+    1275             :         int __npy_mi;                                                         \
+    1276             :         _PyMIT(multi)->index++;                                               \
+    1277             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter;   __npy_mi++) {   \
+    1278             :                 PyArray_ITER_NEXT(_PyMIT(multi)->iters[__npy_mi]);            \
+    1279             :         }                                                                     \
+    1280             : } while (0)
+    1281             : 
+    1282             : #define PyArray_MultiIter_GOTO(multi, dest) do {                            \
+    1283             :         int __npy_mi;                                                       \
+    1284             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter; __npy_mi++) {   \
+    1285             :                 PyArray_ITER_GOTO(_PyMIT(multi)->iters[__npy_mi], dest);    \
+    1286             :         }                                                                   \
+    1287             :         _PyMIT(multi)->index = _PyMIT(multi)->iters[0]->index;              \
+    1288             : } while (0)
+    1289             : 
+    1290             : #define PyArray_MultiIter_GOTO1D(multi, ind) do {                          \
+    1291             :         int __npy_mi;                                                      \
+    1292             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter; __npy_mi++) {  \
+    1293             :                 PyArray_ITER_GOTO1D(_PyMIT(multi)->iters[__npy_mi], ind);  \
+    1294             :         }                                                                  \
+    1295             :         _PyMIT(multi)->index = _PyMIT(multi)->iters[0]->index;             \
+    1296             : } while (0)
+    1297             : 
+    1298             : #define PyArray_MultiIter_DATA(multi, i)                \
+    1299             :         ((void *)(_PyMIT(multi)->iters[i]->dataptr))
+    1300             : 
+    1301             : #define PyArray_MultiIter_NEXTi(multi, i)               \
+    1302             :         PyArray_ITER_NEXT(_PyMIT(multi)->iters[i])
+    1303             : 
+    1304             : #define PyArray_MultiIter_NOTDONE(multi)                \
+    1305             :         (_PyMIT(multi)->index < _PyMIT(multi)->size)
+    1306             : 
+    1307             : /*
+    1308             :  * Store the information needed for fancy-indexing over an array. The
+    1309             :  * fields are slightly unordered to keep consec, dataptr and subspace
+    1310             :  * where they were originally.
+    1311             :  */
+    1312             : typedef struct {
+    1313             :         PyObject_HEAD
+    1314             :         /*
+    1315             :          * Multi-iterator portion --- needs to be present in this
+    1316             :          * order to work with PyArray_Broadcast
+    1317             :          */
+    1318             : 
+    1319             :         int                   numiter;                 /* number of index-array
+    1320             :                                                           iterators */
+    1321             :         npy_intp              size;                    /* size of broadcasted
+    1322             :                                                           result */
+    1323             :         npy_intp              index;                   /* current index */
+    1324             :         int                   nd;                      /* number of dims */
+    1325             :         npy_intp              dimensions[NPY_MAXDIMS]; /* dimensions */
+    1326             :         NpyIter               *outer;                  /* index objects
+    1327             :                                                           iterator */
+    1328             :         void                  *unused[NPY_MAXDIMS - 2];
+    1329             :         PyArrayObject         *array;
+    1330             :         /* Flat iterator for the indexed array. For compatibility solely. */
+    1331             :         PyArrayIterObject     *ait;
+    1332             : 
+    1333             :         /*
+    1334             :          * Subspace array. For binary compatibility (was an iterator,
+    1335             :          * but only the check for NULL should be used).
+    1336             :          */
+    1337             :         PyArrayObject         *subspace;
+    1338             : 
+    1339             :         /*
+    1340             :          * if subspace iteration, then this is the array of axes in
+    1341             :          * the underlying array represented by the index objects
+    1342             :          */
+    1343             :         int                   iteraxes[NPY_MAXDIMS];
+    1344             :         npy_intp              fancy_strides[NPY_MAXDIMS];
+    1345             : 
+    1346             :         /* pointer when all fancy indices are 0 */
+    1347             :         char                  *baseoffset;
+    1348             : 
+    1349             :         /*
+    1350             :          * after binding consec denotes at which axis the fancy axes
+    1351             :          * are inserted.
+    1352             :          */
+    1353             :         int                   consec;
+    1354             :         char                  *dataptr;
+    1355             : 
+    1356             :         int                   nd_fancy;
+    1357             :         npy_intp              fancy_dims[NPY_MAXDIMS];
+    1358             : 
+    1359             :         /*
+    1360             :          * Whether the iterator (any of the iterators) requires API.  This is
+    1361             :          * unused by NumPy itself; ArrayMethod flags are more precise.
+    1362             :          */
+    1363             :         int                   needs_api;
+    1364             : 
+    1365             :         /*
+    1366             :          * Extra op information.
+    1367             :          */
+    1368             :         PyArrayObject         *extra_op;
+    1369             :         PyArray_Descr         *extra_op_dtype;         /* desired dtype */
+    1370             :         npy_uint32            *extra_op_flags;         /* Iterator flags */
+    1371             : 
+    1372             :         NpyIter               *extra_op_iter;
+    1373             :         NpyIter_IterNextFunc  *extra_op_next;
+    1374             :         char                  **extra_op_ptrs;
+    1375             : 
+    1376             :         /*
+    1377             :          * Information about the iteration state.
+    1378             :          */
+    1379             :         NpyIter_IterNextFunc  *outer_next;
+    1380             :         char                  **outer_ptrs;
+    1381             :         npy_intp              *outer_strides;
+    1382             : 
+    1383             :         /*
+    1384             :          * Information about the subspace iterator.
+    1385             :          */
+    1386             :         NpyIter               *subspace_iter;
+    1387             :         NpyIter_IterNextFunc  *subspace_next;
+    1388             :         char                  **subspace_ptrs;
+    1389             :         npy_intp              *subspace_strides;
+    1390             : 
+    1391             :         /* Count for the external loop (which ever it is) for API iteration */
+    1392             :         npy_intp              iter_count;
+    1393             : 
+    1394             : } PyArrayMapIterObject;
+    1395             : 
+    1396             : enum {
+    1397             :     NPY_NEIGHBORHOOD_ITER_ZERO_PADDING,
+    1398             :     NPY_NEIGHBORHOOD_ITER_ONE_PADDING,
+    1399             :     NPY_NEIGHBORHOOD_ITER_CONSTANT_PADDING,
+    1400             :     NPY_NEIGHBORHOOD_ITER_CIRCULAR_PADDING,
+    1401             :     NPY_NEIGHBORHOOD_ITER_MIRROR_PADDING
+    1402             : };
+    1403             : 
+    1404             : typedef struct {
+    1405             :     PyObject_HEAD
+    1406             : 
+    1407             :     /*
+    1408             :      * PyArrayIterObject part: keep this in this exact order
+    1409             :      */
+    1410             :     int               nd_m1;            /* number of dimensions - 1 */
+    1411             :     npy_intp          index, size;
+    1412             :     npy_intp          coordinates[NPY_MAXDIMS];/* N-dimensional loop */
+    1413             :     npy_intp          dims_m1[NPY_MAXDIMS];    /* ao->dimensions - 1 */
+    1414             :     npy_intp          strides[NPY_MAXDIMS];    /* ao->strides or fake */
+    1415             :     npy_intp          backstrides[NPY_MAXDIMS];/* how far to jump back */
+    1416             :     npy_intp          factors[NPY_MAXDIMS];     /* shape factors */
+    1417             :     PyArrayObject     *ao;
+    1418             :     char              *dataptr;        /* pointer to current item*/
+    1419             :     npy_bool          contiguous;
+    1420             : 
+    1421             :     npy_intp          bounds[NPY_MAXDIMS][2];
+    1422             :     npy_intp          limits[NPY_MAXDIMS][2];
+    1423             :     npy_intp          limits_sizes[NPY_MAXDIMS];
+    1424             :     npy_iter_get_dataptr_t translate;
+    1425             : 
+    1426             :     /*
+    1427             :      * New members
+    1428             :      */
+    1429             :     npy_intp nd;
+    1430             : 
+    1431             :     /* Dimensions is the dimension of the array */
+    1432             :     npy_intp dimensions[NPY_MAXDIMS];
+    1433             : 
+    1434             :     /*
+    1435             :      * Neighborhood points coordinates are computed relatively to the
+    1436             :      * point pointed by _internal_iter
+    1437             :      */
+    1438             :     PyArrayIterObject* _internal_iter;
+    1439             :     /*
+    1440             :      * To keep a reference to the representation of the constant value
+    1441             :      * for constant padding
+    1442             :      */
+    1443             :     char* constant;
+    1444             : 
+    1445             :     int mode;
+    1446             : } PyArrayNeighborhoodIterObject;
+    1447             : 
+    1448             : /*
+    1449             :  * Neighborhood iterator API
+    1450             :  */
+    1451             : 
+    1452             : /* General: those work for any mode */
+    1453             : static inline int
+    1454             : PyArrayNeighborhoodIter_Reset(PyArrayNeighborhoodIterObject* iter);
+    1455             : static inline int
+    1456             : PyArrayNeighborhoodIter_Next(PyArrayNeighborhoodIterObject* iter);
+    1457             : #if 0
+    1458             : static inline int
+    1459             : PyArrayNeighborhoodIter_Next2D(PyArrayNeighborhoodIterObject* iter);
+    1460             : #endif
+    1461             : 
+    1462             : /*
+    1463             :  * Include inline implementations - functions defined there are not
+    1464             :  * considered public API
+    1465             :  */
+    1466             : #define NUMPY_CORE_INCLUDE_NUMPY__NEIGHBORHOOD_IMP_H_
+    1467             : #include "_neighborhood_iterator_imp.h"
+    1468             : #undef NUMPY_CORE_INCLUDE_NUMPY__NEIGHBORHOOD_IMP_H_
+    1469             : 
+    1470             : 
+    1471             : 
+    1472             : /* The default array type */
+    1473             : #define NPY_DEFAULT_TYPE NPY_DOUBLE
+    1474             : 
+    1475             : /*
+    1476             :  * All sorts of useful ways to look into a PyArrayObject. It is recommended
+    1477             :  * to use PyArrayObject * objects instead of always casting from PyObject *,
+    1478             :  * for improved type checking.
+    1479             :  *
+    1480             :  * In many cases here the macro versions of the accessors are deprecated,
+    1481             :  * but can't be immediately changed to inline functions because the
+    1482             :  * preexisting macros accept PyObject * and do automatic casts. Inline
+    1483             :  * functions accepting PyArrayObject * provides for some compile-time
+    1484             :  * checking of correctness when working with these objects in C.
+    1485             :  */
+    1486             : 
+    1487             : #define PyArray_ISONESEGMENT(m) (PyArray_CHKFLAGS(m, NPY_ARRAY_C_CONTIGUOUS) || \
+    1488             :                                  PyArray_CHKFLAGS(m, NPY_ARRAY_F_CONTIGUOUS))
+    1489             : 
+    1490             : #define PyArray_ISFORTRAN(m) (PyArray_CHKFLAGS(m, NPY_ARRAY_F_CONTIGUOUS) && \
+    1491             :                              (!PyArray_CHKFLAGS(m, NPY_ARRAY_C_CONTIGUOUS)))
+    1492             : 
+    1493             : #define PyArray_FORTRAN_IF(m) ((PyArray_CHKFLAGS(m, NPY_ARRAY_F_CONTIGUOUS) ? \
+    1494             :                                NPY_ARRAY_F_CONTIGUOUS : 0))
+    1495             : 
+    1496             : #if (defined(NPY_NO_DEPRECATED_API) && (NPY_1_7_API_VERSION <= NPY_NO_DEPRECATED_API))
+    1497             : /*
+    1498             :  * Changing access macros into functions, to allow for future hiding
+    1499             :  * of the internal memory layout. This later hiding will allow the 2.x series
+    1500             :  * to change the internal representation of arrays without affecting
+    1501             :  * ABI compatibility.
+    1502             :  */
+    1503             : 
+    1504             : static inline int
+    1505             : PyArray_NDIM(const PyArrayObject *arr)
+    1506             : {
+    1507             :     return ((PyArrayObject_fields *)arr)->nd;
+    1508             : }
+    1509             : 
+    1510             : static inline void *
+    1511             : PyArray_DATA(PyArrayObject *arr)
+    1512             : {
+    1513           0 :     return ((PyArrayObject_fields *)arr)->data;
+    1514             : }
+    1515             : 
+    1516             : static inline char *
+    1517             : PyArray_BYTES(PyArrayObject *arr)
+    1518             : {
+    1519             :     return ((PyArrayObject_fields *)arr)->data;
+    1520             : }
+    1521             : 
+    1522             : static inline npy_intp *
+    1523             : PyArray_DIMS(PyArrayObject *arr)
+    1524             : {
+    1525           0 :     return ((PyArrayObject_fields *)arr)->dimensions;
+    1526             : }
+    1527             : 
+    1528             : static inline npy_intp *
+    1529             : PyArray_STRIDES(PyArrayObject *arr)
+    1530             : {
+    1531             :     return ((PyArrayObject_fields *)arr)->strides;
+    1532             : }
+    1533             : 
+    1534             : static inline npy_intp
+    1535             : PyArray_DIM(const PyArrayObject *arr, int idim)
+    1536             : {
+    1537             :     return ((PyArrayObject_fields *)arr)->dimensions[idim];
+    1538             : }
+    1539             : 
+    1540             : static inline npy_intp
+    1541             : PyArray_STRIDE(const PyArrayObject *arr, int istride)
+    1542             : {
+    1543             :     return ((PyArrayObject_fields *)arr)->strides[istride];
+    1544             : }
+    1545             : 
+    1546             : static inline NPY_RETURNS_BORROWED_REF PyObject *
+    1547             : PyArray_BASE(PyArrayObject *arr)
+    1548             : {
+    1549             :     return ((PyArrayObject_fields *)arr)->base;
+    1550             : }
+    1551             : 
+    1552             : static inline NPY_RETURNS_BORROWED_REF PyArray_Descr *
+    1553             : PyArray_DESCR(PyArrayObject *arr)
+    1554             : {
+    1555             :     return ((PyArrayObject_fields *)arr)->descr;
+    1556             : }
+    1557             : 
+    1558             : static inline int
+    1559             : PyArray_FLAGS(const PyArrayObject *arr)
+    1560             : {
+    1561           0 :     return ((PyArrayObject_fields *)arr)->flags;
+    1562             : }
+    1563             : 
+    1564             : static inline npy_intp
+    1565             : PyArray_ITEMSIZE(const PyArrayObject *arr)
+    1566             : {
+    1567             :     return ((PyArrayObject_fields *)arr)->descr->elsize;
+    1568             : }
+    1569             : 
+    1570             : static inline int
+    1571             : PyArray_TYPE(const PyArrayObject *arr)
+    1572             : {
+    1573           0 :     return ((PyArrayObject_fields *)arr)->descr->type_num;
+    1574             : }
+    1575             : 
+    1576             : static inline int
+    1577             : PyArray_CHKFLAGS(const PyArrayObject *arr, int flags)
+    1578             : {
+    1579           0 :     return (PyArray_FLAGS(arr) & flags) == flags;
+    1580             : }
+    1581             : 
+    1582             : static inline PyObject *
+    1583             : PyArray_GETITEM(const PyArrayObject *arr, const char *itemptr)
+    1584             : {
+    1585             :     return ((PyArrayObject_fields *)arr)->descr->f->getitem(
+    1586             :                                         (void *)itemptr, (PyArrayObject *)arr);
+    1587             : }
+    1588             : 
+    1589             : /*
+    1590             :  * SETITEM should only be used if it is known that the value is a scalar
+    1591             :  * and of a type understood by the arrays dtype.
+    1592             :  * Use `PyArray_Pack` if the value may be of a different dtype.
+    1593             :  */
+    1594             : static inline int
+    1595             : PyArray_SETITEM(PyArrayObject *arr, char *itemptr, PyObject *v)
+    1596             : {
+    1597             :     return ((PyArrayObject_fields *)arr)->descr->f->setitem(v, itemptr, arr);
+    1598             : }
+    1599             : 
+    1600             : #else
+    1601             : 
+    1602             : /* These macros are deprecated as of NumPy 1.7. */
+    1603             : #define PyArray_NDIM(obj) (((PyArrayObject_fields *)(obj))->nd)
+    1604             : #define PyArray_BYTES(obj) (((PyArrayObject_fields *)(obj))->data)
+    1605             : #define PyArray_DATA(obj) ((void *)((PyArrayObject_fields *)(obj))->data)
+    1606             : #define PyArray_DIMS(obj) (((PyArrayObject_fields *)(obj))->dimensions)
+    1607             : #define PyArray_STRIDES(obj) (((PyArrayObject_fields *)(obj))->strides)
+    1608             : #define PyArray_DIM(obj,n) (PyArray_DIMS(obj)[n])
+    1609             : #define PyArray_STRIDE(obj,n) (PyArray_STRIDES(obj)[n])
+    1610             : #define PyArray_BASE(obj) (((PyArrayObject_fields *)(obj))->base)
+    1611             : #define PyArray_DESCR(obj) (((PyArrayObject_fields *)(obj))->descr)
+    1612             : #define PyArray_FLAGS(obj) (((PyArrayObject_fields *)(obj))->flags)
+    1613             : #define PyArray_CHKFLAGS(m, FLAGS) \
+    1614             :         ((((PyArrayObject_fields *)(m))->flags & (FLAGS)) == (FLAGS))
+    1615             : #define PyArray_ITEMSIZE(obj) \
+    1616             :                     (((PyArrayObject_fields *)(obj))->descr->elsize)
+    1617             : #define PyArray_TYPE(obj) \
+    1618             :                     (((PyArrayObject_fields *)(obj))->descr->type_num)
+    1619             : #define PyArray_GETITEM(obj,itemptr) \
+    1620             :         PyArray_DESCR(obj)->f->getitem((char *)(itemptr), \
+    1621             :                                      (PyArrayObject *)(obj))
+    1622             : 
+    1623             : #define PyArray_SETITEM(obj,itemptr,v) \
+    1624             :         PyArray_DESCR(obj)->f->setitem((PyObject *)(v), \
+    1625             :                                      (char *)(itemptr), \
+    1626             :                                      (PyArrayObject *)(obj))
+    1627             : #endif
+    1628             : 
+    1629             : static inline PyArray_Descr *
+    1630             : PyArray_DTYPE(PyArrayObject *arr)
+    1631             : {
+    1632             :     return ((PyArrayObject_fields *)arr)->descr;
+    1633             : }
+    1634             : 
+    1635             : static inline npy_intp *
+    1636             : PyArray_SHAPE(PyArrayObject *arr)
+    1637             : {
+    1638             :     return ((PyArrayObject_fields *)arr)->dimensions;
+    1639             : }
+    1640             : 
+    1641             : /*
+    1642             :  * Enables the specified array flags. Does no checking,
+    1643             :  * assumes you know what you're doing.
+    1644             :  */
+    1645             : static inline void
+    1646             : PyArray_ENABLEFLAGS(PyArrayObject *arr, int flags)
+    1647             : {
+    1648             :     ((PyArrayObject_fields *)arr)->flags |= flags;
+    1649             : }
+    1650             : 
+    1651             : /*
+    1652             :  * Clears the specified array flags. Does no checking,
+    1653             :  * assumes you know what you're doing.
+    1654             :  */
+    1655             : static inline void
+    1656             : PyArray_CLEARFLAGS(PyArrayObject *arr, int flags)
+    1657             : {
+    1658             :     ((PyArrayObject_fields *)arr)->flags &= ~flags;
+    1659             : }
+    1660             : 
+    1661             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
+    1662             :     static inline NPY_RETURNS_BORROWED_REF PyObject *
+    1663             :     PyArray_HANDLER(PyArrayObject *arr)
+    1664             :     {
+    1665             :         return ((PyArrayObject_fields *)arr)->mem_handler;
+    1666             :     }
+    1667             : #endif
+    1668             : 
+    1669             : #define PyTypeNum_ISBOOL(type) ((type) == NPY_BOOL)
+    1670             : 
+    1671             : #define PyTypeNum_ISUNSIGNED(type) (((type) == NPY_UBYTE) ||   \
+    1672             :                                  ((type) == NPY_USHORT) ||     \
+    1673             :                                  ((type) == NPY_UINT) ||       \
+    1674             :                                  ((type) == NPY_ULONG) ||      \
+    1675             :                                  ((type) == NPY_ULONGLONG))
+    1676             : 
+    1677             : #define PyTypeNum_ISSIGNED(type) (((type) == NPY_BYTE) ||      \
+    1678             :                                ((type) == NPY_SHORT) ||        \
+    1679             :                                ((type) == NPY_INT) ||          \
+    1680             :                                ((type) == NPY_LONG) ||         \
+    1681             :                                ((type) == NPY_LONGLONG))
+    1682             : 
+    1683             : #define PyTypeNum_ISINTEGER(type) (((type) >= NPY_BYTE) &&     \
+    1684             :                                 ((type) <= NPY_ULONGLONG))
+    1685             : 
+    1686             : #define PyTypeNum_ISFLOAT(type) ((((type) >= NPY_FLOAT) && \
+    1687             :                               ((type) <= NPY_LONGDOUBLE)) || \
+    1688             :                               ((type) == NPY_HALF))
+    1689             : 
+    1690             : #define PyTypeNum_ISNUMBER(type) (((type) <= NPY_CLONGDOUBLE) || \
+    1691             :                                   ((type) == NPY_HALF))
+    1692             : 
+    1693             : #define PyTypeNum_ISSTRING(type) (((type) == NPY_STRING) ||    \
+    1694             :                                   ((type) == NPY_UNICODE))
+    1695             : 
+    1696             : #define PyTypeNum_ISCOMPLEX(type) (((type) >= NPY_CFLOAT) &&   \
+    1697             :                                 ((type) <= NPY_CLONGDOUBLE))
+    1698             : 
+    1699             : #define PyTypeNum_ISPYTHON(type) (((type) == NPY_LONG) ||      \
+    1700             :                                   ((type) == NPY_DOUBLE) ||    \
+    1701             :                                   ((type) == NPY_CDOUBLE) ||   \
+    1702             :                                   ((type) == NPY_BOOL) ||      \
+    1703             :                                   ((type) == NPY_OBJECT ))
+    1704             : 
+    1705             : #define PyTypeNum_ISFLEXIBLE(type) (((type) >=NPY_STRING) &&  \
+    1706             :                                     ((type) <=NPY_VOID))
+    1707             : 
+    1708             : #define PyTypeNum_ISDATETIME(type) (((type) >=NPY_DATETIME) &&  \
+    1709             :                                     ((type) <=NPY_TIMEDELTA))
+    1710             : 
+    1711             : #define PyTypeNum_ISUSERDEF(type) (((type) >= NPY_USERDEF) && \
+    1712             :                                    ((type) < NPY_USERDEF+     \
+    1713             :                                     NPY_NUMUSERTYPES))
+    1714             : 
+    1715             : #define PyTypeNum_ISEXTENDED(type) (PyTypeNum_ISFLEXIBLE(type) ||  \
+    1716             :                                     PyTypeNum_ISUSERDEF(type))
+    1717             : 
+    1718             : #define PyTypeNum_ISOBJECT(type) ((type) == NPY_OBJECT)
+    1719             : 
+    1720             : 
+    1721             : #define PyDataType_ISBOOL(obj) PyTypeNum_ISBOOL(((PyArray_Descr*)(obj))->type_num)
+    1722             : #define PyDataType_ISUNSIGNED(obj) PyTypeNum_ISUNSIGNED(((PyArray_Descr*)(obj))->type_num)
+    1723             : #define PyDataType_ISSIGNED(obj) PyTypeNum_ISSIGNED(((PyArray_Descr*)(obj))->type_num)
+    1724             : #define PyDataType_ISINTEGER(obj) PyTypeNum_ISINTEGER(((PyArray_Descr*)(obj))->type_num )
+    1725             : #define PyDataType_ISFLOAT(obj) PyTypeNum_ISFLOAT(((PyArray_Descr*)(obj))->type_num)
+    1726             : #define PyDataType_ISNUMBER(obj) PyTypeNum_ISNUMBER(((PyArray_Descr*)(obj))->type_num)
+    1727             : #define PyDataType_ISSTRING(obj) PyTypeNum_ISSTRING(((PyArray_Descr*)(obj))->type_num)
+    1728             : #define PyDataType_ISCOMPLEX(obj) PyTypeNum_ISCOMPLEX(((PyArray_Descr*)(obj))->type_num)
+    1729             : #define PyDataType_ISPYTHON(obj) PyTypeNum_ISPYTHON(((PyArray_Descr*)(obj))->type_num)
+    1730             : #define PyDataType_ISFLEXIBLE(obj) PyTypeNum_ISFLEXIBLE(((PyArray_Descr*)(obj))->type_num)
+    1731             : #define PyDataType_ISDATETIME(obj) PyTypeNum_ISDATETIME(((PyArray_Descr*)(obj))->type_num)
+    1732             : #define PyDataType_ISUSERDEF(obj) PyTypeNum_ISUSERDEF(((PyArray_Descr*)(obj))->type_num)
+    1733             : #define PyDataType_ISEXTENDED(obj) PyTypeNum_ISEXTENDED(((PyArray_Descr*)(obj))->type_num)
+    1734             : #define PyDataType_ISOBJECT(obj) PyTypeNum_ISOBJECT(((PyArray_Descr*)(obj))->type_num)
+    1735             : #define PyDataType_HASFIELDS(obj) (((PyArray_Descr *)(obj))->names != NULL)
+    1736             : #define PyDataType_HASSUBARRAY(dtype) ((dtype)->subarray != NULL)
+    1737             : #define PyDataType_ISUNSIZED(dtype) ((dtype)->elsize == 0 && \
+    1738             :                                       !PyDataType_HASFIELDS(dtype))
+    1739             : #define PyDataType_MAKEUNSIZED(dtype) ((dtype)->elsize = 0)
+    1740             : 
+    1741             : #define PyArray_ISBOOL(obj) PyTypeNum_ISBOOL(PyArray_TYPE(obj))
+    1742             : #define PyArray_ISUNSIGNED(obj) PyTypeNum_ISUNSIGNED(PyArray_TYPE(obj))
+    1743             : #define PyArray_ISSIGNED(obj) PyTypeNum_ISSIGNED(PyArray_TYPE(obj))
+    1744             : #define PyArray_ISINTEGER(obj) PyTypeNum_ISINTEGER(PyArray_TYPE(obj))
+    1745             : #define PyArray_ISFLOAT(obj) PyTypeNum_ISFLOAT(PyArray_TYPE(obj))
+    1746             : #define PyArray_ISNUMBER(obj) PyTypeNum_ISNUMBER(PyArray_TYPE(obj))
+    1747             : #define PyArray_ISSTRING(obj) PyTypeNum_ISSTRING(PyArray_TYPE(obj))
+    1748             : #define PyArray_ISCOMPLEX(obj) PyTypeNum_ISCOMPLEX(PyArray_TYPE(obj))
+    1749             : #define PyArray_ISPYTHON(obj) PyTypeNum_ISPYTHON(PyArray_TYPE(obj))
+    1750             : #define PyArray_ISFLEXIBLE(obj) PyTypeNum_ISFLEXIBLE(PyArray_TYPE(obj))
+    1751             : #define PyArray_ISDATETIME(obj) PyTypeNum_ISDATETIME(PyArray_TYPE(obj))
+    1752             : #define PyArray_ISUSERDEF(obj) PyTypeNum_ISUSERDEF(PyArray_TYPE(obj))
+    1753             : #define PyArray_ISEXTENDED(obj) PyTypeNum_ISEXTENDED(PyArray_TYPE(obj))
+    1754             : #define PyArray_ISOBJECT(obj) PyTypeNum_ISOBJECT(PyArray_TYPE(obj))
+    1755             : #define PyArray_HASFIELDS(obj) PyDataType_HASFIELDS(PyArray_DESCR(obj))
+    1756             : 
+    1757             :     /*
+    1758             :      * FIXME: This should check for a flag on the data-type that
+    1759             :      * states whether or not it is variable length.  Because the
+    1760             :      * ISFLEXIBLE check is hard-coded to the built-in data-types.
+    1761             :      */
+    1762             : #define PyArray_ISVARIABLE(obj) PyTypeNum_ISFLEXIBLE(PyArray_TYPE(obj))
+    1763             : 
+    1764             : #define PyArray_SAFEALIGNEDCOPY(obj) (PyArray_ISALIGNED(obj) && !PyArray_ISVARIABLE(obj))
+    1765             : 
+    1766             : 
+    1767             : #define NPY_LITTLE '<'
+    1768             : #define NPY_BIG '>'
+    1769             : #define NPY_NATIVE '='
+    1770             : #define NPY_SWAP 's'
+    1771             : #define NPY_IGNORE '|'
+    1772             : 
+    1773             : #if NPY_BYTE_ORDER == NPY_BIG_ENDIAN
+    1774             : #define NPY_NATBYTE NPY_BIG
+    1775             : #define NPY_OPPBYTE NPY_LITTLE
+    1776             : #else
+    1777             : #define NPY_NATBYTE NPY_LITTLE
+    1778             : #define NPY_OPPBYTE NPY_BIG
+    1779             : #endif
+    1780             : 
+    1781             : #define PyArray_ISNBO(arg) ((arg) != NPY_OPPBYTE)
+    1782             : #define PyArray_IsNativeByteOrder PyArray_ISNBO
+    1783             : #define PyArray_ISNOTSWAPPED(m) PyArray_ISNBO(PyArray_DESCR(m)->byteorder)
+    1784             : #define PyArray_ISBYTESWAPPED(m) (!PyArray_ISNOTSWAPPED(m))
+    1785             : 
+    1786             : #define PyArray_FLAGSWAP(m, flags) (PyArray_CHKFLAGS(m, flags) &&       \
+    1787             :                                     PyArray_ISNOTSWAPPED(m))
+    1788             : 
+    1789             : #define PyArray_ISCARRAY(m) PyArray_FLAGSWAP(m, NPY_ARRAY_CARRAY)
+    1790             : #define PyArray_ISCARRAY_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_CARRAY_RO)
+    1791             : #define PyArray_ISFARRAY(m) PyArray_FLAGSWAP(m, NPY_ARRAY_FARRAY)
+    1792             : #define PyArray_ISFARRAY_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_FARRAY_RO)
+    1793             : #define PyArray_ISBEHAVED(m) PyArray_FLAGSWAP(m, NPY_ARRAY_BEHAVED)
+    1794             : #define PyArray_ISBEHAVED_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_ALIGNED)
+    1795             : 
+    1796             : 
+    1797             : #define PyDataType_ISNOTSWAPPED(d) PyArray_ISNBO(((PyArray_Descr *)(d))->byteorder)
+    1798             : #define PyDataType_ISBYTESWAPPED(d) (!PyDataType_ISNOTSWAPPED(d))
+    1799             : 
+    1800             : /************************************************************
+    1801             :  * A struct used by PyArray_CreateSortedStridePerm, new in 1.7.
+    1802             :  ************************************************************/
+    1803             : 
+    1804             : typedef struct {
+    1805             :     npy_intp perm, stride;
+    1806             : } npy_stride_sort_item;
+    1807             : 
+    1808             : /************************************************************
+    1809             :  * This is the form of the struct that's stored in the
+    1810             :  * PyCapsule returned by an array's __array_struct__ attribute. See
+    1811             :  * https://docs.scipy.org/doc/numpy/reference/arrays.interface.html for the full
+    1812             :  * documentation.
+    1813             :  ************************************************************/
+    1814             : typedef struct {
+    1815             :     int two;              /*
+    1816             :                            * contains the integer 2 as a sanity
+    1817             :                            * check
+    1818             :                            */
+    1819             : 
+    1820             :     int nd;               /* number of dimensions */
+    1821             : 
+    1822             :     char typekind;        /*
+    1823             :                            * kind in array --- character code of
+    1824             :                            * typestr
+    1825             :                            */
+    1826             : 
+    1827             :     int itemsize;         /* size of each element */
+    1828             : 
+    1829             :     int flags;            /*
+    1830             :                            * how should be data interpreted. Valid
+    1831             :                            * flags are CONTIGUOUS (1), F_CONTIGUOUS (2),
+    1832             :                            * ALIGNED (0x100), NOTSWAPPED (0x200), and
+    1833             :                            * WRITEABLE (0x400).  ARR_HAS_DESCR (0x800)
+    1834             :                            * states that arrdescr field is present in
+    1835             :                            * structure
+    1836             :                            */
+    1837             : 
+    1838             :     npy_intp *shape;       /*
+    1839             :                             * A length-nd array of shape
+    1840             :                             * information
+    1841             :                             */
+    1842             : 
+    1843             :     npy_intp *strides;    /* A length-nd array of stride information */
+    1844             : 
+    1845             :     void *data;           /* A pointer to the first element of the array */
+    1846             : 
+    1847             :     PyObject *descr;      /*
+    1848             :                            * A list of fields or NULL (ignored if flags
+    1849             :                            * does not have ARR_HAS_DESCR flag set)
+    1850             :                            */
+    1851             : } PyArrayInterface;
+    1852             : 
+    1853             : /*
+    1854             :  * This is a function for hooking into the PyDataMem_NEW/FREE/RENEW functions.
+    1855             :  * See the documentation for PyDataMem_SetEventHook.
+    1856             :  */
+    1857             : typedef void (PyDataMem_EventHookFunc)(void *inp, void *outp, size_t size,
+    1858             :                                        void *user_data);
+    1859             : 
+    1860             : 
+    1861             : /*
+    1862             :  * PyArray_DTypeMeta related definitions.
+    1863             :  *
+    1864             :  * As of now, this API is preliminary and will be extended as necessary.
+    1865             :  */
+    1866             : #if defined(NPY_INTERNAL_BUILD) && NPY_INTERNAL_BUILD
+    1867             :     /*
+    1868             :      * The Structures defined in this block are currently considered
+    1869             :      * private API and may change without warning!
+    1870             :      * Part of this (at least the size) is expected to be public API without
+    1871             :      * further modifications.
+    1872             :      */
+    1873             :     /* TODO: Make this definition public in the API, as soon as its settled */
+    1874             :     NPY_NO_EXPORT extern PyTypeObject PyArrayDTypeMeta_Type;
+    1875             : 
+    1876             :     /*
+    1877             :      * While NumPy DTypes would not need to be heap types the plan is to
+    1878             :      * make DTypes available in Python at which point they will be heap types.
+    1879             :      * Since we also wish to add fields to the DType class, this looks like
+    1880             :      * a typical instance definition, but with PyHeapTypeObject instead of
+    1881             :      * only the PyObject_HEAD.
+    1882             :      * This must only be exposed very extremely careful consideration, since
+    1883             :      * it is a fairly complex construct which may be better to allow
+    1884             :      * refactoring of.
+    1885             :      */
+    1886             :     typedef struct {
+    1887             :         PyHeapTypeObject super;
+    1888             : 
+    1889             :         /*
+    1890             :          * Most DTypes will have a singleton default instance, for the
+    1891             :          * parametric legacy DTypes (bytes, string, void, datetime) this
+    1892             :          * may be a pointer to the *prototype* instance?
+    1893             :          */
+    1894             :         PyArray_Descr *singleton;
+    1895             :         /* Copy of the legacy DTypes type number, usually invalid. */
+    1896             :         int type_num;
+    1897             : 
+    1898             :         /* The type object of the scalar instances (may be NULL?) */
+    1899             :         PyTypeObject *scalar_type;
+    1900             :         /*
+    1901             :          * DType flags to signal legacy, parametric, or
+    1902             :          * abstract.  But plenty of space for additional information/flags.
+    1903             :          */
+    1904             :         npy_uint64 flags;
+    1905             : 
+    1906             :         /*
+    1907             :          * Use indirection in order to allow a fixed size for this struct.
+    1908             :          * A stable ABI size makes creating a static DType less painful
+    1909             :          * while also ensuring flexibility for all opaque API (with one
+    1910             :          * indirection due the pointer lookup).
+    1911             :          */
+    1912             :         void *dt_slots;
+    1913             :         void *reserved[3];
+    1914             :     } PyArray_DTypeMeta;
+    1915             : 
+    1916             : #endif  /* NPY_INTERNAL_BUILD */
+    1917             : 
+    1918             : 
+    1919             : /*
+    1920             :  * Use the keyword NPY_DEPRECATED_INCLUDES to ensure that the header files
+    1921             :  * npy_*_*_deprecated_api.h are only included from here and nowhere else.
+    1922             :  */
+    1923             : #ifdef NPY_DEPRECATED_INCLUDES
+    1924             : #error "Do not use the reserved keyword NPY_DEPRECATED_INCLUDES."
+    1925             : #endif
+    1926             : #define NPY_DEPRECATED_INCLUDES
+    1927             : #if !defined(NPY_NO_DEPRECATED_API) || \
+    1928             :     (NPY_NO_DEPRECATED_API < NPY_1_7_API_VERSION)
+    1929             : #include "npy_1_7_deprecated_api.h"
+    1930             : #endif
+    1931             : /*
+    1932             :  * There is no file npy_1_8_deprecated_api.h since there are no additional
+    1933             :  * deprecated API features in NumPy 1.8.
+    1934             :  *
+    1935             :  * Note to maintainers: insert code like the following in future NumPy
+    1936             :  * versions.
+    1937             :  *
+    1938             :  * #if !defined(NPY_NO_DEPRECATED_API) || \
+    1939             :  *     (NPY_NO_DEPRECATED_API < NPY_1_9_API_VERSION)
+    1940             :  * #include "npy_1_9_deprecated_api.h"
+    1941             :  * #endif
+    1942             :  */
+    1943             : #undef NPY_DEPRECATED_INCLUDES
+    1944             : 
+    1945             : #endif  /* NUMPY_CORE_INCLUDE_NUMPY_NDARRAYTYPES_H_ */
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html b/doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html new file mode 100644 index 000000000..c39d31005 --- /dev/null +++ b/doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/AssocVector.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - AssocVector.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2121100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_5
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEaSERKSE_30
_ZNK4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_41
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE6insertERKSC_1143
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEixERKS6_1143
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/AssocVector.h.func.html b/doc/coverageReport/include/crpropa/AssocVector.h.func.html new file mode 100644 index 000000000..206af8f4c --- /dev/null +++ b/doc/coverageReport/include/crpropa/AssocVector.h.func.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/AssocVector.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - AssocVector.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2121100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_5
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE6insertERKSC_1143
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEaSERKSE_30
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEixERKS6_1143
_ZNK4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_41
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/AssocVector.h.gcov.html b/doc/coverageReport/include/crpropa/AssocVector.h.gcov.html new file mode 100644 index 000000000..6e1f36ba8 --- /dev/null +++ b/doc/coverageReport/include/crpropa/AssocVector.h.gcov.html @@ -0,0 +1,457 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/AssocVector.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - AssocVector.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2121100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : ////////////////////////////////////////////////////////////////////////////////
+       2             : // The Loki Library
+       3             : // Copyright (c) 2001 by Andrei Alexandrescu
+       4             : // This code accompanies the book:
+       5             : // Alexandrescu, Andrei. "Modern C++ Design: Generic Programming and Design
+       6             : //     Patterns Applied". Copyright (c) 2001. Addison-Wesley.
+       7             : //
+       8             : // Permission is hereby granted, free of charge, to any person obtaining a copy
+       9             : // of this software and associated documentation files (the "Software"), to deal
+      10             : // in the Software without restriction, including without limitation the rights
+      11             : // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
+      12             : // copies of the Software, and to permit persons to whom the Software is
+      13             : // furnished to do so, subject to the following conditions:
+      14             : //
+      15             : // The above copyright notice and this permission notice shall be included in
+      16             : // all copies or substantial portions of the Software.
+      17             : //
+      18             : // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
+      19             : // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
+      20             : // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
+      21             : // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
+      22             : // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
+      23             : // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
+      24             : // SOFTWARE.
+      25             : ////////////////////////////////////////////////////////////////////////////////
+      26             : #ifndef LOKI_ASSOCVECTOR_INC_
+      27             : #define LOKI_ASSOCVECTOR_INC_
+      28             : 
+      29             : // $Id$
+      30             : 
+      31             : 
+      32             : #include <algorithm>
+      33             : #include <functional>
+      34             : #include <vector>
+      35             : #include <utility>
+      36             : #include <iterator>
+      37             : #include <map>
+      38             : 
+      39             : 
+      40             : namespace Loki
+      41             : {
+      42             : ////////////////////////////////////////////////////////////////////////////////
+      43             : // class template AssocVectorCompare
+      44             : // Used by AssocVector
+      45             : ////////////////////////////////////////////////////////////////////////////////
+      46             : 
+      47             :     namespace Private
+      48             :     {
+      49             :         template <class Value, class C>
+      50             :         class AssocVectorCompare : public C
+      51             :         {
+      52             :             typedef std::pair<typename C::first_argument_type, Value>
+      53             :                 Data;
+      54             :             typedef typename C::first_argument_type first_argument_type;
+      55             : 
+      56             :         public:
+      57             :             AssocVectorCompare()
+      58             :             {}
+      59             : 
+      60             :             AssocVectorCompare(const C& src) : C(src)
+      61             :             {}
+      62             : 
+      63             :             bool operator()(const first_argument_type& lhs,
+      64             :                 const first_argument_type& rhs) const
+      65             :             { return C::operator()(lhs, rhs); }
+      66             : 
+      67             :             bool operator()(const Data& lhs, const Data& rhs) const
+      68             :             { return operator()(lhs.first, rhs.first); }
+      69             : 
+      70             :             bool operator()(const Data& lhs,
+      71             :                 const first_argument_type& rhs) const
+      72          57 :             { return operator()(lhs.first, rhs); }
+      73             : 
+      74             :             bool operator()(const first_argument_type& lhs,
+      75             :                 const Data& rhs) const
+      76             :             { return operator()(lhs, rhs.first); }
+      77             :         };
+      78             :     }
+      79             : 
+      80             : ////////////////////////////////////////////////////////////////////////////////
+      81             : // class template AssocVector
+      82             : // An associative vector built as a syntactic drop-in replacement for std::map
+      83             : // BEWARE: AssocVector doesn't respect all map's guarantees, the most important
+      84             : //     being:
+      85             : // * iterators are invalidated by insert and erase operations
+      86             : // * the complexity of insert/erase is O(N) not O(log N)
+      87             : // * value_type is std::pair<K, V> not std::pair<const K, V>
+      88             : // * iterators are random
+      89             : ////////////////////////////////////////////////////////////////////////////////
+      90             : 
+      91             : 
+      92             :     template
+      93             :     <
+      94             :         class K,
+      95             :         class V,
+      96             :         class C = std::less<K>,
+      97             :         class A = std::allocator< std::pair<K, V> >
+      98             :     >
+      99          30 :     class AssocVector
+     100             :         : private std::vector< std::pair<K, V>, A >
+     101             :         , private Private::AssocVectorCompare<V, C>
+     102             :     {
+     103             :         typedef std::vector<std::pair<K, V>, A> Base;
+     104             :         typedef Private::AssocVectorCompare<V, C> MyCompare;
+     105             : 
+     106             :     public:
+     107             :         typedef K key_type;
+     108             :         typedef V mapped_type;
+     109             :         typedef typename Base::value_type value_type;
+     110             : 
+     111             :         typedef C key_compare;
+     112             :         typedef A allocator_type;
+     113             :         typedef typename A::reference reference;
+     114             :         typedef typename A::const_reference const_reference;
+     115             :         typedef typename Base::iterator iterator;
+     116             :         typedef typename Base::const_iterator const_iterator;
+     117             :         typedef typename Base::size_type size_type;
+     118             :         typedef typename Base::difference_type difference_type;
+     119             :         typedef typename A::pointer pointer;
+     120             :         typedef typename A::const_pointer const_pointer;
+     121             :         typedef typename Base::reverse_iterator reverse_iterator;
+     122             :         typedef typename Base::const_reverse_iterator const_reverse_iterator;
+     123             : 
+     124             :         class value_compare
+     125             :             : public std::binary_function<value_type, value_type, bool>
+     126             :             , private key_compare
+     127             :         {
+     128             :             friend class AssocVector;
+     129             : 
+     130             :         protected:
+     131             :             value_compare(key_compare pred) : key_compare(pred)
+     132             :             {}
+     133             : 
+     134             :         public:
+     135             :             bool operator()(const value_type& lhs, const value_type& rhs) const
+     136             :             { return key_compare::operator()(lhs.first, rhs.first); }
+     137             :         };
+     138             : 
+     139             :         // 23.3.1.1 construct/copy/destroy
+     140             : 
+     141             :         explicit AssocVector(const key_compare& comp = key_compare(),
+     142             :             const A& alloc = A())
+     143             :         : Base(alloc), MyCompare(comp)
+     144             :         {}
+     145             : 
+     146             :         template <class InputIterator>
+     147             :         AssocVector(InputIterator first, InputIterator last,
+     148             :             const key_compare& comp = key_compare(),
+     149             :             const A& alloc = A())
+     150             :         : Base( alloc ), MyCompare( comp )
+     151             :         {
+     152             :             typedef ::std::vector< ::std::pair< K, V >, A > BaseType;
+     153             :             typedef ::std::map< K, V, C, A > TempMap;
+     154             :             typedef ::std::back_insert_iterator< Base > MyInserter;
+     155             :             MyCompare & me = *this;
+     156             :             const A tempAlloc;
+     157             :             // Make a temporary map similar to this type to prevent any duplicate elements.
+     158             :             TempMap temp( first, last, me, tempAlloc );
+     159             :             Base::reserve( temp.size() );
+     160             :             BaseType & target = static_cast< BaseType & >( *this );
+     161             :             MyInserter myInserter = ::std::back_inserter( target );
+     162             :             ::std::copy( temp.begin(), temp.end(), myInserter );
+     163             :         }
+     164             : 
+     165          30 :         AssocVector& operator=(const AssocVector& rhs)
+     166             :         {
+     167          30 :             AssocVector(rhs).swap(*this);
+     168          30 :             return *this;
+     169             :         }
+     170             : 
+     171             :         // iterators:
+     172             :         // The following are here because MWCW gets 'using' wrong
+     173             :         iterator begin() { return Base::begin(); }
+     174             :         const_iterator begin() const { return Base::begin(); }
+     175             :         iterator end() { return Base::end(); }
+     176             :         const_iterator end() const { return Base::end(); }
+     177             :         reverse_iterator rbegin() { return Base::rbegin(); }
+     178             :         const_reverse_iterator rbegin() const { return Base::rbegin(); }
+     179             :         reverse_iterator rend() { return Base::rend(); }
+     180             :         const_reverse_iterator rend() const { return Base::rend(); }
+     181             : 
+     182             :         // capacity:
+     183             :         bool empty() const { return Base::empty(); }
+     184             :         size_type size() const { return Base::size(); }
+     185             :         size_type max_size() { return Base::max_size(); }
+     186             : 
+     187             :         // 23.3.1.2 element access:
+     188        1143 :         mapped_type& operator[](const key_type& key)
+     189        1143 :         { return insert(value_type(key, mapped_type())).first->second; }
+     190             : 
+     191             :         // modifiers:
+     192        1143 :         std::pair<iterator, bool> insert(const value_type& val)
+     193             :         {
+     194             :             bool found(true);
+     195        1143 :             iterator i(lower_bound(val.first));
+     196             : 
+     197          13 :             if (i == end() || this->operator()(val.first, i->first))
+     198             :             {
+     199        1134 :                 i = Base::insert(i, val);
+     200             :                 found = false;
+     201             :             }
+     202        1143 :             return std::make_pair(i, !found);
+     203             :         }
+     204             :         //Section [23.1.2], Table 69
+     205             :         //http://developer.apple.com/documentation/DeveloperTools/gcc-3.3/libstdc++/23_containers/howto.html#4
+     206             :         iterator insert(iterator pos, const value_type& val)
+     207             :         {
+     208             :             if( (pos == begin() || this->operator()(*(pos-1),val)) &&
+     209             :                 (pos == end()    || this->operator()(val, *pos)) )
+     210             :             {
+     211             :                 return Base::insert(pos, val);
+     212             :             }
+     213             :             return insert(val).first;
+     214             :         }
+     215             : 
+     216             :         template <class InputIterator>
+     217             :         void insert(InputIterator first, InputIterator last)
+     218             :         { for (; first != last; ++first) insert(*first); }
+     219             : 
+     220             :         void erase(iterator pos)
+     221           5 :         { Base::erase(pos); }
+     222             : 
+     223             :         size_type erase(const key_type& k)
+     224             :         {
+     225             :             iterator i(find(k));
+     226             :             if (i == end()) return 0;
+     227             :             erase(i);
+     228             :             return 1;
+     229             :         }
+     230             : 
+     231             :         void erase(iterator first, iterator last)
+     232             :         { Base::erase(first, last); }
+     233             : 
+     234             :         void swap(AssocVector& other)
+     235             :         {
+     236             :             Base::swap(other);
+     237             :             MyCompare& me = *this;
+     238             :             MyCompare& rhs = other;
+     239             :             std::swap(me, rhs);
+     240             :         }
+     241             : 
+     242             :         void clear()
+     243             :         { Base::clear(); }
+     244             : 
+     245             :         // observers:
+     246             :         key_compare key_comp() const
+     247             :         { return *this; }
+     248             : 
+     249             :         value_compare value_comp() const
+     250             :         {
+     251             :             const key_compare& comp = *this;
+     252             :             return value_compare(comp);
+     253             :         }
+     254             : 
+     255             :         // 23.3.1.3 map operations:
+     256           5 :         iterator find(const key_type& k)
+     257             :         {
+     258             :             iterator i(lower_bound(k));
+     259           5 :             if (i != end() && this->operator()(k, i->first))
+     260             :             {
+     261             :                 i = end();
+     262             :             }
+     263           5 :             return i;
+     264             :         }
+     265             : 
+     266          41 :         const_iterator find(const key_type& k) const
+     267             :         {
+     268             :             const_iterator i(lower_bound(k));
+     269          33 :             if (i != end() && this->operator()(k, i->first))
+     270             :             {
+     271             :                 i = end();
+     272             :             }
+     273          41 :             return i;
+     274             :         }
+     275             : 
+     276             :         size_type count(const key_type& k) const
+     277             :         { return find(k) != end(); }
+     278             : 
+     279             :         iterator lower_bound(const key_type& k)
+     280             :         {
+     281             :             MyCompare& me = *this;
+     282        1148 :             return std::lower_bound(begin(), end(), k, me);
+     283             :         }
+     284             : 
+     285             :         const_iterator lower_bound(const key_type& k) const
+     286             :         {
+     287             :             const MyCompare& me = *this;
+     288          41 :             return std::lower_bound(begin(), end(), k, me);
+     289             :         }
+     290             : 
+     291             :         iterator upper_bound(const key_type& k)
+     292             :         {
+     293             :             MyCompare& me = *this;
+     294             :             return std::upper_bound(begin(), end(), k, me);
+     295             :         }
+     296             : 
+     297             :         const_iterator upper_bound(const key_type& k) const
+     298             :         {
+     299             :             const MyCompare& me = *this;
+     300             :             return std::upper_bound(begin(), end(), k, me);
+     301             :         }
+     302             : 
+     303             :         std::pair<iterator, iterator> equal_range(const key_type& k)
+     304             :         {
+     305             :             MyCompare& me = *this;
+     306             :             return std::equal_range(begin(), end(), k, me);
+     307             :         }
+     308             : 
+     309             :         std::pair<const_iterator, const_iterator> equal_range(
+     310             :             const key_type& k) const
+     311             :         {
+     312             :             const MyCompare& me = *this;
+     313             :             return std::equal_range(begin(), end(), k, me);
+     314             :         }
+     315             : 
+     316             :         template <class K1, class V1, class C1, class A1>
+     317             :         friend bool operator==(const AssocVector<K1, V1, C1, A1>& lhs,
+     318             :                         const AssocVector<K1, V1, C1, A1>& rhs);
+     319             : 
+     320             :         bool operator<(const AssocVector& rhs) const
+     321             :         {
+     322             :             const Base& me = *this;
+     323             :             const Base& yo = rhs;
+     324             :             return me < yo;
+     325             :         }
+     326             : 
+     327             :         template <class K1, class V1, class C1, class A1>
+     328             :         friend bool operator!=(const AssocVector<K1, V1, C1, A1>& lhs,
+     329             :                                const AssocVector<K1, V1, C1, A1>& rhs);
+     330             : 
+     331             :         template <class K1, class V1, class C1, class A1>
+     332             :         friend bool operator>(const AssocVector<K1, V1, C1, A1>& lhs,
+     333             :                               const AssocVector<K1, V1, C1, A1>& rhs);
+     334             : 
+     335             :         template <class K1, class V1, class C1, class A1>
+     336             :         friend bool operator>=(const AssocVector<K1, V1, C1, A1>& lhs,
+     337             :                                const AssocVector<K1, V1, C1, A1>& rhs);
+     338             : 
+     339             :         template <class K1, class V1, class C1, class A1>
+     340             :         friend bool operator<=(const AssocVector<K1, V1, C1, A1>& lhs,
+     341             :                                const AssocVector<K1, V1, C1, A1>& rhs);
+     342             :     };
+     343             : 
+     344             :     template <class K, class V, class C, class A>
+     345             :     inline bool operator==(const AssocVector<K, V, C, A>& lhs,
+     346             :                            const AssocVector<K, V, C, A>& rhs)
+     347             :     {
+     348             :       const std::vector<std::pair<K, V>, A>& me = lhs;
+     349             :       return me == rhs;
+     350             :     }
+     351             : 
+     352             :     template <class K, class V, class C, class A>
+     353             :     inline bool operator!=(const AssocVector<K, V, C, A>& lhs,
+     354             :                            const AssocVector<K, V, C, A>& rhs)
+     355             :     { return !(lhs == rhs); }
+     356             : 
+     357             :     template <class K, class V, class C, class A>
+     358             :     inline bool operator>(const AssocVector<K, V, C, A>& lhs,
+     359             :                           const AssocVector<K, V, C, A>& rhs)
+     360             :     { return rhs < lhs; }
+     361             : 
+     362             :     template <class K, class V, class C, class A>
+     363             :     inline bool operator>=(const AssocVector<K, V, C, A>& lhs,
+     364             :                            const AssocVector<K, V, C, A>& rhs)
+     365             :     { return !(lhs < rhs); }
+     366             : 
+     367             :     template <class K, class V, class C, class A>
+     368             :     inline bool operator<=(const AssocVector<K, V, C, A>& lhs,
+     369             :                            const AssocVector<K, V, C, A>& rhs)
+     370             :     { return !(rhs < lhs); }
+     371             : 
+     372             : 
+     373             :     // specialized algorithms:
+     374             :     template <class K, class V, class C, class A>
+     375             :     void swap(AssocVector<K, V, C, A>& lhs, AssocVector<K, V, C, A>& rhs)
+     376             :     { lhs.swap(rhs); }
+     377             : 
+     378             : } // namespace Loki
+     379             : 
+     380             : #endif // end file guardian
+     381             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html new file mode 100644 index 000000000..311549a2e --- /dev/null +++ b/doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Candidate.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Candidate.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Candidate.h.func.html b/doc/coverageReport/include/crpropa/Candidate.h.func.html new file mode 100644 index 000000000..2a4fbcad6 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Candidate.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Candidate.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Candidate.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Candidate.h.gcov.html b/doc/coverageReport/include/crpropa/Candidate.h.gcov.html new file mode 100644 index 000000000..393563bad --- /dev/null +++ b/doc/coverageReport/include/crpropa/Candidate.h.gcov.html @@ -0,0 +1,258 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Candidate.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Candidate.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_CANDIDATE_H
+       2             : #define CRPROPA_CANDIDATE_H
+       3             : 
+       4             : #include "crpropa/ParticleState.h"
+       5             : #include "crpropa/Referenced.h"
+       6             : #include "crpropa/AssocVector.h"
+       7             : #include "crpropa/Variant.h"
+       8             : 
+       9             : #include <vector>
+      10             : #include <map>
+      11             : #include <sstream>
+      12             : #include <stdint.h>
+      13             : 
+      14             : namespace crpropa {
+      15             : /**
+      16             :  * \addtogroup Core
+      17             :  * @{
+      18             :  */
+      19             : 
+      20             : /**
+      21             :  @class Candidate Candidate.h include/crpropa/Candidate.h
+      22             :  @brief All information about the cosmic ray.
+      23             : 
+      24             :  The Candidate is a passive object, that holds the information about the state
+      25             :  of the cosmic ray and the simulation itself.
+      26             :  */
+      27             : class Candidate: public Referenced {
+      28             : public:
+      29             :         ParticleState source; /**< Particle state at the source */
+      30             :         ParticleState created; /**< Particle state of parent particle at the time of creation */
+      31             :         ParticleState current; /**< Current particle state */
+      32             :         ParticleState previous; /**< Particle state at the end of the previous step */
+      33             : 
+      34             :         std::vector<ref_ptr<Candidate> > secondaries; /**< Secondary particles from interactions */
+      35             : 
+      36             :         typedef Loki::AssocVector<std::string, Variant> PropertyMap;
+      37             :         PropertyMap properties; /**< Map of property names and their values. */
+      38             : 
+      39             :         /** Parent candidate. 0 if no parent (initial particle). Must not be a ref_ptr to prevent circular referencing. */
+      40             :         Candidate *parent;
+      41             : 
+      42             : private:
+      43             :         bool active; /**< Active status */
+      44             :         double weight; /**< Weight of the candidate */
+      45             :         double redshift; /**< Current simulation time-point in terms of redshift z */
+      46             :         double trajectoryLength; /**< Comoving distance [m] the candidate has traveled so far */
+      47             :         double currentStep; /**< Size of the currently performed step in [m] comoving units */
+      48             :         double nextStep; /**< Proposed size of the next propagation step in [m] comoving units */
+      49             :         std::string tagOrigin; /**< Name of interaction/source process which created this candidate*/
+      50             : 
+      51             :         static uint64_t nextSerialNumber;
+      52             :         uint64_t serialNumber;
+      53             : 
+      54             : public:
+      55             :         Candidate(
+      56             :                 int id = 0,
+      57             :                 double energy = 0,
+      58             :                 Vector3d position = Vector3d(0, 0, 0),
+      59             :                 Vector3d direction = Vector3d(-1, 0, 0),
+      60             :                 double z = 0,
+      61             :                 double weight = 1., 
+      62             :                 std::string tagOrigin = "PRIM"
+      63             :         );
+      64             : 
+      65             :         /**
+      66             :          Creates a candidate, initializing the Candidate::source, Candidate::created,
+      67             :          Candidate::previous and Candidate::current state with the argument.
+      68             :          */
+      69             :         Candidate(const ParticleState &state);
+      70             : 
+      71             :         bool isActive() const;
+      72             :         void setActive(bool b);
+      73             : 
+      74             :         void setTrajectoryLength(double length);
+      75             :         double getTrajectoryLength() const;
+      76             : 
+      77             :         void setRedshift(double z);
+      78             :         double getRedshift() const;
+      79             : 
+      80             :         /**
+      81             :          Sets weight of each candidate.
+      82             :          Weights are calculated for each tracked secondary.
+      83             :          */
+      84             :         void setWeight(double weight);
+      85             :     void updateWeight(double weight);
+      86             :         double getWeight() const;
+      87             : 
+      88             :         /**
+      89             :          Sets the current step and increases the trajectory length accordingly.
+      90             :          Only the propagation module should use this.
+      91             :          */
+      92             :         void setCurrentStep(double step);
+      93             :         double getCurrentStep() const;
+      94             : 
+      95             :         /**
+      96             :          Sets the proposed next step.
+      97             :          Only the propagation module should use this.
+      98             :          */
+      99             :         void setNextStep(double step);
+     100             :         double getNextStep() const;
+     101             : 
+     102             :         /**
+     103             :          Sets the tagOrigin of the candidate. Can be used to trace back the interactions
+     104             :          */
+     105             :         void setTagOrigin(std::string tagOrigin);
+     106             :         std::string getTagOrigin() const;
+     107             : 
+     108             :         /**
+     109             :          Make a bid for the next step size: the lowest wins.
+     110             :          */
+     111             :         void limitNextStep(double step);
+     112             : 
+     113             :         void setProperty(const std::string &name, const Variant &value);
+     114             :         const Variant &getProperty(const std::string &name) const;
+     115             :         bool removeProperty(const std::string &name);
+     116             :         bool hasProperty(const std::string &name) const;
+     117             : 
+     118             :         /**
+     119             :          Add a new candidate to the list of secondaries.
+     120             :          @param c Candidate
+     121             : 
+     122             :          Adds a new candidate to the list of secondaries of this candidate.
+     123             :          The secondaries Candidate::source and Candidate::previous state are set to the _source_ and _previous_ state of its parent.
+     124             :          The secondaries Candidate::created and Candidate::current state are set to the _current_ state of its parent, except for the secondaries current energy and particle id.
+     125             :          Trajectory length and redshift are copied from the parent.
+     126             :          */
+     127             :         void addSecondary(Candidate *c);
+     128           4 :         inline void addSecondary(ref_ptr<Candidate> c) { addSecondary(c.get()); };
+     129             :         /**
+     130             :          Add a new candidate to the list of secondaries.
+     131             :          @param id                      particle ID of the secondary
+     132             :          @param energy          energy of the secondary
+     133             :          @param w                       weight of the secondary
+     134             :          @param tagOrigin       tag of the secondary
+     135             :          */
+     136             :         void addSecondary(int id, double energy, double w = 1., std::string tagOrigin = "SEC");
+     137             :         /**
+     138             :          Add a new candidate to the list of secondaries.
+     139             :          @param id                      particle ID of the secondary
+     140             :          @param energy          energy of the secondary
+     141             :          @param position        start position of the secondary
+     142             :          @param w                       weight of the secondary
+     143             :          @param tagOrigin       tag of the secondary
+     144             :          */
+     145             :         void addSecondary(int id, double energy, Vector3d position, double w = 1., std::string tagOrigin = "SEC");
+     146             :         void clearSecondaries();
+     147             : 
+     148             :         std::string getDescription() const;
+     149             : 
+     150             :         /** Unique (inside process) serial number (id) of candidate */
+     151             :         uint64_t getSerialNumber() const;
+     152             :         void setSerialNumber(const uint64_t snr);
+     153             : 
+     154             :         /** Serial number of candidate at source*/
+     155             :         uint64_t getSourceSerialNumber() const;
+     156             : 
+     157             :         /** Serial number of candidate at creation */
+     158             :         uint64_t getCreatedSerialNumber() const;
+     159             : 
+     160             :         /** Set the next serial number to use */
+     161             :         static void setNextSerialNumber(uint64_t snr);
+     162             : 
+     163             :         /** Get the next serial number that will be assigned */
+     164             :         static uint64_t getNextSerialNumber();
+     165             : 
+     166             :         /**
+     167             :          Create an exact clone of candidate
+     168             :          @param recursive       recursively clone and add the secondaries
+     169             :          */
+     170             :         ref_ptr<Candidate> clone(bool recursive = false) const;
+     171             : 
+     172             :         /**
+     173             :          Copy the source particle state to the current state
+     174             :          and activate it if inactive, e.g. restart it
+     175             :         */
+     176             :         void restart();
+     177             : };
+     178             : 
+     179             : /** @}*/
+     180             : } // namespace crpropa
+     181             : 
+     182             : #endif // CRPROPA_CANDIDATE_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Common.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Common.h.func-sort-c.html new file mode 100644 index 000000000..b6011ea62 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Common.h.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Common.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Common.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1010100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8gaussIntIZNS_20common_gaussInt_Test8TestBodyEvEUldE0_EEdOT_dd1
_ZN7crpropa8gaussIntIZNKS_19PhotoPionProduction7probEpsEdbddEUldE_EEdOT_dd10660
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Common.h.func.html b/doc/coverageReport/include/crpropa/Common.h.func.html new file mode 100644 index 000000000..480121887 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Common.h.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Common.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Common.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1010100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8gaussIntIZNKS_19PhotoPionProduction7probEpsEdbddEUldE_EEdOT_dd10660
_ZN7crpropa8gaussIntIZNS_20common_gaussInt_Test8TestBodyEvEUldE0_EEdOT_dd1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Common.h.gcov.html b/doc/coverageReport/include/crpropa/Common.h.gcov.html new file mode 100644 index 000000000..13a42780e --- /dev/null +++ b/doc/coverageReport/include/crpropa/Common.h.gcov.html @@ -0,0 +1,163 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Common.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Common.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1010100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_COMMON_H
+       2             : #define CRPROPA_COMMON_H
+       3             : 
+       4             : #include <string>
+       5             : #include <vector>
+       6             : /**
+       7             :  @file
+       8             :  @brief Common helper functions
+       9             :  */
+      10             : 
+      11             : namespace crpropa {
+      12             : /**
+      13             :  * \addtogroup Core
+      14             :  * @{
+      15             :  */
+      16             : 
+      17             : // Returns the full path to a CRPropa data file
+      18             : std::string getDataPath(std::string filename);
+      19             : 
+      20             : // Returns the install prefix
+      21             : std::string getInstallPrefix();
+      22             : 
+      23             : // Returns a certain digit from a given integer
+      24             : inline int digit(const int& value, const int& d) {
+      25        1249 :         return (value % (d * 10)) / d;
+      26             : }
+      27             : 
+      28             : // Return value xclip which is the closest to x, so that lower <= xclip <= upper
+      29             : template <typename T>
+      30             : T clip(const T& x, const T& lower, const T& upper) {
+      31      499341 :         return std::max(lower, std::min(x, upper));
+      32             : }
+      33             : 
+      34             : // Perform linear interpolation on a set of n tabulated data points X[0 .. n-1] -> Y[0 .. n-1]
+      35             : // Returns Y[0] if x < X[0] and Y[n-1] if x > X[n-1]
+      36             : double interpolate(double x, const std::vector<double>& X,
+      37             :                 const std::vector<double>& Y);
+      38             : 
+      39             : 
+      40             : // Perform bilinear interpolation on a set of (n,m) tabulated data points X[0 .. n-1], Y[0 .. m-1] -> Z[0.. n-1*m-1]
+      41             : // Returns 0 if x < X[0] or x > X[n-1] or y < Y[0] or y > Y[m-1]
+      42             : double interpolate2d(double x, double y, const std::vector<double>& X,
+      43             :                 const std::vector<double>& Y, const std::vector<double>& Z);
+      44             : 
+      45             : // Perform linear interpolation on equidistant tabulated data
+      46             : // Returns Y[0] if x < lo and Y[n-1] if x > hi
+      47             : double interpolateEquidistant(double x, double lo, double hi,
+      48             :                 const std::vector<double>& Y);
+      49             : 
+      50             : // Find index of value in a sorted vector X that is closest to x
+      51             : size_t closestIndex(double x, const std::vector<double> &X);
+      52             : /** @}*/
+      53             : 
+      54             : 
+      55             : // pow implementation as template for integer exponents pow_integer<2>(x)
+      56             : // evaluates to x*x
+      57             : template <unsigned int exponent>
+      58             : inline double pow_integer(double base)
+      59             : {
+      60       63069 :   return pow_integer<(exponent >> 1)>(base*base) * (((exponent & 1) > 0) ? base : 1);
+      61             : }
+      62             : 
+      63             : template <>
+      64             : inline double pow_integer<0>(double base)
+      65             : {
+      66             :   return 1;
+      67             : }
+      68             : 
+      69             : // - input:  function over which to integrate, integration limits A and B
+      70             : // - output: 8-points Gauß-Legendre integral
+      71             : static const double X[8] = {.0950125098, .2816035507, .4580167776, .6178762444, .7554044083, .8656312023, .9445750230, .9894009349};
+      72             : static const double W[8] = {.1894506104, .1826034150, .1691565193, .1495959888, .1246289712, .0951585116, .0622535239, .0271524594};
+      73             : template<typename Integrand>
+      74       10661 : double gaussInt(Integrand&& integrand, double A, double B) {
+      75       10661 :         const double XM = 0.5 * (B + A);
+      76       10661 :         const double XR = 0.5 * (B - A);
+      77             :         double SS = 0.;
+      78       95958 :         for (int i = 0; i < 8; ++i) {
+      79       85296 :                 double DX = XR * X[i];
+      80       85296 :                 SS += W[i] * (integrand(XM + DX) + integrand(XM - DX));
+      81             :         }
+      82       10661 :         return XR * SS;
+      83             : }
+      84             : 
+      85             : } // namespace crpropa
+      86             : 
+      87             : #endif // CRPROPA_COMMON_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html b/doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html new file mode 100644 index 000000000..a2a1cc9dd --- /dev/null +++ b/doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/EmissionMap.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - EmissionMap.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/EmissionMap.h.func.html b/doc/coverageReport/include/crpropa/EmissionMap.h.func.html new file mode 100644 index 000000000..fd1749d15 --- /dev/null +++ b/doc/coverageReport/include/crpropa/EmissionMap.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/EmissionMap.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - EmissionMap.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html b/doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html new file mode 100644 index 000000000..deeb84f2e --- /dev/null +++ b/doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html @@ -0,0 +1,212 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/EmissionMap.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - EmissionMap.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_EMISSION_MAP_H
+       2             : #define CRPROPA_EMISSION_MAP_H
+       3             : 
+       4             : #include "Referenced.h"
+       5             : #include "Candidate.h"
+       6             : 
+       7             : namespace crpropa {
+       8             : 
+       9             : /**
+      10             :  @class CylindricalProjectionMap
+      11             :  @brief 2D histogram of spherical coordinates in equal-area projection
+      12             :  */
+      13             : class CylindricalProjectionMap : public Referenced {
+      14             : private:
+      15             :         size_t nPhi, nTheta;
+      16             :         double sPhi, sTheta;
+      17             :         mutable bool dirty;
+      18             :         std::vector<double> pdf;
+      19             :         mutable std::vector<double> cdf;
+      20             : 
+      21             :         /** Calculate the cdf from the pdf */
+      22             :         void updateCdf() const;
+      23             : 
+      24             : public:
+      25             :         CylindricalProjectionMap();
+      26             :         /** constructur
+      27             :          * @param nPhi number of bins for phi (0-2pi)
+      28             :          * @param nTheta number of bins for theta (0-pi)
+      29             :          */
+      30             :         CylindricalProjectionMap(size_t nPhi, size_t nTheta);
+      31             : 
+      32             :         /** Increment the bin value in direction by weight. */
+      33             :         void fillBin(const Vector3d& direction, double weight = 1.);
+      34             : 
+      35             :         /** Increment the bin value by weight. */
+      36             :         void fillBin(size_t bin, double weight = 1.);
+      37             : 
+      38             :         /** Draw a random vector from the distribution. */
+      39             :         Vector3d drawDirection() const;
+      40             : 
+      41             :         /** Check if the direction has a non zero propabiliy. */
+      42             :         bool checkDirection(const Vector3d &direction) const;
+      43             : 
+      44             :         const std::vector<double>& getPdf() const;
+      45             :         std::vector<double>& getPdf();
+      46             : 
+      47             :         const std::vector<double>& getCdf() const;
+      48             : 
+      49             :         size_t getNPhi();
+      50             :         size_t getNTheta();
+      51             : 
+      52             :         /** Calculate the bin from a direction */
+      53             :         size_t binFromDirection(const Vector3d& direction) const;
+      54             : 
+      55             :         /** Calculate a random vector inside the bin boundaries */
+      56             :         Vector3d directionFromBin(size_t bin) const;
+      57             : };
+      58             : 
+      59             : /**
+      60             :  @class EmissionMap
+      61             :  @brief Particle Type and energy binned emission maps.
+      62             : 
+      63             :  Use SourceEmissionMap to suppress directions at the source. Use EmissionMapFiller to create EmissionMap from Observer.
+      64             :  */
+      65           2 : class EmissionMap : public Referenced {
+      66             : public:
+      67             :         typedef std::pair<int, size_t> key_t;
+      68             :         typedef std::map<key_t, ref_ptr<CylindricalProjectionMap> > map_t;
+      69             : 
+      70             :         EmissionMap();
+      71             :         /**
+      72             :          * @param nPhi number of bins for phi (0-2pi)
+      73             :          * @param nTheta number of bins for theta (0-pi)
+      74             :          * @param nEnergy number of bins for energy (1e-4 - 1e4 EeV)
+      75             :          */
+      76             :         EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy);
+      77             : 
+      78             :         /**
+      79             :          * @param nPhi number of bins for phi (0-2pi)
+      80             :          * @param nTheta number of bins for theta (0-pi)
+      81             :          * @param nEnergy number of bins for energy (1e-4 - 1e4 EeV)
+      82             :          * @param minEnergy minimum energy for binning
+      83             :          * @param maxEnergy maximum energy for binning
+      84             :          */
+      85             :         EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy, double minEnergy, double maxEnergy);
+      86             : 
+      87             :         /** Calculate energy from bin */
+      88             :         double energyFromBin(size_t bin) const;
+      89             : 
+      90             :         /** Calculate bin from energy */
+      91             :         size_t binFromEnergy(double energy) const;
+      92             : 
+      93             :         map_t &getMaps();
+      94             :         const map_t &getMaps() const;
+      95             : 
+      96             :         /** Increment the value for particle type, energy and direction by weight. */
+      97             :         void fillMap(int pid, double energy, const Vector3d& direction, double weight = 1.);
+      98             :         /** Increment the value for the particle state by weight. */
+      99             :         void fillMap(const ParticleState& state, double weight = 1.);
+     100             : 
+     101             :         /** Draw a random vector from the distribution. */
+     102             :         bool drawDirection(int pid, double energy, Vector3d& direction) const;
+     103             :         /** Draw a random vector from the distribution. */
+     104             :         bool drawDirection(const ParticleState& state, Vector3d& direction) const;
+     105             : 
+     106             :         /** Check if the direction has a non zero propabiliy. */
+     107             :         bool checkDirection(int pid, double energy, const Vector3d& direction) const;
+     108             :         /** Check if the direction has a non zero propabiliy. */
+     109             :         bool checkDirection(const ParticleState& state) const;
+     110             : 
+     111             :         /** Check if a valid map exists */
+     112             :         bool hasMap(int pid, double energy);
+     113             : 
+     114             :         /** Get the map for the specified pid and energy */
+     115             :         ref_ptr<CylindricalProjectionMap> getMap(int pid, double energy);
+     116             : 
+     117             :         /** Save the content of the maps into a text file */
+     118             :         void save(const std::string &filename);
+     119             :         /** Load the content of the maps from a text file */
+     120             :         void load(const std::string &filename);
+     121             : 
+     122             :         /** Merge other maps, add pdfs */
+     123             :         void merge(const EmissionMap *other);
+     124             : 
+     125             :         /** Merge maps from file */
+     126             :         void merge(const std::string &filename);
+     127             : 
+     128             : protected:
+     129             :         double minEnergy, maxEnergy, logStep;
+     130             :         size_t nPhi, nTheta, nEnergy;
+     131             :         map_t maps;
+     132             : };
+     133             : 
+     134             : } // namespace crpropa
+     135             : 
+     136             : #endif // CRPROPA_EMISSION_MAP_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html new file mode 100644 index 000000000..6b4cfc036 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Geometry.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Geometry.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3475.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa7Surface14getDescriptionB5cxx11Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Geometry.h.func.html b/doc/coverageReport/include/crpropa/Geometry.h.func.html new file mode 100644 index 000000000..9e2e188ad --- /dev/null +++ b/doc/coverageReport/include/crpropa/Geometry.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Geometry.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Geometry.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3475.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa7Surface14getDescriptionB5cxx11Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Geometry.h.gcov.html b/doc/coverageReport/include/crpropa/Geometry.h.gcov.html new file mode 100644 index 000000000..f7e267162 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Geometry.h.gcov.html @@ -0,0 +1,165 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Geometry.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Geometry.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3475.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_GEOMETRY_H
+       2             : #define CRPROPA_GEOMETRY_H
+       3             : 
+       4             : #include <vector>
+       5             : #include <string>
+       6             : 
+       7             : #include "crpropa/Candidate.h"
+       8             : #include "crpropa/Vector3.h"
+       9             : #include "crpropa/Referenced.h"
+      10             : 
+      11             : namespace crpropa {
+      12             : /**
+      13             :  * \addtogroup Core
+      14             :  * @{
+      15             :  */
+      16             : 
+      17             : /**
+      18             :  @class Surface
+      19             :  @brief A geometrical surface
+      20             : 
+      21             :  Defines a surface. Can be queried if the candidate has crossed the surface in the last step.
+      22             :  */
+      23             : class Surface : public Referenced {
+      24             : public:
+      25             :         /** Returns the distance of a point to the surface. Negative on the one side,
+      26             :          positive on the other. For closed surfaces it is negative on the inside.
+      27             :          @param point   vector corresponding to the point to which compute the distance
+      28             :          */
+      29             :         virtual double distance(const Vector3d& point) const = 0;
+      30             :         /**  Returns the normal to the surface at a point. Negative on the one side,
+      31             :          positive on the other. For closed surfaces it is negative on the inside.
+      32             :          @param point   vector corresponding to the point to which compute the normal vector
+      33             :          */
+      34             :         virtual Vector3d normal(const Vector3d& point) const = 0;
+      35           0 :         virtual std::string getDescription() const {return "Surface without description.";};
+      36             : };
+      37             : 
+      38             : 
+      39             : /**
+      40             :  @class Plane
+      41             :  @brief A plane given by a point x0 and two axes v1 and v2 with normal n = v1.cross(v2) or the normal n. Note that distance is negative on one side of the plane and positive on the other, depending on the orientation of the normal vector.
+      42             :  */
+      43           1 : class Plane: public Surface {
+      44             : private:
+      45             :         Vector3d x0, n;
+      46             : public:
+      47             :         Plane(const Vector3d& x0, const Vector3d& v1,const Vector3d& v2);
+      48             :         Plane(const Vector3d& x0, const Vector3d& n);
+      49             :         virtual double distance(const Vector3d &x) const;
+      50             :         virtual Vector3d normal(const Vector3d& point) const;
+      51             :         virtual std::string getDescription() const;
+      52             : };
+      53             : 
+      54             : 
+      55             : /**
+      56             :  @class Sphere
+      57             :  @brief A sphere around point _center with radius _radius.
+      58             :  */
+      59           1 : class Sphere: public Surface {
+      60             : private:
+      61             :         Vector3d center;
+      62             :         double radius;
+      63             : public:
+      64             :         Sphere(const Vector3d& center, double radius);
+      65             :         virtual double distance(const Vector3d &point) const;
+      66             :         virtual Vector3d normal(const Vector3d& point) const;
+      67             :         virtual std::string getDescription() const;
+      68             : };
+      69             : 
+      70             : 
+      71             : /**
+      72             :  @class ParaxialBox
+      73             :  @brief A box with perpendicular surfaces aligned to the x,y,z-axes.
+      74             :  */
+      75           1 : class ParaxialBox: public Surface {
+      76             : private:
+      77             :         Vector3d corner, size;
+      78             : public:
+      79             :         ParaxialBox(const Vector3d& corner, const Vector3d& size);
+      80             :         virtual double distance(const Vector3d &point) const;
+      81             :         virtual Vector3d normal(const Vector3d& point) const;
+      82             :         virtual std::string getDescription() const;
+      83             : };
+      84             : 
+      85             : 
+      86             : /** @}*/
+      87             : } // namespace crpropa
+      88             : 
+      89             : #endif // CRPROPA_GEOMETRY_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html new file mode 100644 index 000000000..3c651a9f5 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html @@ -0,0 +1,296 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Grid.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Grid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:17319588.7 %
Date:2024-04-08 14:58:22Functions:235641.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14GridPropertiesD2Ev0
_ZN7crpropa4GridINS_7Vector3IdEEE11interpolateERKS2_0
_ZN7crpropa4GridINS_7Vector3IdEEE11setGridSizeEmmm0
_ZN7crpropa4GridINS_7Vector3IdEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_md0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmS2_0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmd0
_ZN7crpropa4GridINS_7Vector3IfEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmS4_0
_ZN7crpropa4GridIdE11interpolateERKNS_7Vector3IdEE0
_ZN7crpropa4GridIdE11setGridSizeEmmm0
_ZN7crpropa4GridIdE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmd0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmS3_0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmd0
_ZN7crpropa4GridIdEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridIfE20setInterpolationTypeENS_17interpolationTypeE0
_ZNK7crpropa4GridINS_7Vector3IdEEE12closestValueERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE17positionFromIndexEi0
_ZNK7crpropa4GridINS_7Vector3IdEEE17simdreflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE19tricubicInterpolateENS1_IfEERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE20trilinearInterpolateERKS2_0
_ZNK7crpropa4GridINS_7Vector3IfEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IfEEE17positionFromIndexEi0
_ZNK7crpropa4GridIdE12closestValueERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE13reflectiveGetEmmm0
_ZNK7crpropa4GridIdE17positionFromIndexEi0
_ZNK7crpropa4GridIdE19tricubicInterpolateEdRKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE20trilinearInterpolateERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE22CubicInterpolateScalarEddddd0
_ZNK7crpropa4GridIfE13reflectiveGetEmmm0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmd1
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmS3_1
_ZN7crpropa14GridPropertiesD0Ev2
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmd2
_ZN7crpropa4GridIfEC2ERKNS_14GridPropertiesE3
_ZNK7crpropa4GridIfE19tricubicInterpolateEdRKNS_7Vector3IdEE3
_ZN7crpropa4GridINS_7Vector3IfEEEC2ERKNS_14GridPropertiesE6
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmd6
_ZNK7crpropa4GridIfE12closestValueERKNS_7Vector3IdEE7
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmd9
_ZNK7crpropa4GridIfE20trilinearInterpolateERKNS_7Vector3IdEE9
_ZNK7crpropa4GridINS_7Vector3IfEEE12closestValueERKNS1_IdEE10
_ZN7crpropa4GridIfE11setGridSizeEmmm12
_ZNK7crpropa4GridINS_7Vector3IfEEE19tricubicInterpolateES2_RKNS1_IdEE15
_ZN7crpropa4GridINS_7Vector3IfEEE11setGridSizeEmmm16
_ZN7crpropa4GridIfE11interpolateERKNS_7Vector3IdEE18
_ZN7crpropa15reflectiveClampEdiRiS0_Rd20
_ZN7crpropa5roundEd51
_ZNK7crpropa4GridIfE22CubicInterpolateScalarEddddd63
_ZNK7crpropa4GridINS_7Vector3IfEEE17simdreflectiveGetEmmm384
_ZNK7crpropa4GridIfE17positionFromIndexEi10103
_ZNK7crpropa4GridINS_7Vector3IfEEE20trilinearInterpolateERKNS1_IdEE100046
_ZN7crpropa4GridINS_7Vector3IfEEE11interpolateERKNS1_IdEE100073
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Grid.h.func.html b/doc/coverageReport/include/crpropa/Grid.h.func.html new file mode 100644 index 000000000..0b9457ac3 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Grid.h.func.html @@ -0,0 +1,296 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Grid.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Grid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:17319588.7 %
Date:2024-04-08 14:58:22Functions:235641.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14GridPropertiesD0Ev2
_ZN7crpropa14GridPropertiesD2Ev0
_ZN7crpropa15reflectiveClampEdiRiS0_Rd20
_ZN7crpropa4GridINS_7Vector3IdEEE11interpolateERKS2_0
_ZN7crpropa4GridINS_7Vector3IdEEE11setGridSizeEmmm0
_ZN7crpropa4GridINS_7Vector3IdEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_md0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmS2_0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmd0
_ZN7crpropa4GridINS_7Vector3IfEEE11interpolateERKNS1_IdEE100073
_ZN7crpropa4GridINS_7Vector3IfEEE11setGridSizeEmmm16
_ZN7crpropa4GridINS_7Vector3IfEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmd9
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmS4_0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmd1
_ZN7crpropa4GridINS_7Vector3IfEEEC2ERKNS_14GridPropertiesE6
_ZN7crpropa4GridIdE11interpolateERKNS_7Vector3IdEE0
_ZN7crpropa4GridIdE11setGridSizeEmmm0
_ZN7crpropa4GridIdE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmd0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmS3_0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmd0
_ZN7crpropa4GridIdEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridIfE11interpolateERKNS_7Vector3IdEE18
_ZN7crpropa4GridIfE11setGridSizeEmmm12
_ZN7crpropa4GridIfE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmd2
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmS3_1
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmd6
_ZN7crpropa4GridIfEC2ERKNS_14GridPropertiesE3
_ZN7crpropa5roundEd51
_ZNK7crpropa4GridINS_7Vector3IdEEE12closestValueERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE17positionFromIndexEi0
_ZNK7crpropa4GridINS_7Vector3IdEEE17simdreflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE19tricubicInterpolateENS1_IfEERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE20trilinearInterpolateERKS2_0
_ZNK7crpropa4GridINS_7Vector3IfEEE12closestValueERKNS1_IdEE10
_ZNK7crpropa4GridINS_7Vector3IfEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IfEEE17positionFromIndexEi0
_ZNK7crpropa4GridINS_7Vector3IfEEE17simdreflectiveGetEmmm384
_ZNK7crpropa4GridINS_7Vector3IfEEE19tricubicInterpolateES2_RKNS1_IdEE15
_ZNK7crpropa4GridINS_7Vector3IfEEE20trilinearInterpolateERKNS1_IdEE100046
_ZNK7crpropa4GridIdE12closestValueERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE13reflectiveGetEmmm0
_ZNK7crpropa4GridIdE17positionFromIndexEi0
_ZNK7crpropa4GridIdE19tricubicInterpolateEdRKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE20trilinearInterpolateERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE22CubicInterpolateScalarEddddd0
_ZNK7crpropa4GridIfE12closestValueERKNS_7Vector3IdEE7
_ZNK7crpropa4GridIfE13reflectiveGetEmmm0
_ZNK7crpropa4GridIfE17positionFromIndexEi10103
_ZNK7crpropa4GridIfE19tricubicInterpolateEdRKNS_7Vector3IdEE3
_ZNK7crpropa4GridIfE20trilinearInterpolateERKNS_7Vector3IdEE9
_ZNK7crpropa4GridIfE22CubicInterpolateScalarEddddd63
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Grid.h.gcov.html b/doc/coverageReport/include/crpropa/Grid.h.gcov.html new file mode 100644 index 000000000..cad5f1688 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Grid.h.gcov.html @@ -0,0 +1,640 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Grid.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Grid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:17319588.7 %
Date:2024-04-08 14:58:22Functions:235641.1 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_GRID_H
+       2             : #define CRPROPA_GRID_H
+       3             : 
+       4             : #include "crpropa/Referenced.h"
+       5             : #include "crpropa/Vector3.h"
+       6             : 
+       7             : #include "kiss/string.h"
+       8             : #include "kiss/logger.h"
+       9             : 
+      10             : #include <vector>
+      11             : #include <type_traits>
+      12             : #if HAVE_SIMD
+      13             : #include <immintrin.h>
+      14             : #include <smmintrin.h>
+      15             : #endif // HAVE_SIMD
+      16             : 
+      17             : namespace crpropa {
+      18             : 
+      19             : /** If set to TRILINEAR, use trilinear interpolation (standard)
+      20             : If set to TRICUBIC, use tricubic interpolation instead of trilinear interpolation
+      21             : If set to NEAREST_NEIGHBOUR , use nearest neighbour interpolation instead of trilinear interpolation */
+      22             : enum interpolationType {
+      23             :   TRILINEAR = 0,
+      24             :   TRICUBIC,
+      25             :   NEAREST_NEIGHBOUR
+      26             : };
+      27             : 
+      28             : /** Lower and upper neighbour in a periodically continued unit grid */
+      29             : inline void periodicClamp(double x, int n, int &lo, int &hi) {
+      30      100051 :         lo = ((int(floor(x)) % (n)) + (n)) % (n);
+      31          10 :         hi = (lo + 1) % (n);
+      32             : }
+      33             : 
+      34             : /** grid index in a reflective continued unit grid */
+      35             : inline int reflectiveBoundary(int index, int n) {
+      36        1963 :         while ((index < -0.5) or (index > (n-0.5)))
+      37         806 :                 index = 2 * n * (index > (n-0.5)) - index-1;
+      38             :         return index;
+      39             : }
+      40             : 
+      41             : /** grid index in a periodically continued unit grid */
+      42             : inline int periodicBoundary(int index, int n) {
+      43         768 :         return ((index % (n)) + (n)) % (n);
+      44             : }
+      45             : 
+      46             : /** Lower and upper neighbour in a reflectively repeated unit grid */
+      47          20 : inline void reflectiveClamp(double x, int n, int &lo, int &hi, double &res) {
+      48          36 :         while ((x < -0.5) or (x > (n-0.5)))
+      49          16 :                 x = 2 * n * (x > (n-0.5)) -x-1;
+      50          20 :         res = x;
+      51          20 :         lo = floor(x);
+      52          20 :         hi = lo + (lo < n-1);
+      53          20 :         if (x<0) {
+      54          10 :                 lo=0; 
+      55          10 :                 hi=0;
+      56             :         }
+      57          20 : }
+      58             : 
+      59             : /** Symmetrical round */
+      60          51 : inline double round(double r) {
+      61          51 :         return (r > 0.0) ? floor(r + 0.5) : ceil(r - 0.5);
+      62             : }
+      63             : 
+      64             : /**
+      65             :  * \addtogroup Core
+      66             :  * @{
+      67             :  */
+      68             : 
+      69             : /**
+      70             :  @class GridProperties
+      71             :  @brief Combines parameters that uniquely define Grid class
+      72             :  */
+      73             : class GridProperties: public Referenced {
+      74             : public:
+      75             :         size_t Nx, Ny, Nz;      // Number of grid points
+      76             :         Vector3d origin;        // Position of the lower left front corner of the volume
+      77             :         Vector3d spacing;       // Spacing vector between gridpoints
+      78             :         bool reflective;        // using reflective repetition of the grid instead of periodic
+      79             :         interpolationType ipol; // Interpolation type used between grid points
+      80             :         bool clipVolume;        // Set grid values to 0 outside the volume if true
+      81             : 
+      82             :         /** Constructor for cubic grid
+      83             :          @param origin  Position of the lower left front corner of the volume
+      84             :          @param N               Number of grid points in one direction
+      85             :          @param spacing Spacing between grid points
+      86             :          */
+      87           6 :         GridProperties(Vector3d origin, size_t N, double spacing) :
+      88           6 :                 origin(origin), Nx(N), Ny(N), Nz(N), spacing(Vector3d(spacing)), reflective(false), ipol(TRILINEAR), clipVolume(false) {
+      89             :         }
+      90             : 
+      91             :         /** Constructor for non-cubic grid
+      92             :          @param origin  Position of the lower left front corner of the volume
+      93             :          @param Nx              Number of grid points in x-direction
+      94             :          @param Ny              Number of grid points in y-direction
+      95             :          @param Nz              Number of grid points in z-direction
+      96             :          @param spacing Spacing between grid points
+      97             :          */
+      98           0 :         GridProperties(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, double spacing) :
+      99           0 :                 origin(origin), Nx(Nx), Ny(Ny), Nz(Nz), spacing(Vector3d(spacing)), reflective(false), ipol(TRILINEAR), clipVolume(false) {
+     100             :         }
+     101             : 
+     102             :         /** Constructor for non-cubic grid with spacing vector
+     103             :          @param origin  Position of the lower left front corner of the volume
+     104             :          @param Nx              Number of grid points in x-direction
+     105             :          @param Ny              Number of grid points in y-direction
+     106             :          @param Nz              Number of grid points in z-direction
+     107             :          @param spacing Spacing vector between grid points
+     108             :         */
+     109           1 :         GridProperties(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, Vector3d spacing) :
+     110           1 :                 origin(origin), Nx(Nx), Ny(Ny), Nz(Nz), spacing(spacing), reflective(false), ipol(TRILINEAR), clipVolume(false) {
+     111             :         }
+     112             :         
+     113           2 :         virtual ~GridProperties() {
+     114           4 :         }
+     115             :         
+     116             :         /** If True, the repetition of the grid is refletive instead of periodic. */
+     117             :         void setReflective(bool b) {
+     118           0 :                 reflective = b;
+     119             :         }
+     120             : 
+     121             :         /** set the type of interpolation between grid points.
+     122             :          * @param i: interpolationType (TRILINEAR, TRICUBIC, NEAREST_NEIGHBOUR) */
+     123             :         void setInterpolationType(interpolationType i) {
+     124           0 :                 ipol = i;
+     125             :         }
+     126             : 
+     127             :         /** If True, the grid is set to zero outside of the volume. */
+     128             :         void setClipVolume(bool b) {
+     129           0 :                 clipVolume = b;
+     130             :         }
+     131             : };
+     132             : 
+     133             : /**
+     134             :  @class Grid
+     135             :  @brief Template class for fields on a periodic grid with trilinear interpolation
+     136             : 
+     137             :  The grid spacing is constant with diffrent resolution along all three axes.
+     138             :  Values are calculated by trilinear interpolation of the surrounding 8 grid points.
+     139             :  The grid is periodically (default) or reflectively extended.
+     140             :  The grid sample positions are at 1/2 * size/N, 3/2 * size/N ... (2N-1)/2 * size/N.
+     141             :  */
+     142             : template<typename T>
+     143          17 : class Grid: public Referenced {
+     144             :         std::vector<T> grid;
+     145             :         size_t Nx, Ny, Nz; /**< Number of grid points */
+     146             :         Vector3d origin; /**< Origin of the volume that is represented by the grid. */
+     147             :         Vector3d gridOrigin; /**< Grid origin */
+     148             :         Vector3d spacing; /**< Distance between grid points, determines the extension of the grid */
+     149             :         bool clipVolume; /**< If set to true, all values outside of the grid will be 0*/
+     150             :         bool reflective; /**< If set to true, the grid is repeated reflectively instead of periodically */
+     151             :         interpolationType ipolType; /**< Type of interpolation between the grid points */
+     152             : 
+     153             : public:
+     154             :         /** Constructor for cubic grid
+     155             :          @param origin  Position of the lower left front corner of the volume
+     156             :          @param N               Number of grid points in one direction
+     157             :          @param spacing Spacing between grid points
+     158             :          */
+     159          11 :         Grid(Vector3d origin, size_t N, double spacing) {
+     160             :                 setOrigin(origin);
+     161          11 :                 setGridSize(N, N, N);
+     162             :                 setSpacing(Vector3d(spacing));
+     163             :                 setReflective(false);
+     164             :                 setClipVolume(false);
+     165             :                 setInterpolationType(TRILINEAR);
+     166          11 :         }
+     167             : 
+     168             :         /** Constructor for non-cubic grid
+     169             :          @param origin  Position of the lower left front corner of the volume
+     170             :          @param Nx              Number of grid points in x-direction
+     171             :          @param Ny              Number of grid points in y-direction
+     172             :          @param Nz              Number of grid points in z-direction
+     173             :          @param spacing Spacing between grid points
+     174             :          */
+     175           7 :         Grid(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, double spacing) {
+     176             :                 setOrigin(origin);
+     177           7 :                 setGridSize(Nx, Ny, Nz);
+     178             :                 setSpacing(Vector3d(spacing));
+     179             :                 setReflective(false);
+     180             :                 setClipVolume(false);
+     181             :                 setInterpolationType(TRILINEAR);
+     182           7 :         }
+     183             : 
+     184             :         /** Constructor for non-cubic grid with spacing vector
+     185             :          @param origin  Position of the lower left front corner of the volume
+     186             :          @param Nx              Number of grid points in x-direction
+     187             :          @param Ny              Number of grid points in y-direction
+     188             :          @param Nz              Number of grid points in z-direction
+     189             :          @param spacing Spacing vector between grid points
+     190             :         */
+     191           1 :         Grid(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, Vector3d spacing) {
+     192             :                 setOrigin(origin);
+     193           1 :                 setGridSize(Nx, Ny, Nz);
+     194             :                 setSpacing(spacing);
+     195             :                 setReflective(false);
+     196             :                 setClipVolume(false);
+     197             :                 setInterpolationType(TRILINEAR);
+     198           1 :         }
+     199             : 
+     200             :         /** Constructor for GridProperties
+     201             :          @param p       GridProperties instance
+     202             :      */
+     203           9 :         Grid(const GridProperties &p) :
+     204           9 :                 origin(p.origin), spacing(p.spacing), reflective(p.reflective), ipolType(p.ipol) {
+     205           9 :                 setGridSize(p.Nx, p.Ny, p.Nz);
+     206           9 :                 setClipVolume(p.clipVolume);
+     207           9 :         }
+     208             : 
+     209             :         void setOrigin(Vector3d origin) {
+     210             :                 this->origin = origin;
+     211             :                 this->gridOrigin = origin + spacing/2;
+     212             :         }
+     213             : 
+     214             :         /** Resize grid, also enlarges the volume as the spacing stays constant */
+     215          28 :         void setGridSize(size_t Nx, size_t Ny, size_t Nz) {
+     216          28 :                 this->Nx = Nx;
+     217          28 :                 this->Ny = Ny;
+     218          28 :                 this->Nz = Nz;
+     219          28 :                 grid.resize(Nx * Ny * Nz);
+     220             :                 setOrigin(origin);
+     221          28 :         }
+     222             : 
+     223             :         void setSpacing(Vector3d spacing) {
+     224             :                 this->spacing = spacing;
+     225             :                 setOrigin(origin);
+     226             :         }
+     227             : 
+     228             :         void setReflective(bool b) {
+     229           8 :                 reflective = b;
+     230             :         }
+     231             : 
+     232             :         // If set to true, all values outside of the grid will be 0.
+     233             :         void setClipVolume(bool b) {
+     234          21 :                 clipVolume = b;
+     235             :         }
+     236             : 
+     237             :         /** Change the interpolation type to the routine specified by the user. Check if this routine is
+     238             :                 contained in the enum interpolationType and thus supported by CRPropa.*/
+     239           0 :         void setInterpolationType(interpolationType ipolType) {
+     240           0 :                 if (ipolType == TRILINEAR || ipolType == TRICUBIC || ipolType == NEAREST_NEIGHBOUR) {
+     241          30 :                         this->ipolType = ipolType;
+     242           0 :                         if ((ipolType == TRICUBIC) && (std::is_same<T, Vector3d>::value)) {
+     243           0 :                                 KISS_LOG_WARNING << "Tricubic interpolation on Grid3d works only with float-precision, doubles will be downcasted";
+     244             :                 }
+     245             :                 } else {
+     246           0 :                         throw std::runtime_error("InterpolationType: unknown interpolation type");
+     247             :                 }
+     248           0 :         }
+     249             : 
+     250             :         /** returns the position of the lower left front corner of the volume */
+     251             :         Vector3d getOrigin() const {
+     252             :                 return origin;
+     253             :         }
+     254             : 
+     255             :         bool getClipVolume() const {
+     256           0 :                 return clipVolume;
+     257             :         }
+     258             : 
+     259             :         size_t getNx() const {
+     260         728 :                 return Nx;
+     261             :         }
+     262             : 
+     263             :         size_t getNy() const {
+     264       41792 :                 return Ny;
+     265             :         }
+     266             : 
+     267             :         size_t getNz() const {
+     268     2663721 :                 return Nz;
+     269             :         }
+     270             : 
+     271             :         /** Calculates the total size of the grid in bytes */
+     272             :         size_t getSizeOf() const {
+     273           0 :                 return sizeof(grid) + (sizeof(grid[0]) * grid.size());
+     274             :         }
+     275             : 
+     276             :         Vector3d getSpacing() const {
+     277             :                 return spacing;
+     278             :         }
+     279             : 
+     280             :         bool isReflective() const {
+     281           0 :                 return reflective;
+     282             :         }
+     283             : 
+     284             :         /** Choose the interpolation algorithm based on the set interpolation type.
+     285             :           By default this it the trilinear interpolation. The user can change the
+     286             :           routine with the setInterpolationType function.*/
+     287      100091 :         T interpolate(const Vector3d &position) {
+     288             :                 // check for volume
+     289      100091 :                 if (clipVolume) {
+     290           5 :                         Vector3d edge = origin + Vector3d(Nx, Ny, Nz) * spacing;
+     291           5 :                         bool isInVolume = (position.x >= origin.x) && (position.x <= edge.x);
+     292           5 :                         isInVolume &= (position.y >= origin.y) && (position.y <= edge.y);
+     293           5 :                         isInVolume &= (position.z >= origin.z) && (position.z <= edge.z);
+     294           5 :                         if (!isInVolume) 
+     295             :                                 return T(0.);
+     296             :                 } 
+     297             : 
+     298      100086 :                 if (ipolType == TRICUBIC)
+     299          18 :                         return tricubicInterpolate(T(), position);
+     300      100068 :                 else if (ipolType == NEAREST_NEIGHBOUR)
+     301          13 :                         return closestValue(position);
+     302             :                 else
+     303      100055 :                         return trilinearInterpolate(position);
+     304             :         }
+     305             : 
+     306             :         /** Inspector & Mutator */
+     307             :         T &get(size_t ix, size_t iy, size_t iz) {
+     308     8391022 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
+     309             :         }
+     310             : 
+     311             :         /** Inspector */
+     312             :         const T &get(size_t ix, size_t iy, size_t iz) const {
+     313      100072 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
+     314             :         }
+     315             : 
+     316             :         const T &periodicGet(size_t ix, size_t iy, size_t iz) const {
+     317         192 :                 ix = periodicBoundary(ix, Nx);
+     318         192 :                 iy = periodicBoundary(iy, Ny);
+     319         192 :                 iz = periodicBoundary(iz, Nz);
+     320         192 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
+     321             :         }
+     322             : 
+     323           0 :         const T &reflectiveGet(size_t ix, size_t iy, size_t iz) const {
+     324           0 :                 ix = reflectiveBoundary(ix, Nx);
+     325           0 :                 iy = reflectiveBoundary(iy, Ny);
+     326           0 :                 iz = reflectiveBoundary(iz, Nz);
+     327           0 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
+     328             :         }
+     329             : 
+     330             :         T getValue(size_t ix, size_t iy, size_t iz) {
+     331           0 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
+     332             :         }
+     333             : 
+     334             :         void setValue(size_t ix, size_t iy, size_t iz, T value) {
+     335           0 :                 grid[ix * Ny * Nz + iy * Nz + iz] = value;
+     336             :         }
+     337             : 
+     338             :         /** Return a reference to the grid values */
+     339             :         std::vector<T> &getGrid() {
+     340       10102 :                 return grid;
+     341             :         }
+     342             : 
+     343             :         /** Position of the grid point of a given index */
+     344       10103 :         Vector3d positionFromIndex(int index) const {
+     345       10103 :                 int ix = index / (Ny * Nz);
+     346       10103 :                 int iy = (index / Nz) % Ny;
+     347       10103 :                 int iz = index % Nz;
+     348       10103 :                 return Vector3d(ix, iy, iz) * spacing + gridOrigin;
+     349             :         }
+     350             : 
+     351             :         /** Value of a grid point that is closest to a given position / nearest neighbour interpolation */
+     352          17 :         T closestValue(const Vector3d &position) const {
+     353             :                 Vector3d r = (position - gridOrigin) / spacing;
+     354             :                 int ix, iy, iz;
+     355          17 :                 if (reflective) {
+     356           6 :                         ix = round(r.x);
+     357           6 :                         iy = round(r.y);
+     358           6 :                         iz = round(r.z);
+     359           9 :                         while ((ix < -0.5) or (ix > (Nx-0.5)))
+     360           3 :                                 ix = 2 * Nx * (ix > (Nx-0.5)) - ix-1;
+     361          11 :                         while ((iy < -0.5) or (iy > (Ny-0.5)))
+     362           5 :                                 iy = 2 * Ny * (iy > (Ny-0.5)) - iy-1;
+     363           9 :                         while ((iz < -0.5) or (iz > (Nz-0.5)))
+     364           3 :                                 iz = 2 * Nz * (iz > (Nz-0.5)) - iz-1;
+     365             :                 } else {
+     366          11 :                         ix = round(fmod(r.x, Nx));
+     367          11 :                         iy = round(fmod(r.y, Ny));
+     368          11 :                         iz = round(fmod(r.z, Nz));
+     369          11 :                         ix = (ix + Nx * (ix < 0)) % Nx;
+     370          11 :                         iy = (iy + Ny * (iy < 0)) % Ny;
+     371          11 :                         iz = (iz + Nz * (iz < 0)) % Nz;
+     372             :                 }
+     373          17 :                 return get(ix, iy, iz);
+     374             :         }
+     375             : 
+     376             : private:
+     377             :         #ifdef HAVE_SIMD
+     378             :         __m128 simdperiodicGet(size_t ix, size_t iy, size_t iz) const {
+     379         576 :                 ix = periodicBoundary(ix, Nx);
+     380         576 :                 iy = periodicBoundary(iy, Ny);
+     381         576 :                 iz = periodicBoundary(iz, Nz);
+     382         576 :                 return convertVector3fToSimd(grid[ix * Ny * Nz + iy * Nz + iz]);
+     383             :         }
+     384             : 
+     385         384 :         __m128 simdreflectiveGet(size_t ix, size_t iy, size_t iz) const {
+     386         384 :                 ix = reflectiveBoundary(ix, Nx);
+     387         384 :                 iy = reflectiveBoundary(iy, Ny);
+     388         384 :                 iz = reflectiveBoundary(iz, Nz);
+     389         384 :                 return convertVector3fToSimd(grid[ix * Ny * Nz + iy * Nz + iz]);
+     390             :         }
+     391             : 
+     392             :         __m128 convertVector3fToSimd(const Vector3f v) const {
+     393             :                 __m128 simdVar = _mm_set_ps(0,v.z,v.y,v.x);
+     394             :                 return simdVar;
+     395             :         }
+     396             :         
+     397             :         Vector3f convertSimdToVector3f(__m128 res) const {
+     398             :                 float vec[4];   
+     399             :                 _mm_store_ps(&vec[0], res);
+     400             :                 Vector3f result = Vector3f(vec[0], vec[1], vec[2]);
+     401             :                 return result;
+     402             :         }
+     403             : 
+     404             :         /** Vectorized cubic Interpolator in 1D */
+     405             :         __m128 CubicInterpolate(__m128 p0,__m128 p1,__m128 p2,__m128 p3,double position) const {
+     406             :                 __m128 c1 = _mm_set1_ps (1/2.);
+     407             :                 __m128 c2 = _mm_set1_ps (3/2.);
+     408             :                 __m128 c3 = _mm_set1_ps (2.);
+     409             :                 __m128 c4 = _mm_set1_ps (5/2.);
+     410             : 
+     411         315 :                 __m128 pos  = _mm_set1_ps (position);
+     412         315 :                 __m128 pos2 = _mm_set1_ps (position*position);
+     413         300 :                 __m128 pos3 = _mm_set1_ps (position*position*position);
+     414             : 
+     415             :                 /** SIMD optimized routine to calculate 'res = ((-0.5*p0+3/2.*p1-3/2.*p2+0.5*p3)*pos*pos*pos+(p0-5/2.*p1+p2*2-0.5*p3)*pos*pos+(-0.5*p0+0.5*p2)*pos+p1);'
+     416             :                          where terms are used as:
+     417             :                         term = (-0.5*p0+0.5*p2)*pos
+     418             :                         term2 = (p0-5/2.*p1+p2*2-0.5*p3)*pos*pos;
+     419             :                         term3 = (-0.5*p0+3/2.*p1-3/2.*p2+0.5*p3)*pos*pos*pos;  */
+     420             :                 __m128 term = _mm_mul_ps(_mm_sub_ps(_mm_mul_ps(c1,p2),_mm_mul_ps(c1,p0)),pos);
+     421             :                 __m128 term2 = _mm_mul_ps(_mm_sub_ps(_mm_add_ps(p0,_mm_mul_ps(c3,p2)),_mm_add_ps(_mm_mul_ps(c4,p1),_mm_mul_ps(c1,p3))),pos2);
+     422             :                 __m128 term3 = _mm_mul_ps(_mm_sub_ps(_mm_add_ps(_mm_mul_ps(c2,p1),_mm_mul_ps(c1,p3)),_mm_add_ps(_mm_mul_ps(c1,p0),_mm_mul_ps(c2,p2))),pos3);
+     423             :                 __m128 res = _mm_add_ps(_mm_add_ps(_mm_add_ps(term3,term2),term),p1);
+     424             :                 return res;
+     425             :         }
+     426             :         #endif // HAVE_SIMD
+     427             :         /** Interpolate the grid tricubic at a given position (see https://www.paulinternet.nl/?page=bicubic, http://graphics.cs.cmu.edu/nsp/course/15-462/Fall04/assts/catmullRom.pdf) */
+     428          15 :         Vector3f tricubicInterpolate(Vector3f, const Vector3d &position) const {
+     429             :                 #ifdef HAVE_SIMD
+     430             :                 // position on a unit grid
+     431             :                 Vector3d r = (position - gridOrigin) / spacing;
+     432             : 
+     433             :                 int iX0, iY0, iZ0;
+     434          15 :                 iX0 = floor(r.x);
+     435          15 :                 iY0 = floor(r.y);
+     436          15 :                 iZ0 = floor(r.z);
+     437             : 
+     438             :                 double fX, fY, fZ;
+     439          15 :                 fX = r.x - iX0;
+     440          15 :                 fY = r.y - iY0;
+     441          15 :                 fZ = r.z - iZ0;
+     442             : 
+     443             :                 int nrCubicInterpolations = 4;
+     444          15 :                 __m128 interpolateVaryX[nrCubicInterpolations];
+     445          15 :                 __m128 interpolateVaryY[nrCubicInterpolations];
+     446          15 :                 __m128 interpolateVaryZ[nrCubicInterpolations];
+     447             :                 /** Perform 1D interpolations while iterating in each for loop over the index of another direction */
+     448          75 :                 for (int iLoopX = -1; iLoopX < nrCubicInterpolations-1; iLoopX++) {
+     449         300 :                         for (int iLoopY = -1; iLoopY < nrCubicInterpolations-1; iLoopY++) {
+     450        1200 :                                 for (int iLoopZ = -1; iLoopZ < nrCubicInterpolations-1; iLoopZ++) {
+     451         960 :                                         if (reflective)
+     452         384 :                                                 interpolateVaryZ[iLoopZ+1] = simdreflectiveGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
+     453             :                                         else 
+     454         576 :                                                 interpolateVaryZ[iLoopZ+1] = simdperiodicGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
+     455             :                                 }
+     456         240 :                                 interpolateVaryY[iLoopY+1] = CubicInterpolate(interpolateVaryZ[0], interpolateVaryZ[1], interpolateVaryZ[2], interpolateVaryZ[3], fZ);
+     457             :                         }
+     458          60 :                         interpolateVaryX[iLoopX+1] = CubicInterpolate(interpolateVaryY[0], interpolateVaryY[1], interpolateVaryY[2], interpolateVaryY[3], fY);
+     459             :                 }
+     460          15 :                 __m128 result = CubicInterpolate(interpolateVaryX[0], interpolateVaryX[1], interpolateVaryX[2], interpolateVaryX[3], fX);
+     461          15 :                 return convertSimdToVector3f(result);
+     462             :                 #else // HAVE_SIMD
+     463             :                 throw std::runtime_error( "Tried to use tricubic Interpolation without SIMD_EXTENSION. SIMD Optimization is necessary for tricubic interpolation of vector grids.\n");
+     464             :                 #endif // HAVE_SIMD     
+     465          15 :         }
+     466             : 
+     467             :         /** Vectorized cubic Interpolator in 1D that returns a scalar (see https://www.paulinternet.nl/?page=bicubic, http://graphics.cs.cmu.edu/nsp/course/15-462/Fall04/assts/catmullRom.pdf) */
+     468          63 :         double CubicInterpolateScalar(double p0,double p1,double p2,double p3,double pos) const {
+     469          63 :                 return((-0.5*p0+3/2.*p1-3/2.*p2+0.5*p3)*pos*pos*pos+(p0-5/2.*p1+p2*2-0.5*p3)*pos*pos+(-0.5*p0+0.5*p2)*pos+p1);
+     470             :         }
+     471             : 
+     472             :   /** Interpolate the grid tricubic at a given position (see https://www.paulinternet.nl/?page=bicubic, http://graphics.cs.cmu.edu/nsp/course/15-462/Fall04/assts/catmullRom.pdf) */
+     473           3 :         double tricubicInterpolate(double, const Vector3d &position) const {
+     474             :                 /** position on a unit grid */
+     475             :                 Vector3d r = (position - gridOrigin) / spacing;
+     476             : 
+     477             :                 int iX0, iY0, iZ0;
+     478           3 :                 iX0 = floor(r.x);
+     479           3 :                 iY0 = floor(r.y);
+     480           3 :                 iZ0 = floor(r.z);
+     481             : 
+     482             :                 double fX, fY, fZ;
+     483           3 :                 fX = r.x - iX0;
+     484           3 :                 fY = r.y - iY0;
+     485           3 :                 fZ = r.z - iZ0;
+     486             : 
+     487             :                 int nrCubicInterpolations = 4;
+     488           3 :                 double interpolateVaryX[nrCubicInterpolations];
+     489           3 :                 double interpolateVaryY[nrCubicInterpolations];
+     490           3 :                 double interpolateVaryZ[nrCubicInterpolations];
+     491             :                 /** Perform 1D interpolations while iterating in each for loop over the index of another direction */
+     492          15 :                 for (int iLoopX = -1; iLoopX < nrCubicInterpolations-1; iLoopX++) {
+     493          60 :                         for (int iLoopY = -1; iLoopY < nrCubicInterpolations-1; iLoopY++) {
+     494         240 :                                 for (int iLoopZ = -1; iLoopZ < nrCubicInterpolations-1; iLoopZ++) {
+     495         192 :                                         if (reflective)
+     496           0 :                                                 interpolateVaryZ[iLoopZ+1] = reflectiveGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
+     497             :                                         else
+     498         192 :                                                 interpolateVaryZ[iLoopZ+1] = periodicGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
+     499             :                                 }
+     500          48 :                                 interpolateVaryY[iLoopY+1] = CubicInterpolateScalar(interpolateVaryZ[0], interpolateVaryZ[1], interpolateVaryZ[2], interpolateVaryZ[3], fZ);
+     501             :                         }
+     502          12 :                         interpolateVaryX[iLoopX+1] = CubicInterpolateScalar(interpolateVaryY[0], interpolateVaryY[1], interpolateVaryY[2], interpolateVaryY[3], fY);
+     503             :                 }
+     504           3 :                 double result = CubicInterpolateScalar(interpolateVaryX[0], interpolateVaryX[1], interpolateVaryX[2], interpolateVaryX[3], fX);
+     505           3 :                 return result;
+     506           3 :         }
+     507             : 
+     508             :         /** Interpolate the grid trilinear at a given position */
+     509      100055 :         T trilinearInterpolate(const Vector3d &position) const {
+     510             :                 /** position on a unit grid */
+     511             :                 Vector3d r = (position - gridOrigin) / spacing;
+     512             : 
+     513             :                 /** indices of lower (0) and upper (1) neighbours. The neighbours span a grid
+     514             :                   with the origin at [iX0, iY0, iZ0] and the most distant corner [iX1, iY1, iZ1]. */
+     515             :                 int iX0, iX1, iY0, iY1, iZ0, iZ1;
+     516             :                 double resX, resY, resZ, fX0, fY0, fZ0;
+     517             : 
+     518      100055 :                 if (reflective) {
+     519           6 :                         reflectiveClamp(r.x, Nx, iX0, iX1, resX);
+     520           6 :                         reflectiveClamp(r.y, Ny, iY0, iY1, resY);
+     521           6 :                         reflectiveClamp(r.z, Nz, iZ0, iZ1, resZ);
+     522           6 :                         fX0 = resX - floor(resX);
+     523           6 :                         fY0 = resY - floor(resY);
+     524           6 :                         fZ0 = resZ - floor(resZ);
+     525             :                 } else {
+     526      100049 :                         periodicClamp(r.x, Nx, iX0, iX1);
+     527      100049 :                         periodicClamp(r.y, Ny, iY0, iY1);
+     528      100049 :                         periodicClamp(r.z, Nz, iZ0, iZ1);
+     529      100049 :                         fX0 = r.x - floor(r.x);
+     530      100049 :                         fY0 = r.y - floor(r.y);
+     531      100049 :                         fZ0 = r.z - floor(r.z);
+     532             :                 }
+     533             : 
+     534             :                 /** linear fraction to upper neighbours based on lower neighbours calculated above */
+     535      100055 :                 double fX1 = 1 - fX0;
+     536      100055 :                 double fY1 = 1 - fY0;
+     537      100055 :                 double fZ1 = 1 - fZ0;
+     538             : 
+     539             :                 /** trilinear interpolation (see http://paulbourke.net/miscellaneous/interpolation) */
+     540             :                 T b(0.);
+     541      100055 :                 b += get(iX0, iY0, iZ0) * fX1 * fY1 * fZ1;
+     542      100055 :                 b += get(iX1, iY0, iZ0) * fX0 * fY1 * fZ1;
+     543      100055 :                 b += get(iX0, iY1, iZ0) * fX1 * fY0 * fZ1;
+     544      100055 :                 b += get(iX0, iY0, iZ1) * fX1 * fY1 * fZ0;
+     545           9 :                 b += get(iX1, iY0, iZ1) * fX0 * fY1 * fZ0;
+     546           9 :                 b += get(iX0, iY1, iZ1) * fX1 * fY0 * fZ0;
+     547           9 :                 b += get(iX1, iY1, iZ0) * fX0 * fY0 * fZ1;
+     548           9 :                 b += get(iX1, iY1, iZ1) * fX0 * fY0 * fZ0;
+     549             : 
+     550      100055 :                 return b;
+     551             :         }
+     552             : 
+     553             : }; // class Grid
+     554             : 
+     555             : typedef Grid<double> Grid1d;
+     556             : typedef Grid<float> Grid1f;
+     557             : typedef Grid<Vector3f> Grid3f;
+     558             : typedef Grid<Vector3d> Grid3d;
+     559             : 
+     560             : /** @}*/
+     561             : 
+     562             : } // namespace crpropa
+     563             : 
+     564             : #endif // CRPROPA_GRID_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html new file mode 100644 index 000000000..df316be7f --- /dev/null +++ b/doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Logging.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Logging.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0180.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_Z10logWarningRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z11setLogLeveli0
_Z12setLogStreamRSo0
_Z7logInfoRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logDebugRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logErrorRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Logging.h.func.html b/doc/coverageReport/include/crpropa/Logging.h.func.html new file mode 100644 index 000000000..118e0b0b8 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Logging.h.func.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Logging.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Logging.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0180.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_Z10logWarningRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z11setLogLeveli0
_Z12setLogStreamRSo0
_Z7logInfoRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logDebugRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logErrorRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Logging.h.gcov.html b/doc/coverageReport/include/crpropa/Logging.h.gcov.html new file mode 100644 index 000000000..adb602fd6 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Logging.h.gcov.html @@ -0,0 +1,111 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Logging.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Logging.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0180.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_LOGGING_H
+       2             : #define CRPROPA_LOGGING_H
+       3             : 
+       4             : #include "crpropa/Version.h"
+       5             : 
+       6             : #include "kiss/logger.h"
+       7             : 
+       8             : #include <fstream>
+       9             : 
+      10             : // make the kiss log functions available in python
+      11           0 : void inline logError(const std::string &log) {
+      12           0 :         KISS_LOG_ERROR << log;
+      13           0 : }
+      14             : 
+      15           0 : void inline logInfo(const std::string &log) {
+      16           0 :         KISS_LOG_INFO << log;
+      17           0 : }
+      18             : 
+      19           0 : void inline logWarning(const std::string &log) {
+      20           0 :         KISS_LOG_WARNING << log;
+      21           0 : }
+      22             : 
+      23           0 : void inline logDebug(const std::string &log) {
+      24           0 :         KISS_LOG_DEBUG << log;
+      25           0 : }
+      26             : 
+      27           0 : void setLogStream(std::ostream &stream) {
+      28           0 :         kiss::Logger::setLogStream(stream);
+      29           0 : }
+      30             : 
+      31           0 : void setLogLevel(int level) {
+      32           0 :         kiss::Logger::setLogLevel(static_cast<kiss::eLogLevel>(level));
+      33           0 : }
+      34             : 
+      35             : #endif // CRPROPA_LOGGING_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Module.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Module.h.func-sort-c.html new file mode 100644 index 000000000..33e798596 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Module.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Module.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Module.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2825.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Module.h.func.html b/doc/coverageReport/include/crpropa/Module.h.func.html new file mode 100644 index 000000000..1d53a83bf --- /dev/null +++ b/doc/coverageReport/include/crpropa/Module.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Module.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Module.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2825.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Module.h.gcov.html b/doc/coverageReport/include/crpropa/Module.h.gcov.html new file mode 100644 index 000000000..be630b8ed --- /dev/null +++ b/doc/coverageReport/include/crpropa/Module.h.gcov.html @@ -0,0 +1,141 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Module.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Module.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2825.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_MODULE_H
+       2             : #define CRPROPA_MODULE_H
+       3             : 
+       4             : #include "crpropa/Candidate.h"
+       5             : #include "crpropa/Referenced.h"
+       6             : #include "crpropa/Common.h"
+       7             : 
+       8             : #include <string>
+       9             : 
+      10             : namespace crpropa {
+      11             : 
+      12             : class Candidate;
+      13             : 
+      14             : /**
+      15             :  @class Module
+      16             :  @brief Abstract base class for modules
+      17             :  */
+      18             : class Module: public Referenced {
+      19             :         std::string description;
+      20             : public:
+      21             :         Module();
+      22          37 :         virtual ~Module() {
+      23           4 :         }
+      24             :         virtual std::string getDescription() const;
+      25             :         void setDescription(const std::string &description);
+      26             :         virtual void process(Candidate *candidate) const = 0;
+      27             :         inline void process(ref_ptr<Candidate> candidate) const {
+      28           0 :                 process(candidate.get());
+      29           0 :         }
+      30             : };
+      31             : 
+      32             : 
+      33             : /**
+      34             :  @class AbstractCondition
+      35             :  @brief Abstract Module providing common features for conditional modules.
+      36             :  */
+      37             : class AbstractCondition: public Module {
+      38             : protected:
+      39             :         ref_ptr<Module> rejectAction, acceptAction;
+      40             :         bool makeRejectedInactive, makeAcceptedInactive;
+      41             :         std::string rejectFlagKey, rejectFlagValue;
+      42             :         std::string acceptFlagKey, acceptFlagValue;
+      43             : 
+      44             :         void reject(Candidate *candidate) const;
+      45             :         inline void reject(ref_ptr<Candidate> candidate) const {
+      46           0 :                 reject(candidate.get());
+      47           0 :         }
+      48             : 
+      49             :         void accept(Candidate *candidate) const;
+      50             :         inline void accept(ref_ptr<Candidate> candidate) const {
+      51           0 :                 accept(candidate.get());
+      52           0 :         }
+      53             : 
+      54             : public:
+      55             :         AbstractCondition();
+      56             :         void onReject(Module *rejectAction);
+      57             :         void onAccept(Module *acceptAction);
+      58             :         void setMakeRejectedInactive(bool makeInactive);
+      59             :         void setMakeAcceptedInactive(bool makeInactive);
+      60             :         void setRejectFlag(std::string key, std::string value);
+      61             :         void setAcceptFlag(std::string key, std::string value);
+      62             : };
+      63             : } // namespace crpropa
+      64             : 
+      65             : #endif /* CRPROPA_MODULE_H */
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html b/doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html new file mode 100644 index 000000000..71558e0b3 --- /dev/null +++ b/doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/ParticleState.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - ParticleState.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/ParticleState.h.func.html b/doc/coverageReport/include/crpropa/ParticleState.h.func.html new file mode 100644 index 000000000..0ff39823d --- /dev/null +++ b/doc/coverageReport/include/crpropa/ParticleState.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/ParticleState.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - ParticleState.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/ParticleState.h.gcov.html b/doc/coverageReport/include/crpropa/ParticleState.h.gcov.html new file mode 100644 index 000000000..3c2bcfa41 --- /dev/null +++ b/doc/coverageReport/include/crpropa/ParticleState.h.gcov.html @@ -0,0 +1,196 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/ParticleState.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - ParticleState.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_PARTICLE_STATE_H
+       2             : #define CRPROPA_PARTICLE_STATE_H
+       3             : 
+       4             : #include "crpropa/Vector3.h"
+       5             : 
+       6             : namespace crpropa {
+       7             : /**
+       8             :  * \addtogroup Core
+       9             :  * @{
+      10             :  */
+      11             : 
+      12             : /**
+      13             :  @class ParticleState
+      14             :  @brief State of the particle: ID, energy, position, direction
+      15             : 
+      16             :  The ParticleState defines the state of an ultra-high energy cosmic ray, which
+      17             :  is assumed to be traveling at the exact speed of light.
+      18             :  The cosmic ray state is defined by particle ID, energy and position and
+      19             :  direction vector.
+      20             :  For faster lookup mass and charge of the particle are stored as members.
+      21             :  */
+      22     7199005 : class ParticleState {
+      23             : private:
+      24             :         int id; ///< particle ID (Particle Data Group numbering scheme)
+      25             :         double energy; ///< total energy
+      26             :         Vector3d position; ///< position vector in comoving coordinates
+      27             :         Vector3d direction; ///< unit vector of velocity or momentum
+      28             :         double pmass; ///< particle rest mass
+      29             :         double charge; ///< particle charge
+      30             : 
+      31             : public:
+      32             :         /** Constructor for a particle state.
+      33             :          @param id                      id of the particle following the PDG numbering scheme
+      34             :          @param energy          energy of the particle [in Joules]
+      35             :          @param position        vector containing the coordinates of the particle [in meters]
+      36             :          @param direction       vector containing the direction of motion of the particle
+      37             :          */
+      38             :         ParticleState(int id = 0, double energy = 0,
+      39             :                         Vector3d position = Vector3d(0, 0, 0),
+      40             :                         Vector3d direction = Vector3d(-1, 0, 0));
+      41             : 
+      42             :         /** Set particle position.
+      43             :          In simulations including cosmological effects, the position is given in comoving coordinates.
+      44             :          @param pos             vector containing the coordinates of the particle [in meters]
+      45             :         */
+      46             :         void setPosition(const Vector3d &pos);
+      47             :         /** Get position of particle.
+      48             :          @returns Position vector of particle. If cosmological effects are included, the coordinates are comoving.
+      49             :          */
+      50             :         const Vector3d &getPosition() const;
+      51             : 
+      52             :         /** Set direction unit vector, non unit-vectors are normalized
+      53             :          @param dir     vector containing the direction of motion of the particle
+      54             :          */
+      55             :         void setDirection(const Vector3d &dir);
+      56             :         /** Get direction unit vector
+      57             :          @returns Normalized vector containing direction of motion of particle.
+      58             :          */
+      59             :         const Vector3d &getDirection() const;
+      60             : 
+      61             :         /** Set energy of particle.
+      62             :          @param newEnergy       energy to be assigned to particle [in Joules]
+      63             :          */
+      64             :         void setEnergy(double newEnergy);
+      65             :         /** Get energy of particle.
+      66             :          @returns Energy of particle [in Joules]
+      67             :          */
+      68             :         double getEnergy() const;
+      69             :         /** Get rigidity of particle, defined as E/(Z*e).
+      70             :          @returns Rigidity of the particle [in Volts]
+      71             :          */
+      72             :         double getRigidity() const;
+      73             : 
+      74             :         /** Set particle ID.
+      75             :          This follows the PDG numbering scheme:
+      76             :           https://pdg.lbl.gov/2019/reviews/rpp2019-rev-monte-carlo-numbering.pdf
+      77             :          @param newId           id to be assigned to the particle 
+      78             :          */
+      79             :         void setId(int newId);
+      80             :         /** Get particle ID
+      81             :          @returns Particle ID (in PDG format).
+      82             :          */
+      83             :         int getId() const;
+      84             : 
+      85             :         std::string getDescription() const;
+      86             : 
+      87             :         // ======== Helper methods ========
+      88             : 
+      89             :         /** Get electrical charge of the particle.
+      90             :          @returns Charge of the particle [in Coulombs]
+      91             :          */
+      92             :         double getCharge() const;
+      93             :         /** Get mass of the particle.
+      94             :          @returns Mass of the particle [kg]
+      95             :          */
+      96             :         double getMass() const;
+      97             : 
+      98             :         /** Set Lorentz factor and modify the particle's energy accordingly.
+      99             :          @param gamma           Lorentz factor
+     100             :          */
+     101             :         void setLorentzFactor(double gamma);
+     102             :         /** Get Lorentz factor
+     103             :          @returns Lorentz factor of particle
+     104             :          */
+     105             :         double getLorentzFactor() const;
+     106             : 
+     107             :         /** Get velocity: direction times the speed of light.
+     108             :          @returns Velocity of particle [m/s]
+     109             :          */
+     110             :         Vector3d getVelocity() const;
+     111             :         /** Get momentum: direction times energy divided by the speed of light 
+     112             :          @returns The momentum [kg m/s]
+     113             :         */
+     114             :         Vector3d getMomentum() const;
+     115             : };
+     116             : /** @}*/
+     117             : 
+     118             : } // namespace crpropa
+     119             : 
+     120             : #endif // CRPROPA_PARTICLE_STATE_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html b/doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html new file mode 100644 index 000000000..167da8226 --- /dev/null +++ b/doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/PhotonBackground.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - PhotonBackground.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:222781.5 %
Date:2024-04-08 14:58:22Functions:171989.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19IRB_Saldana21_lowerC2Ev0
_ZN7crpropa19IRB_Saldana21_upperC2Ev0
_ZN7crpropa12URB_Fixsen11C2Ev4
_ZN7crpropa13IRB_Saldana21C2Ev4
_ZN7crpropa15URB_Protheroe96C2Ev6
_ZN7crpropa11IRB_Finke10C2Ev7
_ZN7crpropa11IRB_Finke22C2Ev7
_ZN7crpropa13IRB_Gilmore12C2Ev7
_ZN7crpropa13IRB_Stecker05C2Ev7
_ZN7crpropa15IRB_Dominguez11C2Ev7
_ZN7crpropa18IRB_Franceschini08C2Ev7
_ZN7crpropa19IRB_Stecker16_lowerC2Ev7
_ZN7crpropa19IRB_Stecker16_upperC2Ev7
_ZN7crpropa10URB_Nitu21C2Ev11
_ZN7crpropa13IRB_Kneiske04C2Ev13
_ZN7crpropa3CMBC2Ev40
_ZN7crpropa11PhotonFieldC2Ev135
_ZNK7crpropa11PhotonField12getFieldNameB5cxx11Ev175
_ZNK7crpropa11PhotonField18getRedshiftScalingEd16549
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/PhotonBackground.h.func.html b/doc/coverageReport/include/crpropa/PhotonBackground.h.func.html new file mode 100644 index 000000000..f8d9a9eee --- /dev/null +++ b/doc/coverageReport/include/crpropa/PhotonBackground.h.func.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/PhotonBackground.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - PhotonBackground.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:222781.5 %
Date:2024-04-08 14:58:22Functions:171989.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10URB_Nitu21C2Ev11
_ZN7crpropa11IRB_Finke10C2Ev7
_ZN7crpropa11IRB_Finke22C2Ev7
_ZN7crpropa11PhotonFieldC2Ev135
_ZN7crpropa12URB_Fixsen11C2Ev4
_ZN7crpropa13IRB_Gilmore12C2Ev7
_ZN7crpropa13IRB_Kneiske04C2Ev13
_ZN7crpropa13IRB_Saldana21C2Ev4
_ZN7crpropa13IRB_Stecker05C2Ev7
_ZN7crpropa15IRB_Dominguez11C2Ev7
_ZN7crpropa15URB_Protheroe96C2Ev6
_ZN7crpropa18IRB_Franceschini08C2Ev7
_ZN7crpropa19IRB_Saldana21_lowerC2Ev0
_ZN7crpropa19IRB_Saldana21_upperC2Ev0
_ZN7crpropa19IRB_Stecker16_lowerC2Ev7
_ZN7crpropa19IRB_Stecker16_upperC2Ev7
_ZN7crpropa3CMBC2Ev40
_ZNK7crpropa11PhotonField12getFieldNameB5cxx11Ev175
_ZNK7crpropa11PhotonField18getRedshiftScalingEd16549
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html b/doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html new file mode 100644 index 000000000..0a582c195 --- /dev/null +++ b/doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html @@ -0,0 +1,398 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/PhotonBackground.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - PhotonBackground.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:222781.5 %
Date:2024-04-08 14:58:22Functions:171989.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_PHOTONBACKGROUND_H
+       2             : #define CRPROPA_PHOTONBACKGROUND_H
+       3             : 
+       4             : #include "crpropa/Common.h"
+       5             : #include "crpropa/Referenced.h"
+       6             : 
+       7             : #include <vector>
+       8             : #include <string>
+       9             : 
+      10             : namespace crpropa {
+      11             : /**
+      12             :  * \addtogroup PhotonFields
+      13             :  * @{
+      14             :  */
+      15             : 
+      16             : /**
+      17             :  @class PhotonField
+      18             :  @brief Abstract base class for photon fields.
+      19             :  */
+      20           1 : class PhotonField: public Referenced {
+      21             : public:
+      22         135 :         PhotonField() {
+      23             :                 this->fieldName = "AbstractPhotonField";
+      24         135 :                 this->isRedshiftDependent = false;
+      25         135 :         }
+      26             : 
+      27             :         /**
+      28             :          returns comoving photon density [1/m^3].
+      29             :          multiply with (1+z^3) for physical number density.
+      30             :          @param ePhoton         photon energy [J]
+      31             :          @param z                       redshift (if redshift dependent, default = 0.)
+      32             :          */
+      33             :         virtual double getPhotonDensity(double ePhoton, double z = 0.) const = 0;
+      34             :         virtual double getMinimumPhotonEnergy(double z) const = 0;
+      35             :         virtual double getMaximumPhotonEnergy(double z) const = 0;
+      36         175 :         virtual std::string getFieldName() const {
+      37         175 :                 return this->fieldName;
+      38             :         }
+      39             : 
+      40             :         /**
+      41             :          returns overall comoving scaling factor
+      42             :          (cf. CRPropa3-data/calc_scaling.py)
+      43             :          @param z               redshift
+      44             :          */
+      45       16549 :         virtual double getRedshiftScaling(double z) const {
+      46       16549 :                 return 1.;
+      47             :         };
+      48             : 
+      49             :         bool hasRedshiftDependence() const {
+      50           0 :                 return this->isRedshiftDependent;
+      51             :         }
+      52             : 
+      53             :         void setFieldName(std::string fieldName) {
+      54           0 :                 this->fieldName = fieldName;
+      55           0 :         }
+      56             : 
+      57             : protected:
+      58             :         std::string fieldName;
+      59             :         bool isRedshiftDependent;
+      60             : };
+      61             : 
+      62             : /**
+      63             :  @class TabularPhotonField
+      64             :  @brief Photon field decorator for tabulated photon fields.
+      65             : 
+      66             :  This class reads photon field data from files;
+      67             :  The first file must be a list of photon energies [J], named fieldName_photonEnergy.txt
+      68             :  The second file must be a list of comoving photon field densities [1/m^3], named fieldName_photonDensity.txt
+      69             :  Optionally, a third file contains redshifts, named fieldName_redshift.txt
+      70             :  */
+      71             : class TabularPhotonField: public PhotonField {
+      72             : public:
+      73             :         TabularPhotonField(const std::string fieldName, const bool isRedshiftDependent = true);
+      74             : 
+      75             :         double getPhotonDensity(double ePhoton, double z = 0.) const;
+      76             :         double getRedshiftScaling(double z) const;
+      77             :         double getMinimumPhotonEnergy(double z) const;
+      78             :         double getMaximumPhotonEnergy(double z) const;
+      79             : 
+      80             : protected:
+      81             :         void readPhotonEnergy(std::string filePath);
+      82             :         void readPhotonDensity(std::string filePath);
+      83             :         void readRedshift(std::string filePath);
+      84             :         void initRedshiftScaling();
+      85             :         void checkInputData() const;
+      86             : 
+      87             :         std::vector<double> photonEnergies;
+      88             :         std::vector<double> photonDensity;
+      89             :         std::vector<double> redshifts;
+      90             :         std::vector<double> redshiftScalings;
+      91             : };
+      92             : 
+      93             : /**
+      94             :  @class IRB_Kneiske04
+      95             :  @brief Extragalactic background light model from Kneiske et al. 2004
+      96             : 
+      97             :  Source info:
+      98             :  DOI:10.1051/0004-6361:20031542,
+      99             :  https://www.aanda.org/articles/aa/pdf/2004/03/aa3848.pdf, figure 1 ("Best-fit" model)
+     100             :  */
+     101             : class IRB_Kneiske04: public TabularPhotonField {
+     102             : public:
+     103          26 :         IRB_Kneiske04() : TabularPhotonField("IRB_Kneiske04", true) {}
+     104             : };
+     105             : 
+     106             : /**
+     107             :  @class IRB_Stecker05
+     108             :  @brief Extragalactic background light model by Stecker at al. 2005
+     109             : 
+     110             :  Source info:
+     111             :  DOI:10.1086/506188, astro-ph/0510449
+     112             :  https://iopscience.iop.org/article/10.1086/506188/pdf
+     113             :  */
+     114             : class IRB_Stecker05: public TabularPhotonField {
+     115             : public:
+     116          14 :         IRB_Stecker05() : TabularPhotonField("IRB_Stecker05", true) {}
+     117             : };
+     118             : 
+     119             : /**
+     120             :  @class IRB_Franceschini08
+     121             :  @brief Extragalactic background light model from Franceschini et al. 2008
+     122             : 
+     123             :  Source info:
+     124             :  DOI:10.1051/0004-6361:200809691
+     125             :  https://arxiv.org/pdf/0805.1841.pdf, tables 1 and 2
+     126             :  */
+     127             : class IRB_Franceschini08: public TabularPhotonField {
+     128             : public:
+     129          14 :         IRB_Franceschini08() : TabularPhotonField("IRB_Franceschini08", true) {}
+     130             : };
+     131             : 
+     132             : /**
+     133             :  @class IRB_Finke10
+     134             :  @brief Extragalactic background light model from Finke et al. 2010
+     135             : 
+     136             :  Source info:
+     137             :  DOI:10.1088/0004-637X/712/1/238
+     138             :  https://iopscience.iop.org/article/10.1088/0004-637X/712/1/238/pdf
+     139             :  */
+     140             : class IRB_Finke10: public TabularPhotonField {
+     141             : public:
+     142          14 :         IRB_Finke10() : TabularPhotonField("IRB_Finke10", true) {}
+     143             : };
+     144             : 
+     145             : /**
+     146             :  @class IRB_Dominguez11
+     147             :  @brief Extragalactic background light model from Dominguez et al. 2011
+     148             : 
+     149             :  Source info:
+     150             :  DOI:10.1111/j.1365-2966.2010.17631.x
+     151             :  https://academic.oup.com/mnras/article/410/4/2556/1008012
+     152             :  */
+     153             : class IRB_Dominguez11: public TabularPhotonField {
+     154             : public:
+     155          14 :         IRB_Dominguez11() : TabularPhotonField("IRB_Dominguez11", true) {}
+     156             : };
+     157             : 
+     158             : /**
+     159             :  @class IRB_Gilmore12
+     160             :  @brief Extragalactic background light model from Gilmore et al. 2012
+     161             : 
+     162             :  Source info:
+     163             :  DOI:10.1111/j.1365-2966.2012.20841.x
+     164             :  https://academic.oup.com/mnras/article/422/4/3189/1050758
+     165             :  */
+     166             : class IRB_Gilmore12: public TabularPhotonField {
+     167             : public:
+     168          14 :         IRB_Gilmore12() : TabularPhotonField("IRB_Gilmore12", true) {}
+     169             : };
+     170             : 
+     171             : /**
+     172             :  @class IRB_Stecker16_upper
+     173             :  @brief Extragalactic background light model from Stecker et al. 2016 (upper-bound model)
+     174             : 
+     175             :  Source info:
+     176             :  DOI:10.3847/0004-637X/827/1/6
+     177             :  https://iopscience.iop.org/article/10.3847/0004-637X/827/1/6
+     178             :  */
+     179             : class IRB_Stecker16_upper: public TabularPhotonField {
+     180             : public:
+     181          14 :         IRB_Stecker16_upper() : TabularPhotonField("IRB_Stecker16_upper", true) {}
+     182             : };
+     183             : 
+     184             : /**
+     185             :  @class IRB_Stecker16_lower
+     186             :  @brief Extragalactic background light model from Stecker et al. 2016 (lower-bound model)
+     187             : 
+     188             :  Source info:
+     189             :  DOI:10.3847/0004-637X/827/1/6
+     190             :  https://iopscience.iop.org/article/10.3847/0004-637X/827/1/6
+     191             :  */
+     192             : class IRB_Stecker16_lower: public TabularPhotonField {
+     193             : public:
+     194          14 :         IRB_Stecker16_lower() : TabularPhotonField("IRB_Stecker16_lower", true) {}
+     195             : };
+     196             : 
+     197             : /**
+     198             :  @class IRB_Saldana21
+     199             :  @brief Extragalactic background light model from Saldana-Lopez et al. 2021
+     200             : 
+     201             :  Source info:
+     202             :  DOI:10.1093/mnras/stab2393
+     203             :  https://ui.adsabs.harvard.edu/abs/2021MNRAS.507.5144S/abstract
+     204             :  */
+     205             : class IRB_Saldana21: public TabularPhotonField {
+     206             : public:
+     207           8 :         IRB_Saldana21() : TabularPhotonField("IRB_Saldana21", true) {}
+     208             : };
+     209             : 
+     210             : /**
+     211             :  @class IRB_Saldana21_upper
+     212             :  @brief Extragalactic background light model from Saldana-Lopez et al. 2021 (upper-bound model)
+     213             : 
+     214             :  Source info:
+     215             :  DOI:10.1093/mnras/stab2393
+     216             :  https://ui.adsabs.harvard.edu/abs/2021MNRAS.507.5144S/abstract
+     217             :  */
+     218             : class IRB_Saldana21_upper: public TabularPhotonField {
+     219             : public:
+     220           0 :         IRB_Saldana21_upper() : TabularPhotonField("IRB_Saldana21_upper", true) {}
+     221             : };
+     222             : 
+     223             : /**
+     224             :  @class IRB_Saldana21_lower
+     225             :  @brief Extragalactic background light model from Saldana-Lopez et al. 2021 (lower-bound model)
+     226             : 
+     227             :  Source info:
+     228             :  DOI:10.1093/mnras/stab2393
+     229             :  https://ui.adsabs.harvard.edu/abs/2021MNRAS.507.5144S/abstract
+     230             :  */
+     231             : class IRB_Saldana21_lower: public TabularPhotonField {
+     232             : public:
+     233           0 :         IRB_Saldana21_lower() : TabularPhotonField("IRB_Saldana21_lower", true) {}
+     234             : };
+     235             : 
+     236             : /**
+     237             :  @class IRB_Finke22
+     238             :  @brief Extragalactic background light model from Finke et al. 2022
+     239             : 
+     240             :  Source info:
+     241             :  DOI:10.3847/1538-4357/ac9843
+     242             :  https://iopscience.iop.org/article/10.3847/1538-4357/ac9843/pdf
+     243             :  */
+     244             : class IRB_Finke22: public TabularPhotonField {
+     245             : public:
+     246          14 :         IRB_Finke22() : TabularPhotonField("IRB_Finke22", true) {}
+     247             : };
+     248             : 
+     249             : /**
+     250             :  @class URB
+     251             :  @brief Extragalactic background light model from Protheroe & Biermann 1996
+     252             : 
+     253             :  Source info:
+     254             :  DOI:10.1016/S0927-6505(96)00041-2
+     255             :  https://www.sciencedirect.com/science/article/abs/pii/S0927650596000412
+     256             :  */
+     257             : class URB_Protheroe96: public TabularPhotonField {
+     258             : public:
+     259          12 :         URB_Protheroe96() : TabularPhotonField("URB_Protheroe96", false) {}
+     260             : };
+     261             : 
+     262             : /**
+     263             :  @class URB
+     264             :  @brief Extragalactic background light model based on ARCADE2 observations, by Fixsen et al.
+     265             :  Note that this model does not cover the same energy range as other URB models. Here, only ~10 MHz - 10 GHz is considered.
+     266             :  Therefore, it only makes sense to use this model in very specific studies.
+     267             : 
+     268             :  Source info:
+     269             :  DOI:10.1088/0004-637X/734/1/5
+     270             :  https://iopscience.iop.org/article/10.1088/0004-637X/734/1/5
+     271             :  */
+     272             : class URB_Fixsen11: public TabularPhotonField {
+     273             : public:
+     274           8 :         URB_Fixsen11() : TabularPhotonField("URB_Fixsen11", false) {}
+     275             : };
+     276             : 
+     277             : /**
+     278             :  @class URB
+     279             :  @brief Extragalactic background light model by Nitu et al.
+     280             : 
+     281             :  Source info:
+     282             :  DOI:10.1016/j.astropartphys.2020.102532
+     283             :  https://www.sciencedirect.com/science/article/pii/S0927650520301043?
+     284             :  */
+     285             : class URB_Nitu21: public TabularPhotonField {
+     286             : public:
+     287          22 :         URB_Nitu21() : TabularPhotonField("URB_Nitu21", false) {}
+     288             : };
+     289             : 
+     290             : /**
+     291             :  @class BlackbodyPhotonField
+     292             :  @brief Photon field decorator for black body photon fields.
+     293             :  */
+     294             : class BlackbodyPhotonField: public PhotonField {
+     295             : public:
+     296             :         BlackbodyPhotonField(const std::string fieldName, const double blackbodyTemperature);
+     297             :         double getPhotonDensity(double ePhoton, double z = 0.) const;
+     298             :         double getMinimumPhotonEnergy(double z) const;
+     299             :         double getMaximumPhotonEnergy(double z) const;
+     300             :         void setQuantile(double q);
+     301             : 
+     302             : protected:
+     303             :         double blackbodyTemperature;
+     304             :         double quantile;
+     305             : };
+     306             : 
+     307             : /**
+     308             :  @class CMB
+     309             :  @brief Cosmic mircowave background photon field
+     310             : 
+     311             :  Source info:
+     312             :  This field is an isotropic blackbody photon field with temperature T = 2.73 K
+     313             :  */
+     314             : class CMB: public BlackbodyPhotonField {
+     315             : public:
+     316          80 :         CMB() : BlackbodyPhotonField("CMB", 2.73) {}
+     317             : };
+     318             : 
+     319             : 
+     320             : } // namespace crpropa
+     321             : 
+     322             : #endif // CRPROPA_PHOTONBACKGROUND_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Random.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Random.h.func-sort-c.html new file mode 100644 index 000000000..e8f69e8b4 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Random.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Random.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Random.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7887.5 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Random.h.func.html b/doc/coverageReport/include/crpropa/Random.h.func.html new file mode 100644 index 000000000..16cf98e23 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Random.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Random.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Random.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7887.5 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Random.h.gcov.html b/doc/coverageReport/include/crpropa/Random.h.gcov.html new file mode 100644 index 000000000..5799cec29 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Random.h.gcov.html @@ -0,0 +1,317 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Random.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Random.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7887.5 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : // Random.h
+       2             : // Mersenne Twister random number generator -- a C++ class Random
+       3             : // Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
+       4             : // Richard J. Wagner  v1.0  15 May 2003  rjwagner@writeme.com
+       5             : 
+       6             : // The Mersenne Twister is an algorithm for generating random numbers.  It
+       7             : // was designed with consideration of the flaws in various other generators.
+       8             : // The period, 2^19937-1, and the order of equidistribution, 623 dimensions,
+       9             : // are far greater.  The generator is also fast; it avoids multiplication and
+      10             : // division, and it benefits from caches and pipelines.  For more information
+      11             : // see the inventors' web page at http://www.math.keio.ac.jp/~matumoto/emt.html
+      12             : 
+      13             : // Reference
+      14             : // M. Matsumoto and T. Nishimura, "Mersenne Twister: A 623-Dimensionally
+      15             : // Equidistributed Uniform Pseudo-Random Number Generator", ACM Transactions on
+      16             : // Modeling and Computer Simulation, Vol. 8, No. 1, January 1998, pp 3-30.
+      17             : 
+      18             : // Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura,
+      19             : // Copyright (C) 2000 - 2003, Richard J. Wagner
+      20             : // All rights reserved.
+      21             : //
+      22             : // Redistribution and use in source and binary forms, with or without
+      23             : // modification, are permitted provided that the following conditions
+      24             : // are met:
+      25             : //
+      26             : //   1. Redistributions of source code must retain the above copyright
+      27             : //      notice, this list of conditions and the following disclaimer.
+      28             : //
+      29             : //   2. Redistributions in binary form must reproduce the above copyright
+      30             : //      notice, this list of conditions and the following disclaimer in the
+      31             : //      documentation and/or other materials provided with the distribution.
+      32             : //
+      33             : //   3. The names of its contributors may not be used to endorse or promote
+      34             : //      products derived from this software without specific prior written
+      35             : //      permission.
+      36             : //
+      37             : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+      38             : // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+      39             : // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+      40             : // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+      41             : // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+      42             : // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+      43             : // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+      44             : // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+      45             : // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+      46             : // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+      47             : // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+      48             : 
+      49             : // The original code included the following notice:
+      50             : //
+      51             : //     When you use this, send an email to: matumoto@math.keio.ac.jp
+      52             : //     with an appropriate reference to your work.
+      53             : //
+      54             : // It would be nice to CC: rjwagner@writeme.com and Cokus@math.washington.edu
+      55             : // when you write.
+      56             : 
+      57             : // Parts of this file are modified beginning in 29.10.09 for adaption in PXL.
+      58             : // Parts of this file are modified beginning in 10.02.12 for adaption in CRPropa.
+      59             : 
+      60             : #ifndef RANDOM_H
+      61             : #define RANDOM_H
+      62             : 
+      63             : // Not thread safe (unless auto-initialization is avoided and each thread has
+      64             : // its own Random object)
+      65             : #include "crpropa/Vector3.h"
+      66             : 
+      67             : #include <iostream>
+      68             : #include <limits>
+      69             : #include <ctime>
+      70             : #include <cmath>
+      71             : #include <vector>
+      72             : #include <stdexcept>
+      73             : #include <algorithm>
+      74             : 
+      75             : #include <stdint.h>
+      76             : #include <string>
+      77             : 
+      78             : //necessary for win32
+      79             : #ifndef M_PI
+      80             : #define M_PI 3.14159265358979323846
+      81             : #endif
+      82             : 
+      83             : namespace crpropa {
+      84             : 
+      85             : /**
+      86             :  * \addtogroup Core
+      87             :  * @{
+      88             :  */
+      89             : /**
+      90             :  @class Random
+      91             :  @brief Random number generator.
+      92             : 
+      93             :  Mersenne Twister random number generator -- a C++ class Random
+      94             :  Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
+      95             :  Richard J. Wagner  v1.0  15 May 2003  rjwagner@writeme.com
+      96             :  */
+      97           3 : class Random {
+      98             : public:
+      99             :         enum {N = 624}; // length of state vector
+     100             :         enum {SAVE = N + 1}; // length of array for save()
+     101             : 
+     102             : protected:
+     103             :         enum {M = 397}; // period parameter
+     104             :         uint32_t state[N];// internal state
+     105             :         std::vector<uint32_t> initial_seed;//
+     106             :         uint32_t *pNext;// next value to get from state
+     107             :         int left;// number of values left before reload needed
+     108             : 
+     109             : //Methods
+     110             : public:
+     111             :         /// initialize with a simple uint32_t
+     112             :         Random( const uint32_t& oneSeed );
+     113             :         // initialize with an array
+     114             :         Random( uint32_t *const bigSeed, uint32_t const seedLength = N );
+     115             :         /// auto-initialize with /dev/urandom or time() and clock()
+     116             :         /// Do NOT use for CRYPTOGRAPHY without securely hashing several returned
+     117             :         /// values together, otherwise the generator state can be learned after
+     118             :         /// reading 624 consecutive values.
+     119             :         Random();
+     120             :         // Access to 32-bit random numbers
+     121             :         double rand();///< real number in [0,1]
+     122             :         double rand( const double& n );///< real number in [0,n]
+     123             :         double randExc();///< real number in [0,1)
+     124             :         double randExc( const double& n );///< real number in [0,n)
+     125             :         double randDblExc();///< real number in (0,1)
+     126             :         double randDblExc( const double& n );///< real number in (0,n)
+     127             :         // Pull a 32-bit integer from the generator state
+     128             :         // Every other access function simply transforms the numbers extracted here
+     129             :         uint32_t randInt();///< integer in [0,2**32-1]
+     130             :         uint32_t randInt( const uint32_t& n );///< integer in [0,n] for n < 2**32
+     131             : 
+     132             :         uint64_t randInt64(); ///< integer in [0, 2**64 -1]. PROBABLY NOT SECURE TO USE
+     133             :         uint64_t randInt64(const uint64_t &n); ///< integer in [0, n] for n < 2**64 -1. PROBABLY NOT SECURE TO USE
+     134             : 
+     135           0 :         double operator()() {return rand();} ///< same as rand()
+     136             : 
+     137             :         // Access to 53-bit random numbers (capacity of IEEE double precision)
+     138             :         double rand53();///< real number in [0,1)  (capacity of IEEE double precision)
+     139             :         ///Exponential distribution in (0,inf)
+     140             :         double randExponential();
+     141             :         /// Normal distributed random number
+     142     1715954 :         double randNorm( const double& mean = 0.0, const double& variance = 1.0 );
+     143             :         /// Uniform distribution in [min, max]
+     144             :         double randUniform(double min, double max);
+     145             :         /// Rayleigh distributed random number
+     146             :         double randRayleigh(double sigma);
+     147             :         /// Fisher distributed random number
+     148             :         double randFisher(double k);
+     149             : 
+     150             :         /// Draw a random bin from a (unnormalized) cumulative distribution function, without leading zero.
+     151             :         size_t randBin(const std::vector<float> &cdf);
+     152             :         size_t randBin(const std::vector<double> &cdf);
+     153             : 
+     154             :         /// Random point on a unit-sphere
+     155             :         Vector3d randVector();
+     156             :         /// Random vector with given angular separation around mean direction
+     157             :         Vector3d randVectorAroundMean(const Vector3d &meanDirection, double angle);
+     158             :         /// Fisher distributed random vector
+     159             :         Vector3d randFisherVector(const Vector3d &meanDirection, double kappa);
+     160             :         /// Uniform distributed random vector inside a cone
+     161             :         Vector3d randConeVector(const Vector3d &meanDirection, double angularRadius);
+     162             :         /// Random lamberts distributed vector with theta distribution: sin(t) * cos(t),
+     163             :         /// aka cosine law (https://en.wikipedia.org/wiki/Lambert%27s_cosine_law),
+     164             :         /// for a surface element with normal vector pointing in positive z-axis (0, 0, 1)
+     165             :         Vector3d randVectorLamberts();
+     166             :         /// Same as above but rotated to the respective normalVector of surface element
+     167             :         Vector3d randVectorLamberts(const Vector3d &normalVector);
+     168             :         ///_Position vector uniformly distributed within propagation step size bin
+     169             :         Vector3d randomInterpolatedPosition(const Vector3d &a, const Vector3d &b);
+     170             : 
+     171             :         /// Power-law distribution of a given differential spectral index
+     172             :         double randPowerLaw(double index, double min, double max);
+     173             :         /// Broken power-law distribution
+     174             :         double randBrokenPowerLaw(double index1, double index2, double breakpoint, double min, double max );
+     175             : 
+     176             :         /// Seed the generator with a simple uint32_t
+     177             :         void seed( const uint32_t oneSeed );
+     178             :         /// Seed the generator with an array of uint32_t's
+     179             :         /// There are 2^19937-1 possible initial states.  This function allows
+     180             :         /// all of those to be accessed by providing at least 19937 bits (with a
+     181             :         /// default seed length of N = 624 uint32_t's).  Any bits above the lower 32
+     182             :         /// in each element are discarded.
+     183             :         /// Just call seed() if you want to get array from /dev/urandom
+     184             :         void seed( uint32_t *const bigSeed, const uint32_t seedLength = N );
+     185             :         // seed via an b64 encoded string
+     186             :         void seed( const std::string &b64Seed);
+     187             :         /// Seed the generator with an array from /dev/urandom if available
+     188             :         /// Otherwise use a hash of time() and clock() values
+     189             :         void seed();
+     190             : 
+     191             :         // Saving and loading generator state
+     192             :         void save( uint32_t* saveArray ) const;// to array of size SAVE
+     193             :         void load( uint32_t *const loadArray );// from such array
+     194             :         const std::vector<uint32_t> &getSeed() const; // copy the seed to the array
+     195             :         const std::string getSeed_base64() const; // get the base 64 encoded seed
+     196             : 
+     197             :         friend std::ostream& operator<<( std::ostream& os, const Random& mtrand );
+     198             :         friend std::istream& operator>>( std::istream& is, Random& mtrand );
+     199             : 
+     200             :         static Random &instance();
+     201             :         static void seedThreads(const uint32_t oneSeed);
+     202             :         static std::vector< std::vector<uint32_t> > getSeedThreads();
+     203             : 
+     204             : protected:
+     205             :         /// Initialize generator state with seed
+     206             :         /// See Knuth TAOCP Vol 2, 3rd Ed, p.106 for multiplier.
+     207             :         /// In previous versions, most significant bits (MSBs) of the seed affect
+     208             :         /// only MSBs of the state array.  Modified 9 Jan 2002 by Makoto Matsumoto.
+     209             :         void initialize( const uint32_t oneSeed );
+     210             : 
+     211             :         /// Generate N new values in state
+     212             :         /// Made clearer and faster by Matthew Bellew (matthew.bellew@home.com)
+     213             :         void reload();
+     214    28904304 :         uint32_t hiBit( const uint32_t& u ) const {return u & 0x80000000UL;}
+     215    28904304 :         uint32_t loBit( const uint32_t& u ) const {return u & 0x00000001UL;}
+     216    28904304 :         uint32_t loBits( const uint32_t& u ) const {return u & 0x7fffffffUL;}
+     217             :         uint32_t mixBits( const uint32_t& u, const uint32_t& v ) const
+     218    28904304 :         {       return hiBit(u) | loBits(v);}
+     219             : 
+     220             : #ifdef _MSC_VER
+     221             : #pragma warning( push )
+     222             : #pragma warning( disable : 4146 )
+     223             : #endif
+     224             :         uint32_t twist( const uint32_t& m, const uint32_t& s0, const uint32_t& s1 ) const
+     225    28857983 :         {       return m ^ (mixBits(s0,s1)>>1) ^ (-loBit(s1) & 0x9908b0dfUL);}
+     226             : 
+     227             : #ifdef _MSC_VER
+     228             : #pragma warning( pop )
+     229             : #endif
+     230             : 
+     231             :         /// Get a uint32_t from t and c
+     232             :         /// Better than uint32_t(x) in case x is floating point in [0,1]
+     233             :         /// Based on code by Lawrence Kirby (fred@genesis.demon.co.uk)
+     234             :         static uint32_t hash( time_t t, clock_t c );
+     235             : 
+     236             : };
+     237             : /** @}*/
+     238             : 
+     239             : } //namespace crpropa
+     240             : 
+     241             : #endif  // RANDOM_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html new file mode 100644 index 000000000..ce69cfb72 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Referenced.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Referenced.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:415673.2 %
Date:2024-04-08 14:58:22Functions:101952.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10ReferencedD0Ev0
_ZN7crpropa10ReferencedD2Ev0
_ZN7crpropa7ref_ptrINS_10ModuleListEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_11EmissionMapEEaSEPS1_0
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEE6assignIS4_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridIfEEE6assignIS2_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridIfEEEaSEPS2_0
_ZN7crpropa7ref_ptrINS_6ModuleEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_7DensityEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_13MagneticFieldEEaSEPS1_2
_ZN7crpropa7ref_ptrINS_6ModuleEEaSEPS1_4
_ZN7crpropa7ref_ptrINS_24CylindricalProjectionMapEE6assignIS1_EEvRKNS0_IT_EE5
_ZN7crpropa7ref_ptrINS_14AdvectionFieldEE6assignIS1_EEvRKNS0_IT_EE6
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEEaSEPS4_6
_ZN7crpropa7ref_ptrINS_13MagneticFieldEE6assignIS1_EEvRKNS0_IT_EE46
_ZN7crpropa7ref_ptrINS_11PhotonFieldEEaSEPS1_66
_ZN7crpropa7ref_ptrINS_11PhotonFieldEE6assignIS1_EEvRKNS0_IT_EE159
_ZN7crpropa7ref_ptrINS_9CandidateEE6assignIS1_EEvRKNS0_IT_EE1103
_ZNK7crpropa10Referenced15removeReferenceEv10914622
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Referenced.h.func.html b/doc/coverageReport/include/crpropa/Referenced.h.func.html new file mode 100644 index 000000000..1897f7f51 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Referenced.h.func.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Referenced.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Referenced.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:415673.2 %
Date:2024-04-08 14:58:22Functions:101952.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10ReferencedD0Ev0
_ZN7crpropa10ReferencedD2Ev0
_ZN7crpropa7ref_ptrINS_10ModuleListEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_11EmissionMapEEaSEPS1_0
_ZN7crpropa7ref_ptrINS_11PhotonFieldEE6assignIS1_EEvRKNS0_IT_EE159
_ZN7crpropa7ref_ptrINS_11PhotonFieldEEaSEPS1_66
_ZN7crpropa7ref_ptrINS_13MagneticFieldEE6assignIS1_EEvRKNS0_IT_EE46
_ZN7crpropa7ref_ptrINS_13MagneticFieldEEaSEPS1_2
_ZN7crpropa7ref_ptrINS_14AdvectionFieldEE6assignIS1_EEvRKNS0_IT_EE6
_ZN7crpropa7ref_ptrINS_24CylindricalProjectionMapEE6assignIS1_EEvRKNS0_IT_EE5
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEE6assignIS4_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEEaSEPS4_6
_ZN7crpropa7ref_ptrINS_4GridIfEEE6assignIS2_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridIfEEEaSEPS2_0
_ZN7crpropa7ref_ptrINS_6ModuleEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_6ModuleEEaSEPS1_4
_ZN7crpropa7ref_ptrINS_7DensityEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_9CandidateEE6assignIS1_EEvRKNS0_IT_EE1103
_ZNK7crpropa10Referenced15removeReferenceEv10914622
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Referenced.h.gcov.html b/doc/coverageReport/include/crpropa/Referenced.h.gcov.html new file mode 100644 index 000000000..5a9b12d1c --- /dev/null +++ b/doc/coverageReport/include/crpropa/Referenced.h.gcov.html @@ -0,0 +1,320 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Referenced.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Referenced.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:415673.2 %
Date:2024-04-08 14:58:22Functions:101952.6 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_REFERENCED_H
+       2             : #define CRPROPA_REFERENCED_H
+       3             : 
+       4             : #include <cstddef>
+       5             : 
+       6             : #ifdef DEBUG
+       7             : #include <iostream>
+       8             : #include <typeinfo>
+       9             : #endif
+      10             : 
+      11             : namespace crpropa {
+      12             : /**
+      13             :  * \addtogroup Core
+      14             :  * @{
+      15             :  */
+      16             : 
+      17             : /**
+      18             :  @class Referenced
+      19             :  @brief Base class for reference counting
+      20             : 
+      21             :  A form of memory management is needed to prevent memory leaks when using MPC in Python via SWIG.
+      22             :  This base class enables reference counting.
+      23             :  Every reference increases the reference counter, every dereference decreases it.
+      24             :  When the counter is decreased to 0, the object is deleted.
+      25             :  Candidate, Module, MagneticField and Source inherit from this class
+      26             :  */
+      27             : class Referenced {
+      28             : public:
+      29             : 
+      30     3369415 :         inline Referenced() :
+      31     3369394 :                         _referenceCount(0) {
+      32             :         }
+      33             : 
+      34           0 :         inline Referenced(const Referenced&) :
+      35           0 :                         _referenceCount(0) {
+      36             :         }
+      37             : 
+      38             :         inline Referenced& operator =(const Referenced&) {
+      39             :                 return *this;
+      40             :         }
+      41             : 
+      42             :         inline size_t addReference() const {
+      43             :                 int newRef;
+      44             : #if defined(OPENMP_3_1)
+      45             :                 #pragma omp atomic capture
+      46             :                 {newRef = _referenceCount++;}
+      47             : #elif defined(__GNUC__)
+      48    10913236 :                 newRef = __sync_add_and_fetch(&_referenceCount, 1);
+      49             : #else
+      50             :                 #pragma omp critical
+      51             :                 {newRef = _referenceCount++;}
+      52             : #endif
+      53     7546128 :                 return newRef;
+      54             :         }
+      55             : 
+      56    10914622 :         inline size_t removeReference() const {
+      57             : #ifdef DEBUG
+      58             :                 if (_referenceCount == 0)
+      59             :                         std::cerr
+      60             :                                         << "WARNING: Remove reference from Object with NO references: "
+      61             :                                         << typeid(*this).name() << std::endl;
+      62             : #endif
+      63             :                 int newRef;
+      64             : #if defined(OPENMP_3_1)
+      65             :                 #pragma omp atomic capture
+      66             :                 {newRef = _referenceCount--;}
+      67             : #elif defined(__GNUC__)
+      68    10914622 :                 newRef = __sync_sub_and_fetch(&_referenceCount, 1);
+      69             : #else
+      70             :                 #pragma omp critical
+      71             :                 {newRef = _referenceCount--;}
+      72             : #endif
+      73             : 
+      74    10914622 :                 if (newRef == 0) {
+      75     3367410 :                         delete this;
+      76             :                 }
+      77    10914622 :                 return newRef;
+      78             :         }
+      79             : 
+      80             :         int removeReferenceNoDelete() const {
+      81           0 :                 return --_referenceCount;
+      82             :         }
+      83             : 
+      84             :         inline size_t getReferenceCount() const {
+      85           0 :                 return _referenceCount;
+      86             :         }
+      87             : 
+      88             : protected:
+      89             : 
+      90           0 :         virtual inline ~Referenced() {
+      91             : #ifdef DEBUG
+      92             :                 if (_referenceCount)
+      93             :                         std::cerr << "WARNING: Deleting Object with references: "
+      94             :                                         << typeid(*this).name() << std::endl;
+      95             : #endif
+      96           0 :         }
+      97             : 
+      98             :         mutable size_t _referenceCount;
+      99             : };
+     100             : 
+     101             : inline void intrusive_ptr_add_ref(Referenced* p) {
+     102             :         p->addReference();
+     103             : }
+     104             : inline void intrusive_ptr_release(Referenced* p) {
+     105           0 :         p->removeReference();
+     106             : }
+     107             : 
+     108             : /**
+     109             :  @class ref_ptr
+     110             :  @brief Referenced pointer
+     111             :  */
+     112             : template<class T>
+     113             : class ref_ptr {
+     114             : public:
+     115             :         typedef T element_type;
+     116             : 
+     117         167 :         ref_ptr() :
+     118         167 :                         _ptr(0) {
+     119             :         }
+     120     3328293 :         ref_ptr(T* ptr) :
+     121     3330334 :                         _ptr(ptr) {
+     122        3307 :                 if (_ptr)
+     123             :                         _ptr->addReference();
+     124             :         }
+     125     7541490 :         ref_ptr(const ref_ptr& rp) :
+     126     7541372 :                         _ptr(rp._ptr) {
+     127     7541428 :                 if (_ptr)
+     128             :                         _ptr->addReference();
+     129           2 :         }
+     130           4 :         template<class Other> ref_ptr(const ref_ptr<Other>& rp) :
+     131           4 :                         _ptr(rp._ptr) {
+     132             :                 if (_ptr)
+     133             :                         _ptr->addReference();
+     134             :         }
+     135             : 
+     136             :         ~ref_ptr() {
+     137    10870856 :                 if (_ptr)
+     138    10870929 :                         _ptr->removeReference();
+     139             :                 _ptr = 0;
+     140    10870851 :         }
+     141             : 
+     142             :         ref_ptr& operator =(const ref_ptr& rp) {
+     143         218 :                 assign(rp);
+     144           0 :                 return *this;
+     145             :         }
+     146             : 
+     147             :         template<class Other> ref_ptr& operator =(const ref_ptr<Other>& rp) {
+     148             :                 assign(rp);
+     149             :                 return *this;
+     150             :         }
+     151             : 
+     152          78 :         inline ref_ptr& operator =(T* ptr) {
+     153          78 :                 if (_ptr == ptr)
+     154             :                         return *this;
+     155             :                 T* tmp_ptr = _ptr;
+     156          78 :                 _ptr = ptr;
+     157          78 :                 if (_ptr)
+     158             :                         _ptr->addReference();
+     159          78 :                 if (tmp_ptr)
+     160          68 :                         tmp_ptr->removeReference();
+     161             :                 return *this;
+     162             :         }
+     163             : 
+     164             :         operator T*() const {
+     165      481185 :                 return _ptr;
+     166             :         }
+     167             : 
+     168             :         T& operator*() const {
+     169        6611 :                 return *_ptr;
+     170             :         }
+     171             :         T* operator->() const {
+     172     6292284 :                 return _ptr;
+     173             :         }
+     174             :         T* get() const {
+     175          37 :                 return _ptr;
+     176             :         }
+     177             : 
+     178             :         bool operator!() const {
+     179           0 :                 return _ptr == 0;
+     180             :         } // not required
+     181             :         bool valid() const {
+     182     5881570 :                 return _ptr != 0;
+     183             :         }
+     184             : 
+     185             :         T* release() {
+     186           0 :                 T* tmp = _ptr;
+     187           0 :                 if (_ptr)
+     188             :                         _ptr->removeReferenceNoDelete();
+     189           0 :                 _ptr = 0;
+     190             :                 return tmp;
+     191             :         }
+     192             : 
+     193             :         void swap(ref_ptr& rp) {
+     194           0 :                 T* tmp = _ptr;
+     195           0 :                 _ptr = rp._ptr;
+     196           0 :                 rp._ptr = tmp;
+     197             :         }
+     198             : 
+     199             : private:
+     200             : 
+     201        1319 :         template<class Other> void assign(const ref_ptr<Other>& rp) {
+     202        1319 :                 if (_ptr == rp._ptr)
+     203             :                         return;
+     204             :                 T* tmp_ptr = _ptr;
+     205        1315 :                 _ptr = rp._ptr;
+     206        1315 :                 if (_ptr)
+     207             :                         _ptr->addReference();
+     208        1315 :                 if (tmp_ptr)
+     209          91 :                         tmp_ptr->removeReference();
+     210             :         }
+     211             : 
+     212             :         template<class Other> friend class ref_ptr;
+     213             : 
+     214             :         T* _ptr;
+     215             : };
+     216             : 
+     217             : template<class T> inline
+     218             : void swap(ref_ptr<T>& rp1, ref_ptr<T>& rp2) {
+     219             :         rp1.swap(rp2);
+     220             : }
+     221             : 
+     222             : template<class T> inline T* get_pointer(const ref_ptr<T>& rp) {
+     223             :         return rp.get();
+     224             : }
+     225             : 
+     226             : template<class T, class Y> inline ref_ptr<T> static_pointer_cast(
+     227             :                 const ref_ptr<Y>& rp) {
+     228             :         return static_cast<T*>(rp.get());
+     229             : }
+     230             : 
+     231             : template<class T, class Y> inline ref_ptr<T> dynamic_pointer_cast(
+     232             :                 const ref_ptr<Y>& rp) {
+     233             :         return dynamic_cast<T*>(rp.get());
+     234             : }
+     235             : 
+     236             : template<class T, class Y> inline ref_ptr<T> const_pointer_cast(
+     237             :                 const ref_ptr<Y>& rp) {
+     238             :         return const_cast<T*>(rp.get());
+     239             : }
+     240             : 
+     241             : /** @}*/
+     242             : } // namespace crpropa
+     243             : 
+     244             : #endif // CRPROPA_REFERENCED_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Source.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Source.h.func-sort-c.html new file mode 100644 index 000000000..e0c693ff0 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Source.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Source.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Source.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:141877.8 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13SourceFeature15prepareParticleERNS_13ParticleStateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Source.h.func.html b/doc/coverageReport/include/crpropa/Source.h.func.html new file mode 100644 index 000000000..646b8d073 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Source.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Source.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Source.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:141877.8 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13SourceFeature15prepareParticleERNS_13ParticleStateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Source.h.gcov.html b/doc/coverageReport/include/crpropa/Source.h.gcov.html new file mode 100644 index 000000000..82cca4d84 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Source.h.gcov.html @@ -0,0 +1,1002 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Source.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Source.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:141877.8 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_SOURCE_H
+       2             : #define CRPROPA_SOURCE_H
+       3             : 
+       4             : #include "crpropa/Candidate.h"
+       5             : #include "crpropa/Grid.h"
+       6             : #include "crpropa/EmissionMap.h"
+       7             : #include "crpropa/massDistribution/Density.h"
+       8             : 
+       9             : 
+      10             : #include <vector>
+      11             : 
+      12             : namespace crpropa {
+      13             : /** @addtogroup SourceFeatures
+      14             :  *  @{
+      15             :  */
+      16             : 
+      17             : 
+      18             : /**
+      19             :  @class SourceFeature
+      20             :  @brief Abstract base class for specific source features
+      21             :  */
+      22           7 : class SourceFeature: public Referenced {
+      23             : protected:
+      24             :         std::string description;
+      25             : public:
+      26           0 :         virtual void prepareParticle(ParticleState& particle) const {};
+      27             :         virtual void prepareCandidate(Candidate& candidate) const;
+      28             :         std::string getDescription() const;
+      29             : };
+      30             : 
+      31             : 
+      32             : /**
+      33             :  @class SourceInterface
+      34             :  @brief Abstract base class for sources
+      35             :  */
+      36             : class SourceInterface : public Referenced {
+      37             : public:
+      38             :         virtual ref_ptr<Candidate> getCandidate() const = 0;
+      39             :         virtual std::string getDescription() const = 0;
+      40             : };
+      41             : 
+      42             : 
+      43             : /**
+      44             :  @class Source
+      45             :  @brief General source of particles
+      46             : 
+      47             :  This class is a container for source features.
+      48             :  The source prepares a new candidate by passing it to all its source features
+      49             :  to be modified accordingly.
+      50             :  */
+      51          10 : class Source: public SourceInterface {
+      52             :         std::vector<ref_ptr<SourceFeature> > features;
+      53             : public:
+      54             :         void add(SourceFeature* feature);
+      55             :         ref_ptr<Candidate> getCandidate() const;
+      56             :         std::string getDescription() const;
+      57             : };
+      58             : 
+      59             : 
+      60             : /**
+      61             :  @class SourceList
+      62             :  @brief List of particle sources of individual luminosities.
+      63             : 
+      64             :  The SourceList is a source itself. It can be used if several sources are
+      65             :  needed in one simulation.
+      66             :  */
+      67           3 : class SourceList: public SourceInterface {
+      68             :         std::vector<ref_ptr<Source> > sources;
+      69             :         std::vector<double> cdf;
+      70             : public:
+      71             :         /** Add an individual source to the list.
+      72             :          @param source          source to be added
+      73             :          @param weight          weight of the source; defaults to 1.
+      74             :          */
+      75             :         void add(Source* source, double weight = 1);
+      76             :         ref_ptr<Candidate> getCandidate() const;
+      77             :         std::string getDescription() const;
+      78             : };
+      79             : 
+      80             : 
+      81             : /**
+      82             :  @class SourceParticleType
+      83             :  @brief Particle type at the source
+      84             : 
+      85             :  This feature assigns a single particle type to the source.
+      86             :  For multiple types, use e.g. SourceMultipleParticleTypes.
+      87             :  Particles are identified following the PDG numbering scheme:
+      88             :    https://pdg.lbl.gov/2019/reviews/rpp2019-rev-monte-carlo-numbering.pdf
+      89             :  */
+      90             : class SourceParticleType: public SourceFeature {
+      91             :         int id;
+      92             : public:
+      93             :         /** Constructor for a source with a sign
+      94             :          @param id              id of the particle following the PDG numbering scheme
+      95             :         */
+      96             :         SourceParticleType(int id);
+      97             :         void prepareParticle(ParticleState &particle) const;
+      98             :         void setDescription();
+      99             : };
+     100             : 
+     101             : 
+     102             : /**
+     103             :  @class SourceMultipleParticleTypes
+     104             :  @brief Multiple particle types with individual relative abundances
+     105             : 
+     106             :  This feature assigns particle types to the events emitted by the sources.
+     107             :  It is possible to control the relative abundance of each particle species.
+     108             :  Particles are identified following the PDG numbering scheme:
+     109             :    https://pdg.lbl.gov/2019/reviews/rpp2019-rev-monte-carlo-numbering.pdf
+     110             :  */
+     111             : class SourceMultipleParticleTypes: public SourceFeature {
+     112             :         std::vector<int> particleTypes;
+     113             :         std::vector<double> cdf;
+     114             : public:
+     115             :         /** Constructor
+     116             :          */
+     117             :         SourceMultipleParticleTypes();
+     118             :         /** Add an individual particle type.
+     119             :          @param id                      id of the particle following the PDG numbering scheme
+     120             :          @param weight          relative abundance of individual particle species
+     121             :          */
+     122             :         void add(int id, double weight = 1);
+     123             :         void prepareParticle(ParticleState &particle) const;
+     124             :         void setDescription();
+     125             : };
+     126             : 
+     127             : 
+     128             : /**
+     129             :  @class SourceEnergy
+     130             :  @brief Sets the initial energy of the emitted particles to a specific value
+     131             : 
+     132             :  This feature assigns a monochromatic spectrum, i.e., a single energy to all particles.
+     133             :  */
+     134             : class SourceEnergy: public SourceFeature {
+     135             :         double E;
+     136             : public:
+     137             :         /** Constructor
+     138             :          @param energy          energy of the particle (in Joules)
+     139             :          */
+     140             :         SourceEnergy(double energy);
+     141             :         void prepareParticle(ParticleState &particle) const;
+     142             :         void setDescription();
+     143             : };
+     144             : 
+     145             : 
+     146             : /**
+     147             :  @class SourcePowerLawSpectrum
+     148             :  @brief Particle energy following a power-law spectrum
+     149             : 
+     150             :  The power law is of the form: dN/dE ~ E^index, for energies in the interval [Emin, Emax].
+     151             :  */
+     152           1 : class SourcePowerLawSpectrum: public SourceFeature {
+     153             :         double Emin;
+     154             :         double Emax;
+     155             :         double index;
+     156             : public:
+     157             :         /** Constructor
+     158             :          @param Emin            minimum energy (in Joules)
+     159             :          @param Emax            maximum energy (in Joules)
+     160             :          @param index           spectral index of the power law
+     161             :          */
+     162             :         SourcePowerLawSpectrum(double Emin, double Emax, double index);
+     163             :         void prepareParticle(ParticleState &particle) const;
+     164             :         void setDescription();
+     165             : };
+     166             : 
+     167             : 
+     168             : /**
+     169             :  @class SourceComposition
+     170             :  @brief Multiple nuclear species with a rigidity-dependent power-law spectrum
+     171             : 
+     172             :  The power law is of the form: E^index, for energies in the interval [Emin, Z * Rmax].
+     173             :  */
+     174             : class SourceComposition: public SourceFeature {
+     175             :         double Emin;
+     176             :         double Rmax;
+     177             :         double index;
+     178             :         std::vector<int> nuclei;
+     179             :         std::vector<double> cdf;
+     180             : public:
+     181             :         /** Constructor
+     182             :          @param Emin            minimum energy (in Joules)
+     183             :          @param Rmax            maximum rigidity (in Volts)
+     184             :          @param index           spectral index of the power law
+     185             :          */
+     186             :         SourceComposition(double Emin, double Rmax, double index);
+     187             :         /** Add individual particle species with a given abundance
+     188             :          @param id                      id of the particle following the PDG numbering scheme
+     189             :          @param abundance       relative abundance of the particle species
+     190             :          */
+     191             :         void add(int id, double abundance);
+     192             :         /** Add individual particle species with a given abundance
+     193             :          @param A                       atomic mass of the cosmic-ray nucleus
+     194             :          @param Z                       atomic number of the cosmic-ray nucleus
+     195             :          @param abundance       relative abundance of the particle species
+     196             :          */
+     197             :         void add(int A, int Z, double abundance);
+     198             :         void prepareParticle(ParticleState &particle) const;
+     199             :         void setDescription();
+     200             : };
+     201             : 
+     202             : 
+     203             : /**
+     204             :  @class SourcePosition
+     205             :  @brief Position of a point source
+     206             :  */
+     207           1 : class SourcePosition: public SourceFeature {
+     208             :         Vector3d position; 
+     209             : public:
+     210             :         /** Constructor for a source in 3D
+     211             :          @param position        vector containing the coordinates of the point source [in meters]
+     212             :          */
+     213             :         SourcePosition(Vector3d position);
+     214             :         /** Constructor for a source in 1D
+     215             :          @param d       distance of the point source to the observer at x = 0 [in meters]; 
+     216             :                                 internally this will be converted to a vector with x-coordinate equal to d
+     217             :          */
+     218             :         SourcePosition(double d);
+     219             :         void prepareParticle(ParticleState &state) const;
+     220             :         void setDescription();
+     221             : };
+     222             : 
+     223             : 
+     224             : /**
+     225             :  @class SourceMultiplePositions
+     226             :  @brief Multiple point-source positions with individual luminosities
+     227             :  */
+     228             : class SourceMultiplePositions: public SourceFeature {
+     229             :         std::vector<Vector3d> positions;
+     230             :         std::vector<double> cdf;
+     231             : public:
+     232             :         /** Constructor.
+     233             :          The sources must be added individually to the object.
+     234             :          */
+     235             :         SourceMultiplePositions();
+     236             :         /** Add an individual source with a given luminosity/contribution.
+     237             :          @param position        vector containing the coordinates of the point source [in meters]
+     238             :          @param weight          luminosity/contribution of the individual source
+     239             :          */
+     240             :         void add(Vector3d position, double weight = 1);
+     241             :         void prepareParticle(ParticleState &particle) const;
+     242             :         void setDescription();
+     243             : };
+     244             : 
+     245             : 
+     246             : /**
+     247             :  @class SourceUniformSphere
+     248             :  @brief Uniform distribution of sources in a spherical volume
+     249             :  */
+     250           1 : class SourceUniformSphere: public SourceFeature {
+     251             :         Vector3d center;
+     252             :         double radius;
+     253             : public:
+     254             :         /** Constructor
+     255             :          @param center          vector containing the coordinates of the center of the sphere
+     256             :          @param radius          radius of the sphere
+     257             :          */
+     258             :         SourceUniformSphere(Vector3d center, double radius);
+     259             :         void prepareParticle(ParticleState &particle) const;
+     260             :         void setDescription();
+     261             : };
+     262             : 
+     263             : 
+     264             : /**
+     265             :  @class SourceUniformHollowSphere
+     266             :  @brief Uniform distribution of sources between two spheres
+     267             :  */
+     268           1 : class SourceUniformHollowSphere: public SourceFeature {
+     269             :         Vector3d center;
+     270             :         double radius_inner;
+     271             :         double radius_outer;
+     272             : public:
+     273             :         /** Constructor
+     274             :          @param center                  vector containing the coordinates of the center of the sphere
+     275             :          @param radius_inner    radius of the inner sphere
+     276             :          @param radius_outer    radius of the outer sphere
+     277             :          */
+     278             :         SourceUniformHollowSphere(Vector3d center,
+     279             :                         double radius_inner, double radius_outer);
+     280             :         void prepareParticle(ParticleState &particle) const;
+     281             :         void setDescription();
+     282             : };
+     283             : 
+     284             : 
+     285             : /**
+     286             :  @class SourceUniformShell
+     287             :  @brief Uniform distribution of source positions on the surface of a sphere
+     288             :  */
+     289             : class SourceUniformShell: public SourceFeature {
+     290             :         Vector3d center;
+     291             :         double radius;
+     292             : public:
+     293             :         /** Constructor
+     294             :          @param center          vector containing the coordinates of the center of the sphere
+     295             :          @param radius          radius of the sphere
+     296             :          */
+     297             :         SourceUniformShell(Vector3d center, double radius);
+     298             :         void prepareParticle(ParticleState &particle) const;
+     299             :         void setDescription();
+     300             : };
+     301             : 
+     302             : 
+     303             : /**
+     304             :  @class SourceUniformBox
+     305             :  @brief Uniform random source positions inside a box. The box is aligned with the coordinate axes.
+     306             :  */
+     307           1 : class SourceUniformBox: public SourceFeature {
+     308             :         Vector3d origin;        // lower box corner
+     309             :         Vector3d size;          // sizes along each coordinate axes.
+     310             : public:
+     311             :         /** Constructor
+     312             :          @param origin  vector corresponding to the lower box corner
+     313             :          @param size    vector corresponding to the box sizes along each direction
+     314             :          */
+     315             :         SourceUniformBox(Vector3d origin, Vector3d size);
+     316             :         void prepareParticle(ParticleState &particle) const;
+     317             :         void setDescription();
+     318             : };
+     319             : 
+     320             : 
+     321             : /**
+     322             :  @class SourceUniformCylinder
+     323             :  @brief Uniform distribution of source positions inside the volume of a cylinder whose axis is along the z-axis. 
+     324             : 
+     325             :  The circle of the cylinder lays in the xy-plane and the height is along the z-axis.
+     326             :  */
+     327           1 : class SourceUniformCylinder: public SourceFeature {
+     328             :         Vector3d origin;        // central point of cylinder 
+     329             :         double height;          // total height of the cylinder along z-axis. Half over/under the center.
+     330             :         double radius;          // radius of the cylinder in the xy-plane
+     331             : public:
+     332             :         /** Constructor
+     333             :          @param origin  vector corresponding to the center of the cylinder axis
+     334             :          @param height  height of the cylinder, half lays over the origin, half is lower
+     335             :          @param radius  radius of the cylinder
+     336             :          */
+     337             :         SourceUniformCylinder(Vector3d origin, double height, double radius);
+     338             :         void prepareParticle(ParticleState &particle) const;
+     339             :         void setDescription();
+     340             : };
+     341             : 
+     342             : 
+     343             : /**
+     344             :  @class SourceSNRDistribution
+     345             :  @brief Source distribution that follows the Galactic SNR distribution in 2D
+     346             : 
+     347             :  The origin of the distribution is the Galactic center. The default maximum radius is set 
+     348             :  to rMax=20 kpc and the default maximum height is zMax = 5 kpc.
+     349             :  See G. Case and D. Bhattacharya (1996) for the details of the distribution.
+     350             :  */
+     351           1 : class SourceSNRDistribution: public SourceFeature {
+     352             :         double rEarth; // parameter given by observation
+     353             :         double alpha; // parameter to shift the maximum in R direction
+     354             :         double beta; // parameter to shift the maximum in R direction
+     355             :         double zg; // exponential cut parameter in z direction
+     356             :         double frMax; // helper for efficient sampling
+     357             :         double fzMax; // helper for efficient sampling
+     358             :         double rMax; // maximum radial distance - default 20 kpc 
+     359             :                       // (due to the extension of the JF12 field)
+     360             :         double zMax; // maximum distance from galactic plane - default 5 kpc
+     361             :         void setFrMax(); // calculate frMax with the current parameter. 
+     362             : 
+     363             : public:
+     364             :         /** Default constructor. 
+     365             :          Default parameters are:
+     366             :          . rEarth = 8.5 kpc
+     367             :          . alpha = 2
+     368             :          . beta = 3.53
+     369             :          . zg = 300 pc
+     370             :          . rMax = 20 kpc
+     371             :          . zMax = 5 kpc
+     372             :         */ 
+     373             :         SourceSNRDistribution();
+     374             :         /** Generic constructor
+     375             :          @param rEarth    distance from Earth to the Galactic centre [in meters]
+     376             :          @param alpha     parameter that shifts radially the maximum of the distributions
+     377             :          @param beta      parameter that shifts radially the maximum of the distributions 
+     378             :          @param zg                exponential cut-off parameter in the z-direction [in meters]
+     379             :         */      
+     380             :         SourceSNRDistribution(double rEarth,double alpha, double beta, double zg);
+     381             : 
+     382             :         void prepareParticle(ParticleState &particle) const;
+     383             :         /**
+     384             :          radial distribution of the SNR density.
+     385             :          @param r       galactocentric radius in [meter]
+     386             :         */
+     387             :         double fr(double r) const;
+     388             :         /**
+     389             :          height distribution of the SNR density.
+     390             :          @param z       height over/under the galactic plane in [meter]
+     391             :         */
+     392             :         double fz(double z) const;
+     393             : 
+     394             :         /**
+     395             :          Set the exponential cut-off parameter in the z-direction.
+     396             :          @param Zg      cut-off parameter
+     397             :         */
+     398             :         void setFzMax(double Zg);
+     399             : 
+     400             :         /**
+     401             :          @param rMax maximal radius up to which sources are possible
+     402             :         */
+     403             :         void setRMax(double rMax);
+     404             : 
+     405             :         /**
+     406             :          @param zMax maximal height up to which sources are possible
+     407             :         */
+     408             :         void setZMax(double zMax);
+     409             : 
+     410             :         // parameter for the raidal distribution
+     411             :         void setAlpha(double a);
+     412             :         // parameter for the exponential cut-off in the radial distribution
+     413             :         void setBeta(double b);
+     414             :         double getFrMax() const;
+     415             :         double getFzMax() const;
+     416             :         double getRMax() const;
+     417             :         double getZMax() const;
+     418             :         double getAlpha() const;
+     419             :         double getBeta() const;
+     420             :         void setDescription();
+     421             : };
+     422             : 
+     423             : 
+     424             : /**
+     425             :  @class SourcePulsarDistribution
+     426             :  @brief Source distribution following the Galactic pulsar distribution
+     427             : 
+     428             :  A logarithmic spiral with four arms is used for the radial distribution.
+     429             :  The z-distribution is a simple exponentially decaying distribution.
+     430             :  The pulsar distribution is explained in detail in C.-A. Faucher-Giguere
+     431             :  and V. M. Kaspi, ApJ 643 (May, 2006) 332. The radial distribution is 
+     432             :  parametrized as in Blasi and Amato, JCAP 1 (Jan., 2012) 10.
+     433             :  */
+     434             : class SourcePulsarDistribution: public SourceFeature {
+     435             :         double rEarth; // parameter given by observation
+     436             :         double beta; // parameter to shift the maximum in R direction
+     437             :         double zg; // exponential cut parameter in z direction
+     438             :         double frMax; // helper for efficient sampling
+     439             :         double fzMax; // helper for efficient sampling
+     440             :         double rMax; // maximum radial distance - default 22 kpc 
+     441             :         double zMax; // maximum distance from galactic plane - default 5 kpc
+     442             :         double rBlur; // relative smearing factor for the radius
+     443             :         double thetaBlur; // smearing factor for the angle. Unit = [1/length]
+     444             : public:
+     445             :         /** Default constructor. 
+     446             :          Default parameters are:
+     447             :          . rEarth = 8.5 kpc
+     448             :          . beta = 3.53
+     449             :          . zg = 300 pc
+     450             :          . Rmax = 22 kpc
+     451             :          . Zmax = 5 kpc
+     452             :          . rBlur = 0.07
+     453             :          . thetaBlur = 0.35 / kpc
+     454             :          */ 
+     455             :         SourcePulsarDistribution();     
+     456             :         /** Generic constructor
+     457             :          @param rEarth          distance from Earth to the Galactic centre [in meters]
+     458             :          @param beta            parameter that shifts radially the maximum of the distributions 
+     459             :          @param zg                      exponential cut-off parameter in the z-direction [in meters]
+     460             :          @param rBlur           relative smearing factor for radius
+     461             :          @param thetaBlur       smearing factor for the angle [in 1 / meters]
+     462             :          */     
+     463             :         SourcePulsarDistribution(double rEarth, double beta, double zg, double rBlur, double thetaBlur);
+     464             :         void prepareParticle(ParticleState &particle) const;
+     465             : 
+     466             :         /** 
+     467             :          radial distribution of pulsars
+     468             :          @param r       galactocentric radius
+     469             :         */
+     470             :         double fr(double r) const;
+     471             :         /**
+     472             :          z distribution of pulsars
+     473             :          @param z       height over/under the galactic plane
+     474             :         */
+     475             :         double fz(double z) const;
+     476             :         double ftheta(int i, double r) const;
+     477             :         double blurR(double r_tilde) const;
+     478             :         double blurTheta(double theta_tilde, double r_tilde) const;
+     479             :         void setFrMax(double R, double b);
+     480             :         void setFzMax(double zg);
+     481             :         void setRMax(double rMax);
+     482             :         void setZMax(double zMax);
+     483             :         void setRBlur(double rBlur);
+     484             :         void setThetaBlur(double thetaBlur);
+     485             :         double getFrMax();
+     486             :         double getFzMax();
+     487             :         double getRMax();
+     488             :         double getZMax();
+     489             :         double getRBlur();
+     490             :         double getThetaBlur();
+     491             :         void setDescription();
+     492             : };
+     493             : 
+     494             : 
+     495             : /**
+     496             :  @class SourceUniform1D
+     497             :  @brief Uniform source distribution in 1D
+     498             : 
+     499             :  This source property sets random x-coordinates according to a uniform source
+     500             :  distribution in a given distance interval. If cosmological effects are included, 
+     501             :  this is done by drawing a light-travel distance from a flat distribution and
+     502             :  converting to a comoving distance. In the absence of cosmological effects, the
+     503             :  positions are drawn uniformly in the light-travel distance interval (as opposed
+     504             :  to a comoving interval).
+     505             :  The source positions are assigned to the x-coordinate (Vector3d(distance, 0, 0))
+     506             :  in this one-dimensional case.
+     507             :  */
+     508             : class SourceUniform1D: public SourceFeature {
+     509             :         double minD; // minimum light-travel distance
+     510             :         double maxD; // maximum light-travel distance
+     511             :         bool withCosmology;     // whether to account for cosmological effects (expansion of the Universe)
+     512             : public:
+     513             :         /** Constructor
+     514             :          @param minD                    minimum distance; comoving if withCosmology is True
+     515             :          @param maxD                    maximum distance; comoving if withCosmology is True
+     516             :          @param withCosmology   whether to account for cosmological effects (expansion of the Universe)
+     517             :          */
+     518             :         SourceUniform1D(double minD, double maxD, bool withCosmology = true);
+     519             :         void prepareParticle(ParticleState& particle) const;
+     520             :         void setDescription();
+     521             : };
+     522             : 
+     523             : 
+     524             : /**
+     525             :  @class SourceDensityGrid
+     526             :  @brief Random source positions from a density grid
+     527             :  */
+     528             : class SourceDensityGrid: public SourceFeature {
+     529             :         ref_ptr<Grid1f> grid;
+     530             : public:
+     531             :         /** Constructor
+     532             :          @param densityGrid     3D grid containing the density of sources in each cell
+     533             :          */
+     534             :         SourceDensityGrid(ref_ptr<Grid1f> densityGrid);
+     535             :         void prepareParticle(ParticleState &particle) const;
+     536             :         void setDescription();
+     537             : };
+     538             : 
+     539             : 
+     540             : /**
+     541             :  @class SourceDensityGrid1D
+     542             :  @brief Random source positions from a 1D density grid
+     543             :  */
+     544             : class SourceDensityGrid1D: public SourceFeature {
+     545             :         ref_ptr<Grid1f> grid;     // 1D grid with Ny = Nz = 1
+     546             : public:
+     547             :         /** Constructor
+     548             :          @param densityGrid     1D grid containing the density of sources in each cell, Ny and Nz must be 1
+     549             :          */
+     550             :         SourceDensityGrid1D(ref_ptr<Grid1f> densityGrid);
+     551             :         void prepareParticle(ParticleState &particle) const;
+     552             :         void setDescription();
+     553             : };
+     554             : 
+     555             : 
+     556             : /**
+     557             :  @class SourceIsotropicEmission
+     558             :  @brief Isotropic emission from a source
+     559             :  */
+     560             : class SourceIsotropicEmission: public SourceFeature {
+     561             : public:
+     562             :         /** Constructor
+     563             :          */
+     564             :         SourceIsotropicEmission();
+     565             :         void prepareParticle(ParticleState &particle) const;
+     566             :         void setDescription();
+     567             : };
+     568             : 
+     569             : 
+     570             : /**
+     571             :  @class SourceDirectedEmission
+     572             :  @brief Directed emission from a source from the von-Mises-Fisher distribution 
+     573             :  
+     574             :  The emission from the source is generated following the von-Mises-Fisher distribution
+     575             :  with mean direction mu and concentration parameter kappa.
+     576             :  The sampling from the vMF distribution follows this document by Julian Straub:
+     577             :  http://people.csail.mit.edu/jstraub/download/straub2017vonMisesFisherInference.pdf
+     578             :  The emitted particles are assigned a weight so that the detected particles can be
+     579             :  reweighted to an isotropic emission distribution instead of a vMF distribution.
+     580             :  For details, see PoS (ICRC2019) 447.
+     581             :  */
+     582           1 : class SourceDirectedEmission: public SourceFeature {
+     583             :         Vector3d mu; // Mean emission direction in the vMF distribution
+     584             :         double kappa; // Concentration parameter of the vMF distribution
+     585             : public:
+     586             :         /** Constructor
+     587             :          @param mu      mean direction of the emission, mu should be normelized
+     588             :          @param kappa   concentration parameter
+     589             :         */
+     590             :         SourceDirectedEmission(Vector3d mu, double kappa);
+     591             :         void prepareCandidate(Candidate &candidate) const;
+     592             :         void setDescription();
+     593             : };
+     594             : 
+     595             : /**
+     596             :  @class SourceLambertDistributionOnSphere
+     597             :  @brief Uniform random position on a sphere with isotropic Lamberts distributed directions.
+     598             : 
+     599             :  This function should be used for crosschecking the arrival distribution for a
+     600             :  Galactic propagation with an isotropic arrival distribution at the Edge of our
+     601             :  Galaxy. Note, that for simulation speed you should rather use the backtracking
+     602             :  technique: see e.g. http://physik.rwth-aachen.de/parsec
+     603             :  */
+     604             : class SourceLambertDistributionOnSphere: public SourceFeature {
+     605             :         Vector3d center;        // center of the sphere
+     606             :         double radius;          // radius of the sphere
+     607             :         bool inward;            // if true, direction point inwards
+     608             : public:
+     609             :         /** Constructor
+     610             :          @param center          vector containing the coordinates of the center of the sphere
+     611             :          @param radius          radius of the sphere
+     612             :          @param inward          if true, the directions point inwards
+     613             :          */
+     614             :         SourceLambertDistributionOnSphere(const Vector3d &center, double radius, bool inward);
+     615             :         void prepareParticle(ParticleState &particle) const;
+     616             :         void setDescription();
+     617             : };
+     618             : 
+     619             : 
+     620             : /**
+     621             :  @class SourceDirection
+     622             :  @brief Collimated emission along a specific direction
+     623             :  */
+     624             : class SourceDirection: public SourceFeature {
+     625             :         Vector3d direction;
+     626             : public:
+     627             :         /** Constructor
+     628             :          @param direction       Vector3d corresponding to the direction of emission
+     629             :          */
+     630             :         SourceDirection(Vector3d direction = Vector3d(-1, 0, 0));
+     631             :         void prepareParticle(ParticleState &particle) const;
+     632             :         void setDescription();
+     633             : };
+     634             : 
+     635             : 
+     636             : /**
+     637             :  @class SourceEmissionMap
+     638             :  @brief Deactivate Candidate if it has zero probability in provided EmissionMap. 
+     639             : 
+     640             :         This feature does not change the direction of the candidate. Therefore a usefull direction feature (isotropic or directed emission)
+     641             :         must be added to the sources before. The propability of the emission map is not taken into account. 
+     642             :  */
+     643             : class SourceEmissionMap: public SourceFeature {
+     644             :         ref_ptr<EmissionMap> emissionMap;
+     645             : public:
+     646             :         /** Constructor
+     647             :          @param emissionMap             emission map containing probabilities of emission in various directions
+     648             :          */
+     649             :         SourceEmissionMap(EmissionMap *emissionMap);
+     650             :         void prepareCandidate(Candidate &candidate) const;
+     651             :         void setEmissionMap(EmissionMap *emissionMap);
+     652             :         void setDescription();
+     653             : };
+     654             : 
+     655             : 
+     656             : /**
+     657             :  @class SourceEmissionCone
+     658             :  @brief Uniform emission within a cone
+     659             :  */
+     660           1 : class SourceEmissionCone: public SourceFeature {
+     661             :         Vector3d direction;
+     662             :         double aperture;
+     663             : public:
+     664             :         /** Constructor
+     665             :          @param direction               Vector3d corresponding to the cone axis 
+     666             :          @param aperture                opening angle of the cone
+     667             :          */
+     668             :         SourceEmissionCone(Vector3d direction, double aperture);
+     669             :         void prepareParticle(ParticleState &particle) const;
+     670             : 
+     671             :         /**
+     672             :          @param direction Vector3d corresponding to the cone axis
+     673             :         */
+     674             :         void setDirection(Vector3d direction);
+     675             :         void setDescription();
+     676             : };
+     677             : 
+     678             : 
+     679             : /**
+     680             :  @class SourceRedshift
+     681             :  @brief Emission of particles at a specific redshift (or time)
+     682             : 
+     683             :  The redshift coordinate is used to treat cosmological effects and as a time coordinate.
+     684             :  Consider, for instance, a source located at a distance corresponding to a redshift z. 
+     685             :  In the absence of processes that cause time delays (e.g., magnetic deflections), particles
+     686             :  from this source could arrive after a time corresponding to the source redshift. Charged 
+     687             :  particles, on the other hand, can arrive at a time later than the corresponding straight-
+     688             :  line travel duration. 
+     689             :  This treatment is also useful for time-dependent studies (e.g. transient sources).
+     690             :  */
+     691             : class SourceRedshift: public SourceFeature {
+     692             :         double z;
+     693             : public:
+     694             :         /** Constructor
+     695             :          @param z               redshift of emission
+     696             :          */
+     697             :         SourceRedshift(double z);
+     698             :         void prepareCandidate(Candidate &candidate) const;
+     699             :         void setDescription();
+     700             : };
+     701             : 
+     702             : 
+     703             : /**
+     704             :  @class SourceUniformRedshift
+     705             :  @brief Random redshift (time of emission) from a uniform distribution
+     706             : 
+     707             :  This function assigns random redshifts to the particles emitted by a given source.
+     708             :  These values are drawn from a uniform redshift distribution in the interval [zmin, zmax].
+     709             :  The redshift coordinate is used to treat cosmological effects and as a time coordinate.
+     710             :  Consider, for instance, a source located at a distance corresponding to a redshift z. 
+     711             :  In the absence of processes that cause time delays (e.g., magnetic deflections), particles
+     712             :  from this source could arrive after a time corresponding to the source redshift. Charged 
+     713             :  particles, on the other hand, can arrive at a time later than the corresponding straight-
+     714             :  line travel duration. 
+     715             :  This treatment is also useful for time-dependent studies (e.g. transient sources).
+     716             :  */
+     717             : class SourceUniformRedshift: public SourceFeature {
+     718             :         double zmin, zmax;
+     719             : public:
+     720             :         /** Constructor
+     721             :          @param zmin    minimum redshift
+     722             :          @param zmax    maximum redshift
+     723             :          */
+     724             :         SourceUniformRedshift(double zmin, double zmax);
+     725             :         void prepareCandidate(Candidate &candidate) const;
+     726             :         void setDescription();
+     727             : };
+     728             : 
+     729             : 
+     730             : /**
+     731             :  @class SourceRedshiftEvolution
+     732             :  @brief Random redshift (time of emission) from (1+z)^m distribution
+     733             : 
+     734             :  This assigns redshifts to a given source according to a typical power-law distribution.
+     735             :  The redshift coordinate is used to treat cosmological effects and as a time coordinate.
+     736             :  Consider, for instance, a source located at a distance corresponding to a redshift z. 
+     737             :  In the absence of processes that cause time delays (e.g., magnetic deflections), particles
+     738             :  from this source could arrive after a time corresponding to the source redshift. Charged 
+     739             :  particles, on the other hand, can arrive at a time later than the corresponding straight-
+     740             :  line travel duration. 
+     741             :  This treatment is also useful for time-dependent studies (e.g. transient sources).
+     742             :  */
+     743           2 : class SourceRedshiftEvolution: public SourceFeature {
+     744             :         double zmin, zmax;
+     745             :         double m;
+     746             : public:
+     747             :         /** Constructor
+     748             :          @param m               index of the power law (1 + z)^m
+     749             :          @param zmin    minimum redshift
+     750             :          @param zmax    maximum redshift
+     751             :          */
+     752             :         SourceRedshiftEvolution(double m, double zmin, double zmax);
+     753             :         void prepareCandidate(Candidate &candidate) const;
+     754             : };
+     755             : 
+     756             : 
+     757             : /**
+     758             :  @class SourceRedshift1D
+     759             :  @brief Redshift according to the distance to 0
+     760             : 
+     761             :  This source property sets the redshift according to the distance from 
+     762             :  the source to the origin (0, 0, 0). 
+     763             :  It must be added after the position of the source is set because it
+     764             :  computes the redshifts based on the source distance.
+     765             :  */
+     766             : class SourceRedshift1D: public SourceFeature {
+     767             : public:
+     768             :         /** Constructor
+     769             :          */
+     770             :         SourceRedshift1D();
+     771             :         void prepareCandidate(Candidate &candidate) const;
+     772             :         void setDescription();
+     773             : };
+     774             : 
+     775             : 
+     776             : #ifdef CRPROPA_HAVE_MUPARSER
+     777             : /**
+     778             :  @class SourceGenericComposition
+     779             :  @brief Add multiple cosmic rays with energies described by an expression string
+     780             : 
+     781             :  This is particularly useful if an arbitrary combination of nuclei types with 
+     782             :  specific energy spectra. The strings parsed may contain 'A' (atomic mass), 
+     783             :  'Z' (atomic number).  The following units are recognized as part of the strings:
+     784             :  GeV, TeV, PeV, EeV.  The variable for energy is 'E', with limits 'Emin', 'Emax'.
+     785             :  This property only works if muparser is available.
+     786             :  For details about the library see:
+     787             :         https://beltoforion.de/en/muparser/
+     788             :  */
+     789             : class SourceGenericComposition: public SourceFeature {
+     790             : public:
+     791           7 :         struct Nucleus {
+     792             :                 int id;
+     793             :                 std::vector<double> cdf;
+     794             :         };
+     795             :         /** Constructor
+     796             :          @param Emin            minimum energy [in Joules]
+     797             :          @param Emax            maximum energy [in Joules]
+     798             :          @param expression      string containing the expression to generate the composition
+     799             :          @param bins            number of energy bins
+     800             :          */
+     801             :         SourceGenericComposition(double Emin, double Emax, std::string expression, size_t bins = 1024);
+     802             :         /** Add an individual particle id.
+     803             :          @param id                      id of the particle following the PDG numbering scheme
+     804             :          @param abundance       relative abundance of individual particle species
+     805             :          */
+     806             :         void add(int id, double abundance);
+     807             :         /** Add an individual particle id.
+     808             :          @param A                       atomic mass of the cosmic-ray nucleus
+     809             :          @param Z                       atomic number of the cosmic-ray nucleus
+     810             :          @param abundance       relative abundance of individual particle species
+     811             :          */
+     812             :         void add(int A, int Z, double abundance);
+     813             :         void prepareParticle(ParticleState &particle) const;
+     814             :         void setDescription();
+     815             : 
+     816             :         const std::vector<double> *getNucleusCDF(int id) const {
+     817           0 :                 for (size_t i = 0; i < nuclei.size(); i++) {
+     818           0 :                         if (nuclei[i].id == id)
+     819           0 :                                 return &nuclei[i].cdf;
+     820             :                 }
+     821             :                 return 0;
+     822             :         }
+     823             : 
+     824             : protected:
+     825             :         double Emin, Emax;
+     826             :         size_t bins;
+     827             :         std::string expression;
+     828             :         std::vector<double> energy;
+     829             : 
+     830             :         std::vector<Nucleus> nuclei;
+     831             :         std::vector<double> cdf;
+     832             : 
+     833             : };
+     834             : #endif
+     835             : 
+     836             : /**
+     837             :  * @class SourceTag
+     838             :  * @brief All candidates from this source get a given tag. This can be used to distinguish between different sources that follow the same spatial distribution
+     839             :  * 
+     840             :  * Sets the tag of the candidate. Can be used to trace back additional candidate properties, e.g. production interaction or source type. 
+     841             :  * The interaction overwrites the candidate tag from the source for all secondaries. 
+     842             :  */
+     843             : 
+     844             : class SourceTag: public SourceFeature {
+     845             : private:
+     846             :         std::string sourceTag;
+     847             : 
+     848             : public:
+     849             :         SourceTag(std::string tag);
+     850             :         void prepareCandidate(Candidate &candidate) const;
+     851             :         void setDescription();
+     852             :         void setTag(std::string tag);
+     853             : };
+     854             : 
+     855             : /**
+     856             :         @class SourceMassDistribution
+     857             :         @brief  Source position follows a given mass distribution
+     858             : 
+     859             :         The (source)position of the candidate is sampled from a given mass distribution. The distribution uses the getDensity function of the density module. 
+     860             :         If a weighting for different components is desired, the use of different densities in a densityList is recommended.
+     861             : 
+     862             :         The sampling range of the position can be restricted. Default is a sampling for x in [-20, 20] * kpc, y in [-20, 20] * kpc and z in [-4, 4] * kpc.
+     863             : */
+     864             : class SourceMassDistribution: public SourceFeature {
+     865             : private: 
+     866             :         ref_ptr<Density> density; //< density distribution
+     867             :         double maxDensity;                      //< maximal value of the density in the region of interest
+     868             :         double xMin, xMax;                      //< x-range to sample positions
+     869             :         double yMin, yMax;                      //< y-range to sample positions
+     870             :         double zMin, zMax;                      //< z-range to sample positions
+     871             :         int maxTries = 10000;           //< maximal number of tries to sample the position 
+     872             : 
+     873             : public: 
+     874             :         /** Constructor
+     875             :         @param density: CRPropa mass distribution 
+     876             :         @param maxDensity:      maximal density in the region where the position should be sampled
+     877             :         @param x:       the position will be sampled in the range [-x, x]. Non symmetric values can be set with setXrange.
+     878             :         @param y:       the position will be sampled in the range [-y, y]. Non symmetric values can be set with setYrange.
+     879             :         @param z:       the position will be sampled in the range [-z, z]. Non symmetric values can be set with setZrange.
+     880             :         */
+     881             :         SourceMassDistribution(ref_ptr<Density> density, double maxDensity = 0, double x = 20 * kpc, double y = 20 * kpc, double z = 4 * kpc);
+     882             : 
+     883             :         void prepareParticle(ParticleState &particle) const;
+     884             : 
+     885             :         /** Set the maximal density in the region of interest. This parameter is necessary for the sampling
+     886             :         @param maxDensity:      maximal density in [particle / m^3]
+     887             :         */
+     888             :         void setMaximalDensity(double maxDensity);
+     889             : 
+     890             :         /** set x-range in which the position of the candidate will be sampled. x in [xMin, xMax].
+     891             :         @param xMin: minimal x value of the allowed sample range in [m]
+     892             :         @param xMax: maximal x value of the allowed sample range in [m]
+     893             :         */
+     894             :         void setXrange(double xMin, double xMax);
+     895             : 
+     896             :         /** set y-range in which the position of the candidate will be sampled. y in [yMin, yMax].
+     897             :         @param yMin: minimal y value of the allowed sample range in [m]
+     898             :         @param yMax: maximal y value of the allowed sample range in [m]
+     899             :         */
+     900             :         void setYrange(double yMin, double yMax);
+     901             : 
+     902             :         /** set z-range in which the position of the candidate will be sampled. z in [zMin, zMax].
+     903             :         @param zMin: minimal z value of the allowed sample range in [m]
+     904             :         @param zMax: maximal z value of the allowed sample range in [m]
+     905             :         */
+     906             :         void setZrange(double zMin, double zMax);
+     907             : 
+     908             :         /*      samples the position. Can be used for testing.
+     909             :                 @return Vector3d with sampled position
+     910             :         */
+     911             :         Vector3d samplePosition() const;
+     912             : 
+     913             : 
+     914             :         /** set the number of maximal tries until the sampling routine breaks.
+     915             :                 @param tries: number of the maximal tries
+     916             :         */
+     917             :         void setMaximalTries(int tries);
+     918             : 
+     919             :         std::string getDescription();
+     920             : };
+     921             : 
+     922             : /**  @} */ // end of group SourceFeature
+     923             : 
+     924             : } // namespace crpropa
+     925             : 
+     926             : #endif // CRPROPA_SOURCE_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html new file mode 100644 index 000000000..fa4e80473 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Variant.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Variant.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:133537.1 %
Date:2024-04-08 14:58:22Functions:41625.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10safeDeleteINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEEvRPT_0
_ZN7crpropa10safeDeleteISt6vectorINS_7VariantESaIS2_EEEEvRPT_0
_ZN7crpropa7Variant14bad_conversionC2ENS0_4TypeES2_0
_ZN7crpropa7Variant14bad_conversionD0Ev0
_ZN7crpropa7Variant14bad_conversionD2Ev0
_ZN7crpropa7VariantaSERKNS_7Vector3ISt7complexIdEEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IdEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IfEE0
_ZN7crpropa7VariantaSERKSt6vectorIS0_SaIS0_EE0
_ZN7crpropa7VariantaSERKSt7complexIdE0
_ZN7crpropa7VariantaSERKSt7complexIfE0
_ZNK7crpropa7Variant14bad_conversion4whatEv0
_ZN7crpropa7VariantC2ERKSt6vectorIS0_SaIS0_EE1
_ZNK7crpropa7VariantcvNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEv1
_ZN7crpropa7VariantC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1130
_ZN7crpropa7VariantaSERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1136
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Variant.h.func.html b/doc/coverageReport/include/crpropa/Variant.h.func.html new file mode 100644 index 000000000..070430d10 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Variant.h.func.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Variant.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Variant.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:133537.1 %
Date:2024-04-08 14:58:22Functions:41625.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10safeDeleteINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEEvRPT_0
_ZN7crpropa10safeDeleteISt6vectorINS_7VariantESaIS2_EEEEvRPT_0
_ZN7crpropa7Variant14bad_conversionC2ENS0_4TypeES2_0
_ZN7crpropa7Variant14bad_conversionD0Ev0
_ZN7crpropa7Variant14bad_conversionD2Ev0
_ZN7crpropa7VariantC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1130
_ZN7crpropa7VariantC2ERKSt6vectorIS0_SaIS0_EE1
_ZN7crpropa7VariantaSERKNS_7Vector3ISt7complexIdEEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IdEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IfEE0
_ZN7crpropa7VariantaSERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1136
_ZN7crpropa7VariantaSERKSt6vectorIS0_SaIS0_EE0
_ZN7crpropa7VariantaSERKSt7complexIdE0
_ZN7crpropa7VariantaSERKSt7complexIfE0
_ZNK7crpropa7Variant14bad_conversion4whatEv0
_ZNK7crpropa7VariantcvNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Variant.h.gcov.html b/doc/coverageReport/include/crpropa/Variant.h.gcov.html new file mode 100644 index 000000000..a97907206 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Variant.h.gcov.html @@ -0,0 +1,410 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Variant.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Variant.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:133537.1 %
Date:2024-04-08 14:58:22Functions:41625.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : //-------------------------------------------------------------
+       2             : // Based on Variant.hh of the Physics eXtension Library (PXL) -
+       3             : // http://vispa.physik.rwth-aachen.de/                        -
+       4             : // Licensed under a LGPL-2 or later license                   -
+       5             : //-------------------------------------------------------------
+       6             : 
+       7             : #ifndef CRPROPA_VARIANT_H
+       8             : #define CRPROPA_VARIANT_H
+       9             : 
+      10             : #include <complex>
+      11             : #include <cstdint>
+      12             : #include <cstdlib>
+      13             : #include <cstring>
+      14             : #include <iostream>
+      15             : #include <limits>
+      16             : #include <string>
+      17             : #include <sstream>
+      18             : #include <stdexcept>
+      19             : #include <typeinfo>
+      20             : 
+      21             : #include "crpropa/Vector3.h"
+      22             : 
+      23             : 
+      24             : 
+      25             : // defines copy constructor X(const X&), isX(), asX(), fromX(), toX(), op(), op=, op==, op!=
+      26             : #define VARIANT_ADD_TYPE_DECL_POD(NAME, TYPE, VALUE, FIELD) \
+      27             :         Variant(const VALUE& v) { \
+      28             :                 data._t_##FIELD = v; \
+      29             :                 type = TYPE;  \
+      30             :         } \
+      31             :         bool is##NAME() const { \
+      32             :                 return type == TYPE; \
+      33             :         } \
+      34             :         VALUE& as##NAME() { \
+      35             :                 check(TYPE); \
+      36             :                 return data._t_##FIELD; \
+      37             :         } \
+      38             :         const VALUE& as##NAME() const { \
+      39             :                 check(TYPE); \
+      40             :                 return data._t_##FIELD; \
+      41             :         } \
+      42             :         static Variant from##NAME(const VALUE& v) { \
+      43             :                 return Variant(v); \
+      44             :         } \
+      45             :         VALUE to##NAME() const; \
+      46             :         operator VALUE() const { \
+      47             :                 return to##NAME(); \
+      48             :         } \
+      49             :         Variant& operator=(const VALUE& v) { \
+      50             :                 clear(); \
+      51             :                 type = TYPE; \
+      52             :                 data._t_##FIELD = v; \
+      53             :                 return *this; \
+      54             :         } \
+      55             :         bool operator==(const VALUE& v) const { \
+      56             :                 check(TYPE); \
+      57             :                 return data._t_##FIELD == v; \
+      58             :         } \
+      59             :         bool operator!=(const VALUE& v) const { \
+      60             :                 check(TYPE); \
+      61             :                 return data._t_##FIELD != v; \
+      62             :         } \
+      63             : 
+      64             : // defines isX(), asX(), fromX()
+      65             : #define VARIANT_ADD_TYPE_DECL_PTR_BASE(NAME, TYPE, VALUE, FIELD) \
+      66             :         bool is##NAME() const { \
+      67             :                 return type == TYPE; \
+      68             :         } \
+      69             :         VALUE& as##NAME() { \
+      70             :                 check(TYPE); \
+      71             :                 return *data._t_##FIELD; \
+      72             :         } \
+      73             :         const VALUE& as##NAME() const { \
+      74             :                 check(TYPE); \
+      75             :                 return *data._t_##FIELD; \
+      76             :         } \
+      77             :         static Variant from##NAME(const VALUE& v) { \
+      78             :                 return Variant(v); \
+      79             :         } \
+      80             : 
+      81             : // defines isX(), asX(), fromX(), and copy constructor X(const X&), op=, op==, op!=
+      82             : #define VARIANT_ADD_TYPE_DECL_PTR(NAME, TYPE, VALUE, FIELD) \
+      83             :         VARIANT_ADD_TYPE_DECL_PTR_BASE(NAME, TYPE, VALUE, FIELD) \
+      84             :         Variant(const VALUE& v) { \
+      85             :                 data._t_##FIELD = new VALUE(v); \
+      86             :                 type = TYPE; \
+      87             :         } \
+      88             :         Variant& operator=(const VALUE& v) { \
+      89             :                 if (type != TYPE) { \
+      90             :                         clear(); \
+      91             :                         data._t_##FIELD = new VALUE();\
+      92             :                 } \
+      93             :                 type = TYPE; \
+      94             :                 (*data._t_##FIELD) = v; \
+      95             :                 return *this; \
+      96             :         } \
+      97             :         bool operator==(const VALUE& v) const { \
+      98             :                 check(TYPE); \
+      99             :                 return *data._t_##FIELD == v; \
+     100             :         } \
+     101             :         bool operator!=(const VALUE& v) const { \
+     102             :                 return !(*this == v); \
+     103             :         } \
+     104             : 
+     105             : #define VARIANT_ADD_ITER_DECL_PTR(NAME, TYPE, FIELD) \
+     106             :         typedef FIELD##_t::iterator FIELD##_iterator; \
+     107             :         typedef FIELD##_t::const_iterator FIELD##_const_iterator; \
+     108             :         inline FIELD##_iterator begin##NAME() { \
+     109             :                 check(TYPE); \
+     110             :                 return data._t_##FIELD->begin(); \
+     111             :         } \
+     112             :         inline FIELD##_iterator end##NAME() { \
+     113             :                 check(TYPE); \
+     114             :                 return data._t_##FIELD->end(); \
+     115             :         } \
+     116             :         inline FIELD##_const_iterator begin##NAME() const { \
+     117             :                 check(TYPE); \
+     118             :                 return data._t_##FIELD->begin(); \
+     119             :         } \
+     120             :         inline FIELD##_const_iterator end##NAME() const { \
+     121             :                 check(TYPE); \
+     122             :                 return data._t_##FIELD->end(); \
+     123             :         }                                                                                
+     124             : 
+     125             : 
+     126             : 
+     127             : namespace crpropa {
+     128             : 
+     129             : /**
+     130             :  @class Variant
+     131             :  @brief storage container for data types as e.g. int, float, string, etc.
+     132             : 
+     133             :  Allows storage of multiple data types in one base class. Used to construct a map of `arbitrary' data types.
+     134             :  Note that most default C++ types allow default conversions from `Variant` to the corresponding type.
+     135             :  Types that require an explicit call via `toTargetType()` are: complex (float and double), Vector3, and vector<Variant>.
+     136             :  */
+     137             : class Variant {
+     138             : public:
+     139             :         enum Type {
+     140             :                 TYPE_NONE = 0,
+     141             :                 TYPE_BOOL,
+     142             :                 TYPE_CHAR,
+     143             :                 TYPE_UCHAR,
+     144             :                 TYPE_INT16,
+     145             :                 TYPE_UINT16,
+     146             :                 TYPE_INT32,
+     147             :                 TYPE_UINT32,
+     148             :                 TYPE_INT64,
+     149             :                 TYPE_UINT64,
+     150             :                 TYPE_FLOAT,
+     151             :                 TYPE_DOUBLE,
+     152             :                 TYPE_LONGDOUBLE,
+     153             :                 TYPE_COMPLEXF,
+     154             :                 TYPE_COMPLEXD,
+     155             :                 TYPE_STRING,
+     156             :                 TYPE_VECTOR3F,
+     157             :                 TYPE_VECTOR3D,
+     158             :                 TYPE_VECTOR3C,
+     159             :                 TYPE_VECTOR
+     160             :         };
+     161             : 
+     162             :         class bad_conversion: public std::exception {
+     163             :                 protected:
+     164             :                         std::string msg;
+     165             :                 public:
+     166           0 :                         const char* what() const throw () {
+     167           0 :                                 return msg.c_str();
+     168             :                         }
+     169             : 
+     170           0 :                         bad_conversion(Type f, Type t) {
+     171             :                                 msg = "Variant: bad conversion from '";
+     172           0 :                                 msg += Variant::getTypeName(f);
+     173             :                                 msg += "' to '";
+     174           0 :                                 msg += Variant::getTypeName(t);
+     175             :                                 msg += "'";
+     176           0 :                         }
+     177             : 
+     178           0 :                         ~bad_conversion() throw () {
+     179           0 :                         }
+     180             :         };
+     181             : 
+     182             :         typedef std::complex<float> complex_f;
+     183             :         typedef std::complex<double> complex_d;
+     184             :         typedef Vector3<std::complex<double>> Vector3c;
+     185             :         typedef std::vector<Variant> vector_t;
+     186             : 
+     187             : protected:
+     188             :         Type type;
+     189             : 
+     190             :         union {
+     191             :                 bool _t_bool;
+     192             :                 char _t_char;
+     193             :                 unsigned char _t_uchar;
+     194             :                 int16_t _t_int16;
+     195             :                 uint16_t _t_uint16;
+     196             :                 int32_t _t_int32;
+     197             :                 uint32_t _t_uint32;
+     198             :                 int64_t _t_int64;
+     199             :                 uint64_t _t_uint64;
+     200             :                 float _t_float;
+     201             :                 double _t_double;
+     202             :                 long double _t_ldouble;
+     203             :                 complex_f* _t_complex_f;
+     204             :                 complex_d* _t_complex_d;
+     205             :                 std::string* _t_string;
+     206             :                 Vector3f* _t_vector3f;
+     207             :                 Vector3d* _t_vector3d;
+     208             :                 Vector3c* _t_vector3c;
+     209             :                 vector_t* _t_vector;
+     210             :         } data;
+     211             : 
+     212             : 
+     213             : public:
+     214             :         Variant();
+     215             :         Variant(Type t);
+     216             :         Variant(const Variant& v);
+     217             :         Variant(const char* s);
+     218             :         ~Variant();
+     219             :         inline Type getType() const {
+     220           2 :                 return type;
+     221             :         }
+     222             :         const char* getTypeName() const;
+     223             :         static const char* getTypeName(Type t);
+     224             :         const std::type_info& getTypeInfo() const;
+     225             :         static Type toType(const std::string& name);                
+     226             :         std::string toString(const std::string& delimiter = "\t") const;
+     227             :         std::complex<float> toComplexFloat() const;
+     228             :         std::complex<double> toComplexDouble() const;
+     229             :         Vector3f toVector3f() const;
+     230             :         Vector3d toVector3d() const;
+     231             :         Vector3c toVector3c() const;
+     232             :         vector_t toVector() const;
+     233             :         static Variant fromString(const std::string& str, Type type);
+     234             :         void clear(Type t = TYPE_NONE);
+     235             :         bool isValid() const;
+     236             :         size_t size() const;
+     237             :         size_t getSizeOf() const;
+     238             :         size_t getSize() const;
+     239             :         void resize(size_t i);
+     240             :         size_t copyToBuffer(void* buffer);
+     241           1 :         operator std::string() const {
+     242           2 :                 return toString();
+     243             :         }
+     244             :         Variant& operator=(const Variant& v);
+     245             :         bool operator==(const Variant& v) const;
+     246             :         bool operator!=(const Variant& v) const;
+     247             :         bool operator!=(const char* a) const;
+     248             :         Variant& operator[](size_t i);
+     249             :         inline Variant& operator[](int i) {
+     250             :                 return operator[]((size_t) i);
+     251             :         }
+     252             :         const Variant& operator[](size_t i) const;
+     253             :         const Variant& operator[](int i) const {
+     254             :                 return operator[]((size_t) i);
+     255             :         }
+     256             :         operator vector_t&();
+     257             :         operator const vector_t&() const;
+     258             : 
+     259             : 
+     260             :         template<class T>
+     261             :         T to() const {
+     262             :                 throw bad_conversion(type, TYPE_NONE);
+     263             :         }
+     264             : 
+     265             :         // automatically-generated functions    
+     266           6 :         VARIANT_ADD_TYPE_DECL_POD(Bool, TYPE_BOOL, bool, bool)
+     267           0 :         VARIANT_ADD_TYPE_DECL_POD(Char, TYPE_CHAR, char, char)
+     268           0 :         VARIANT_ADD_TYPE_DECL_POD(UChar, TYPE_UCHAR, unsigned char, uchar)
+     269           0 :         VARIANT_ADD_TYPE_DECL_POD(Int16, TYPE_INT16, int16_t, int16)
+     270           0 :         VARIANT_ADD_TYPE_DECL_POD(UInt16, TYPE_UINT16, uint16_t, uint16)
+     271          12 :         VARIANT_ADD_TYPE_DECL_POD(Int32, TYPE_INT32, int32_t, int32)
+     272           0 :         VARIANT_ADD_TYPE_DECL_POD(UInt32, TYPE_UINT32, uint32_t, uint32)
+     273           6 :         VARIANT_ADD_TYPE_DECL_POD(Int64, TYPE_INT64, int64_t, int64)
+     274          16 :         VARIANT_ADD_TYPE_DECL_POD(UInt64, TYPE_UINT64, uint64_t, uint64)
+     275           0 :         VARIANT_ADD_TYPE_DECL_POD(Float, TYPE_FLOAT, float, float)
+     276          34 :         VARIANT_ADD_TYPE_DECL_POD(Double, TYPE_DOUBLE, double, double)
+     277           0 :         VARIANT_ADD_TYPE_DECL_POD(LongDouble, TYPE_LONGDOUBLE, long double, ldouble)
+     278           0 :         VARIANT_ADD_TYPE_DECL_PTR(ComplexFloat, TYPE_COMPLEXF, std::complex<float>, complex_f)
+     279           1 :         VARIANT_ADD_TYPE_DECL_PTR(ComplexDouble, TYPE_COMPLEXD, std::complex<double>, complex_d)
+     280        3396 :         VARIANT_ADD_TYPE_DECL_PTR(String, TYPE_STRING, std::string, string)
+     281           0 :         VARIANT_ADD_TYPE_DECL_PTR(Vector3f, TYPE_VECTOR3F, Vector3f, vector3f)
+     282           1 :         VARIANT_ADD_TYPE_DECL_PTR(Vector3d, TYPE_VECTOR3D, Vector3d, vector3d)
+     283           1 :         VARIANT_ADD_TYPE_DECL_PTR(Vector3c, TYPE_VECTOR3C, Vector3c, vector3c)
+     284           2 :         VARIANT_ADD_TYPE_DECL_PTR(Vector, TYPE_VECTOR, vector_t, vector)
+     285             :         VARIANT_ADD_ITER_DECL_PTR(Vector, TYPE_VECTOR, vector)
+     286             :                 
+     287             : private:
+     288             :         void copy(const Variant& v);
+     289             :         void check(const Type t) const;
+     290             :         void check(const Type t);
+     291             : };
+     292             : 
+     293             : #define VARIANT_TO_DECL(NAME, VALUE) \
+     294             :         template<> inline VALUE Variant::to<VALUE>() const { \
+     295             :                 return to##NAME(); \
+     296             :         } \
+     297             : 
+     298             : // declare type conversion functions
+     299             : // not implemented for Vector3 and complex_*
+     300             : VARIANT_TO_DECL(Bool, bool)
+     301             : VARIANT_TO_DECL(Char, char)
+     302             : VARIANT_TO_DECL(UChar, unsigned char)
+     303             : VARIANT_TO_DECL(Int16, int16_t)
+     304             : VARIANT_TO_DECL(UInt16, uint16_t)
+     305             : VARIANT_TO_DECL(Int32, int32_t)
+     306             : VARIANT_TO_DECL(UInt32, uint32_t)
+     307             : VARIANT_TO_DECL(Int64, int64_t)
+     308             : VARIANT_TO_DECL(UInt64, uint64_t)
+     309             : VARIANT_TO_DECL(Float, float)
+     310             : VARIANT_TO_DECL(Double, double)
+     311             : VARIANT_TO_DECL(LongDouble, long double)
+     312             : VARIANT_TO_DECL(String, std::string)
+     313             : VARIANT_TO_DECL(Vector, Variant::vector_t)
+     314             : 
+     315             : std::ostream& operator <<(std::ostream& os, const Variant &v);
+     316             : 
+     317             : 
+     318             : /**
+     319             :  Taken from PXL
+     320             :  https://git.rwth-aachen.de/3pia/pxl/pxl/-/blob/master/core/include/pxl/core/Functions.hh
+     321             :  */
+     322             : template <class T> 
+     323           0 : inline void safeDelete(T*& p) {
+     324           0 :         if (p) {
+     325           0 :                 delete p;
+     326           0 :                 p = 0;
+     327             :         }
+     328           0 : }
+     329             : 
+     330             : 
+     331             : 
+     332             : } // namespace crpropa 
+     333             : 
+     334             : #endif // CRPROPA_VARIANT
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html new file mode 100644 index 000000000..b44071763 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html @@ -0,0 +1,236 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Vector3.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Vector3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9915165.6 %
Date:2024-04-08 14:58:22Functions:164139.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Vector3IdE4setREd0
_ZN7crpropa7Vector3IdErMERKS1_0
_ZN7crpropa7Vector3IfE12setRThetaPhiEfff0
_ZN7crpropa7Vector3IfE4setREf0
_ZN7crpropa7Vector3IfErMERKS1_0
_ZN7crpropa7Vector3IfErMERKf0
_ZN7crpropalsISt7complexIdEEERSoS3_RKNS_7Vector3IT_EE0
_ZNK7crpropa7Vector3IdE4ceilEv0
_ZNK7crpropa7Vector3IdE4clipEdd0
_ZNK7crpropa7Vector3IdErmERKS1_0
_ZNK7crpropa7Vector3IdErmERKd0
_ZNK7crpropa7Vector3IfE10getRotatedERKS1_f0
_ZNK7crpropa7Vector3IfE13getDistanceToERKS1_0
_ZNK7crpropa7Vector3IfE13getParallelToERKS1_0
_ZNK7crpropa7Vector3IfE13getUnitVectorEv0
_ZNK7crpropa7Vector3IfE16getUnitVectorPhiEv0
_ZNK7crpropa7Vector3IfE18getPerpendicularToERKS1_0
_ZNK7crpropa7Vector3IfE18getUnitVectorThetaEv0
_ZNK7crpropa7Vector3IfE4ceilEv0
_ZNK7crpropa7Vector3IfE4clipEff0
_ZNK7crpropa7Vector3IfE5floorEv0
_ZNK7crpropa7Vector3IfE6getPhiEv0
_ZNK7crpropa7Vector3IfE8getThetaEv0
_ZNK7crpropa7Vector3IfErmERKS1_0
_ZNK7crpropa7Vector3IfErmERKf0
_ZN7crpropa7Vector3IdErMERKd1
_ZNK7crpropa7Vector3IdE18getPerpendicularToERKS1_1
_ZNK7crpropa7Vector3IdE18getUnitVectorThetaEv1
_ZNK7crpropa7Vector3IdE13getParallelToERKS1_2
_ZN7crpropa7Vector3IdE12setRThetaPhiEddd3
_ZNK7crpropa7Vector3IdE16getUnitVectorPhiEv4
_ZNK7crpropa7Vector3IdE5floorEv6
_ZNK7crpropa7Vector3IdE10getAngleToERKS1_8
_ZNK7crpropa7Vector3IdE8getThetaEv8
_ZN7crpropalsIdEERSoS1_RKNS_7Vector3IT_EE11
_ZNK7crpropa7Vector3IdE6getPhiEv19
_ZN7crpropalsIfEERSoS1_RKNS_7Vector3IT_EE27
_ZNK7crpropa7Vector3IdE13getDistanceToERKS1_110
_ZNK7crpropa7Vector3IdE10getRotatedERKS1_d481006
_ZNK7crpropa7Vector3IfE10getAngleToERKS1_691017
_ZNK7crpropa7Vector3IdE13getUnitVectorEv7201361
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Vector3.h.func.html b/doc/coverageReport/include/crpropa/Vector3.h.func.html new file mode 100644 index 000000000..8b3511c68 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Vector3.h.func.html @@ -0,0 +1,236 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Vector3.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Vector3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9915165.6 %
Date:2024-04-08 14:58:22Functions:164139.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Vector3IdE12setRThetaPhiEddd3
_ZN7crpropa7Vector3IdE4setREd0
_ZN7crpropa7Vector3IdErMERKS1_0
_ZN7crpropa7Vector3IdErMERKd1
_ZN7crpropa7Vector3IfE12setRThetaPhiEfff0
_ZN7crpropa7Vector3IfE4setREf0
_ZN7crpropa7Vector3IfErMERKS1_0
_ZN7crpropa7Vector3IfErMERKf0
_ZN7crpropalsISt7complexIdEEERSoS3_RKNS_7Vector3IT_EE0
_ZN7crpropalsIdEERSoS1_RKNS_7Vector3IT_EE11
_ZN7crpropalsIfEERSoS1_RKNS_7Vector3IT_EE27
_ZNK7crpropa7Vector3IdE10getAngleToERKS1_8
_ZNK7crpropa7Vector3IdE10getRotatedERKS1_d481006
_ZNK7crpropa7Vector3IdE13getDistanceToERKS1_110
_ZNK7crpropa7Vector3IdE13getParallelToERKS1_2
_ZNK7crpropa7Vector3IdE13getUnitVectorEv7201361
_ZNK7crpropa7Vector3IdE16getUnitVectorPhiEv4
_ZNK7crpropa7Vector3IdE18getPerpendicularToERKS1_1
_ZNK7crpropa7Vector3IdE18getUnitVectorThetaEv1
_ZNK7crpropa7Vector3IdE4ceilEv0
_ZNK7crpropa7Vector3IdE4clipEdd0
_ZNK7crpropa7Vector3IdE5floorEv6
_ZNK7crpropa7Vector3IdE6getPhiEv19
_ZNK7crpropa7Vector3IdE8getThetaEv8
_ZNK7crpropa7Vector3IdErmERKS1_0
_ZNK7crpropa7Vector3IdErmERKd0
_ZNK7crpropa7Vector3IfE10getAngleToERKS1_691017
_ZNK7crpropa7Vector3IfE10getRotatedERKS1_f0
_ZNK7crpropa7Vector3IfE13getDistanceToERKS1_0
_ZNK7crpropa7Vector3IfE13getParallelToERKS1_0
_ZNK7crpropa7Vector3IfE13getUnitVectorEv0
_ZNK7crpropa7Vector3IfE16getUnitVectorPhiEv0
_ZNK7crpropa7Vector3IfE18getPerpendicularToERKS1_0
_ZNK7crpropa7Vector3IfE18getUnitVectorThetaEv0
_ZNK7crpropa7Vector3IfE4ceilEv0
_ZNK7crpropa7Vector3IfE4clipEff0
_ZNK7crpropa7Vector3IfE5floorEv0
_ZNK7crpropa7Vector3IfE6getPhiEv0
_ZNK7crpropa7Vector3IfE8getThetaEv0
_ZNK7crpropa7Vector3IfErmERKS1_0
_ZNK7crpropa7Vector3IfErmERKf0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/Vector3.h.gcov.html b/doc/coverageReport/include/crpropa/Vector3.h.gcov.html new file mode 100644 index 000000000..f1fbcd9c0 --- /dev/null +++ b/doc/coverageReport/include/crpropa/Vector3.h.gcov.html @@ -0,0 +1,516 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/Vector3.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa - Vector3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9915165.6 %
Date:2024-04-08 14:58:22Functions:164139.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_VECTOR3_H
+       2             : #define CRPROPA_VECTOR3_H
+       3             : 
+       4             : #include <iostream>
+       5             : #include <cmath>
+       6             : #include <vector>
+       7             : #include <limits>
+       8             : #include <algorithm>
+       9             : 
+      10             : namespace crpropa {
+      11             : 
+      12             : /**
+      13             :  * \addtogroup Core
+      14             :  * @{
+      15             :  */
+      16             : 
+      17             : /**
+      18             :  @class Vector3
+      19             :  @brief Template class for 3-vectors of type float, double, ...
+      20             : 
+      21             :  Allows accessing and changing the elements x, y, z directly or  through the
+      22             :  corresponding get and set methods.
+      23             : 
+      24             :  Angle definitions are
+      25             :  phi [-pi, pi]: azimuthal angle in the x-y plane, 0 pointing in x-direction
+      26             :  theta [0, pi]: zenith angle towards the z axis, 0 pointing in z-direction
+      27             :  */
+      28             : template<typename T>
+      29             : class Vector3 {
+      30             : public:
+      31             :         union {
+      32             :                 struct
+      33             :                 {
+      34             :                         T x;
+      35             :                         T y;
+      36             :                         T z;
+      37             :                 };
+      38             :                 T data[3];
+      39             :         };
+      40             : 
+      41     3187045 :         Vector3() : data{0., 0., 0.} {
+      42             :         }
+      43             : 
+      44             :         // avoid creation of default non-conversion constructor
+      45    20387451 :         Vector3(const Vector3 &v) : data{v.data[0], v.data[1], v.data[2]} {
+      46           0 :         }
+      47             : 
+      48             :         // Provides implicit conversion
+      49             :         template<typename U>
+      50           0 :         Vector3(const Vector3<U> &v) {
+      51          14 :                 data[0] = v.x;
+      52           4 :                 data[1] = v.y;
+      53           4 :                 data[2] = v.z;
+      54           0 :         }
+      55             : 
+      56             :         ~Vector3()
+      57             :         {
+      58    26216757 :         }
+      59             : 
+      60           0 :         explicit Vector3(const double *v) {
+      61           0 :                 data[0] = v[0];
+      62           0 :                 data[1] = v[1];
+      63           0 :                 data[2] = v[2];
+      64             :         }
+      65             : 
+      66           0 :         explicit Vector3(const float *v) {
+      67           0 :                 data[0] = v[0];
+      68           0 :                 data[1] = v[1];
+      69           0 :                 data[2] = v[2];
+      70             :         }
+      71             : 
+      72    12617888 :         explicit Vector3(const T &X, const T &Y, const T &Z) : data{X, Y, Z} {
+      73             :         }
+      74             : 
+      75    18504508 :         explicit Vector3(T t) : data{t, t, t} {
+      76           1 :         }
+      77             : 
+      78             :         void setX(const T X) {
+      79           1 :                 x = X;
+      80             :         }
+      81             : 
+      82             :         void setY(const T Y) {
+      83           0 :                 y = Y;
+      84             :         }
+      85             : 
+      86             :         void setZ(const T Z) {
+      87           0 :                 z = Z;
+      88             :         }
+      89             : 
+      90             :         void setXYZ(const T X, const T Y, const T Z) {
+      91     1351680 :                 x = X;
+      92     1351680 :                 y = Y;
+      93     1351680 :                 z = Z;
+      94             :         }
+      95             : 
+      96           0 :         void setR(const T r) {
+      97           0 :                 *this *= r / getR();
+      98           0 :         }
+      99             : 
+     100           3 :         void setRThetaPhi(const T r, const T theta, const T phi) {
+     101           3 :                 x = r * sin(theta) * cos(phi);
+     102           3 :                 y = r * sin(theta) * sin(phi);
+     103           3 :                 z = r * cos(theta);
+     104           3 :         }
+     105             : 
+     106             :         T getX() const {
+     107      370007 :                 return x;
+     108             :         }
+     109             : 
+     110             :         T getY() const {
+     111      370006 :                 return y;
+     112             :         }
+     113             : 
+     114             :         T getZ() const {
+     115       40006 :                 return z;
+     116             :         }
+     117             : 
+     118             :         // magnitude (2-norm) of the vector
+     119             :         T getR() const {
+     120    25099477 :                 return std::sqrt(x * x + y * y + z * z);
+     121             :         }
+     122             : 
+     123             :         // square of magnitude of the vector
+     124             :         T getR2() const {
+     125     2883584 :                 return x * x + y * y + z * z;
+     126             :         }
+     127             : 
+     128             :         // return the azimuth angle
+     129          19 :         T getPhi() const {
+     130             :                 T eps = std::numeric_limits < T > ::min();
+     131          19 :                 if ((fabs(x) < eps) && (fabs(y) < eps))
+     132             :                         return 0.0;
+     133             :                 else
+     134          18 :                         return std::atan2(y, x);
+     135             :         }
+     136             : 
+     137             :         // return the zenith angle
+     138           8 :         T getTheta() const {
+     139             :                 T eps = std::numeric_limits < T > ::min();
+     140           8 :                 if ((fabs(x) < eps) && (fabs(y) < eps) && (fabs(z) < eps))
+     141             :                         return 0.0;
+     142             :                 else
+     143           8 :                         return atan2((T) sqrt(x * x + y * y), z);
+     144             :         }
+     145             : 
+     146             :         // return the unit-vector e_r
+     147     7201361 :         Vector3<T> getUnitVector() const {
+     148     7201361 :                 return *this / getR();
+     149             :         }
+     150             : 
+     151             :         // return the unit-vector e_theta
+     152           1 :         Vector3<T> getUnitVectorTheta() const {
+     153           1 :                 T theta = getTheta();
+     154           1 :                 T phi = getPhi();
+     155           1 :                 return Vector3<T>(cos(theta) * cos(phi), cos(theta) * sin(phi),
+     156           1 :                                 -sin(theta));
+     157             :         }
+     158             : 
+     159             :         // return the unit-vector e_phi
+     160           4 :         Vector3<T> getUnitVectorPhi() const {
+     161           4 :                 return Vector3<T>(-sin(getPhi()), cos(getPhi()), 0);
+     162             :         }
+     163             : 
+     164             :         // return the angle [0, pi] between the vectors
+     165      691025 :         T getAngleTo(const Vector3<T> &v) const {
+     166      691025 :                 T cosdistance = dot(v) / v.getR() / getR();
+     167             :                 // In some directions cosdistance is > 1 on some compilers
+     168             :                 // This ensures that the correct result is returned
+     169      691025 :                 if (cosdistance >= 1.)
+     170             :                         return 0;
+     171      690880 :                 else if (cosdistance <= -1.)
+     172             :                         return M_PI;
+     173             :                 else
+     174      690880 :                         return acos(cosdistance);
+     175             :         }
+     176             : 
+     177             :         // return true if the angle between the vectors is smaller than a threshold
+     178             :         bool isParallelTo(const Vector3<T> &v, T maxAngle) const {
+     179      691017 :                 return getAngleTo(v) < maxAngle;
+     180             :         }
+     181             : 
+     182             :         // linear distance to a given vector
+     183         110 :         T getDistanceTo(const Vector3<T> &point) const {
+     184             :                 Vector3<T> d = *this - point;
+     185         110 :                 return d.getR();
+     186             :         }
+     187             : 
+     188             :         // return the component parallel to a second vector
+     189             :         // 0 if the second vector has 0 magnitude
+     190           2 :         Vector3<T> getParallelTo(const Vector3<T> &v) const {
+     191             :                 T vmag = v.getR();
+     192           2 :                 if (vmag == std::numeric_limits < T > ::min())
+     193             :                         return Vector3<T>(0.);
+     194             :                 return v * dot(v) / vmag;
+     195             :         }
+     196             : 
+     197             :         // return the component perpendicular to a second vector
+     198             :         // 0 if the second vector has 0 magnitude
+     199           1 :         Vector3<T> getPerpendicularTo(const Vector3<T> &v) const {
+     200           1 :                 if (v.getR() == std::numeric_limits < T > ::min())
+     201             :                         return Vector3<T>(0.);
+     202           1 :                 return (*this) - getParallelTo(v);
+     203             :         }
+     204             : 
+     205             :         // rotate the vector around a given axis by a given angle
+     206      481006 :         Vector3<T> getRotated(const Vector3<T> &axis, T angle) const {
+     207             :                 Vector3<T> u = axis;
+     208      481006 :                 if (u.getR() != 0.)
+     209             :                         u = u / u.getR();
+     210      481006 :                 T c = cos(angle);
+     211      481006 :                 T s = sin(angle);
+     212      481006 :                 Vector3<T> Rx(c + u.x * u.x * (1 - c), u.x * u.y * (1 - c) - u.z * s,
+     213      481006 :                                 u.x * u.z * (1 - c) + u.y * s);
+     214      481006 :                 Vector3<T> Ry(u.y * u.x * (1 - c) + u.z * s, c + u.y * u.y * (1 - c),
+     215      481006 :                                 u.y * u.z * (1 - c) - u.x * s);
+     216      481006 :                 Vector3<T> Rz(u.z * u.x * (1 - c) - u.y * s,
+     217      481006 :                                 u.z * u.y * (1 - c) + u.x * s, c + u.z * u.z * (1 - c));
+     218      481006 :                 return Vector3<T>(dot(Rx), dot(Ry), dot(Rz));
+     219             :         }
+     220             : 
+     221             :         // return vector with values limited to the range [lower, upper]
+     222           0 :         Vector3<T> clip(T lower, T upper) const {
+     223             :                 Vector3<T> out;
+     224           0 :                 out.x = std::max(lower, std::min(x, upper));
+     225           0 :                 out.y = std::max(lower, std::min(y, upper));
+     226           0 :                 out.z = std::max(lower, std::min(z, upper));
+     227           0 :                 return out;
+     228             :         }
+     229             : 
+     230             :         // return vector with absolute values
+     231             :         Vector3<T> abs() const {
+     232           0 :                 return Vector3<T>(std::abs(x), std::abs(y), std::abs(z));
+     233             :         }
+     234             : 
+     235             :         // return vector with floored values
+     236           6 :         Vector3<T> floor() const {
+     237           6 :                 return Vector3<T>(std::floor(x), std::floor(y), std::floor(z));
+     238             :         }
+     239             : 
+     240             :         // return vector with ceiled values
+     241           0 :         Vector3<T> ceil() const {
+     242           0 :                 return Vector3<T>(std::ceil(x), std::ceil(y), std::ceil(z));
+     243             :         }
+     244             : 
+     245             :         // minimum element
+     246             :         T min() const {
+     247           4 :                 return std::min(x, std::min(y, z));
+     248             :         }
+     249             : 
+     250             :         // maximum element
+     251             :         T max() const {
+     252           4 :                 return std::max(x, std::max(y, z));
+     253             :         }
+     254             : 
+     255             :         // dot product
+     256             :         T dot(const Vector3<T> &v) const {
+     257      692583 :                 return x * v.x + y * v.y + z * v.z;
+     258             :         }
+     259             : 
+     260             :         // cross product
+     261             :         Vector3<T> cross(const Vector3<T> &v) const {
+     262     2132230 :                 return Vector3<T>(y * v.z - v.y * z, z * v.x - v.z * x,
+     263     1652230 :                                 x * v.y - v.x * y);
+     264             :         }
+     265             : 
+     266             :         // returns true if all elements of the two vectors are equal
+     267             :         bool operator ==(const Vector3<T> &v) const {
+     268          33 :                 if (x != v.x)
+     269             :                         return false;
+     270          33 :                 if (y != v.y)
+     271             :                         return false;
+     272          33 :                 if (z != v.z)
+     273           0 :                         return false;
+     274             :                 return true;
+     275             :         }
+     276             : 
+     277             :         Vector3<T> operator +(const Vector3<T> &v) const {
+     278     4339186 :                 return Vector3(x + v.x, y + v.y, z + v.z);
+     279             :         }
+     280             : 
+     281             :         Vector3<T> operator +(const T &f) const {
+     282           0 :                 return Vector3(x + f, y + f, z + f);
+     283             :         }
+     284             : 
+     285             :         Vector3<T> operator -(const Vector3<T> &v) const {
+     286     7533903 :                 return Vector3(x - v.x, y - v.y, z - v.z);
+     287             :         }
+     288             : 
+     289             :         Vector3<T> operator -(const T &f) const {
+     290           0 :                 return Vector3(x - f, y - f, z - f);
+     291             :         }
+     292             : 
+     293             :         // element-wise multiplication
+     294             :         Vector3<T> operator *(const Vector3<T> &v) const {
+     295          20 :                 return Vector3(x * v.x, y * v.y, z * v.z);
+     296             :         }
+     297             : 
+     298             :         Vector3<T> operator *(T v) const {
+     299     1191262 :                 return Vector3(data[0] * v, data[1] * v, data[2] * v);
+     300             :         }
+     301             : 
+     302             :         // element-wise division
+     303             :         Vector3<T> operator /(const Vector3<T> &v) const {
+     304      100097 :                 return Vector3(x / v.x, y / v.y, z / v.z);
+     305             :         }
+     306             : 
+     307             :         Vector3<T> operator /(const T &f) const {
+     308     6242639 :                 return Vector3(x / f, y / f, z / f);
+     309             :         }
+     310             : 
+     311             :         // element-wise modulo operation
+     312           0 :         Vector3<T> operator %(const Vector3<T> &v) const {
+     313           0 :                 return Vector3(fmod(x, v.x), fmod(y, v.y), fmod(z, v.z));
+     314             :         }
+     315             : 
+     316           0 :         Vector3<T> operator %(const T &f) const {
+     317           0 :                 return Vector3(fmod(x, f), fmod(y, f), fmod(z, f));
+     318             :         }
+     319             : 
+     320             :         Vector3<T> &operator -=(const Vector3<T> &v) {
+     321           0 :                 data[0] -= v.x;
+     322           0 :                 data[1] -= v.y;
+     323           0 :                 data[2] -= v.z;
+     324             :                 return *this;
+     325             :         }
+     326             : 
+     327             :         Vector3<T> &operator -=(const T &f) {
+     328           0 :                 data[0] -= f;
+     329           0 :                 data[1] -= f;
+     330           0 :                 data[2] -= f;
+     331             :                 return *this;
+     332             :         }
+     333             : 
+     334             :         Vector3<T> &operator +=(const Vector3<T> &v) {
+     335    20664839 :                 data[0] += v.x;
+     336    20664839 :                 data[1] += v.y;
+     337    20544720 :                 data[2] += v.z;
+     338             :                 return *this;
+     339             :         }
+     340             : 
+     341             :         Vector3<T> &operator +=(const T &f) {
+     342           0 :                 data[0] += f;
+     343           0 :                 data[1] += f;
+     344           0 :                 data[2] += f;
+     345             :                 return *this;
+     346             :         }
+     347             : 
+     348             :         // element-wise multiplication
+     349             :         Vector3<T> &operator *=(const Vector3<T> &v) {
+     350           0 :                 data[0] *= v.x;
+     351           0 :                 data[1] *= v.y;
+     352           0 :                 data[2] *= v.z;
+     353             :                 return *this;
+     354             :         }
+     355             : 
+     356             :         Vector3<T> &operator *=(const T &f) {
+     357     3312538 :                 data[0] *= f;
+     358     3312538 :                 data[1] *= f;
+     359     3312538 :                 data[2] *= f;
+     360             :                 return *this;
+     361             :         }
+     362             : 
+     363             :         // element-wise division
+     364             :         Vector3<T> &operator /=(const Vector3<T> &v) {
+     365           0 :                 data[0] /= v.x;
+     366           0 :                 data[1] /= v.y;
+     367           0 :                 data[2] /= v.z;
+     368             :                 return *this;
+     369             :         }
+     370             : 
+     371             :         Vector3<T> &operator /=(const T &f) {
+     372      691019 :                 data[0] /= f;
+     373      691019 :                 data[1] /= f;
+     374      691019 :                 data[2] /= f;
+     375             :                 return *this;
+     376             :         }
+     377             : 
+     378             :         // element-wise modulo operation
+     379           0 :         Vector3<T> &operator %=(const Vector3<T> &v) {
+     380           0 :                 data[0] = fmod(x, v.x);
+     381           0 :                 data[1] = fmod(y, v.y);
+     382           0 :                 data[2] = fmod(z, v.z);
+     383           0 :                 return *this;
+     384             :         }
+     385             : 
+     386           1 :         Vector3<T> &operator %=(const T &f) {
+     387           1 :                 data[0] = fmod(x, f);
+     388           1 :                 data[1] = fmod(y, f);
+     389           1 :                 data[2] = fmod(z, f);
+     390           1 :                 return *this;
+     391             :         }
+     392             : 
+     393             :         Vector3<T> &operator =(const Vector3<T> &v) {
+     394    64125712 :                 data[0] = v.x;
+     395    64125726 :                 data[1] = v.y;
+     396    63640105 :                 data[2] = v.z;
+     397           0 :                 return *this;
+     398             :         }
+     399             : 
+     400             :         //Vector3<T> &operator =(Vector3<T> &&v) noexcept {
+     401             :         //      data[0] = v.data[0];
+     402             :         //      data[1] = v.data[1];
+     403             :         //      data[2] = v.data[2];
+     404             :         //      return *this;
+     405             :         //}
+     406             : 
+     407             :         Vector3<T> &operator =(const T &f) {
+     408             :                 data[0] = f;
+     409             :                 data[1] = f;
+     410             :                 data[2] = f;
+     411             :                 return *this;
+     412             :         }
+     413             : };
+     414             : 
+     415             : #ifndef SWIG
+     416             : template<typename T>
+     417          38 : inline std::ostream &operator <<(std::ostream &out, const Vector3<T> &v) {
+     418         114 :         out << v.x << " " << v.y << " " << v.z;
+     419          38 :         return out;
+     420             : }
+     421             : 
+     422             : template<typename T>
+     423             : inline std::istream &operator >>(std::istream &in, Vector3<T> &v) {
+     424             :         in >> v.x >> v.y >> v.z;
+     425             :         return in;
+     426             : }
+     427             : #endif
+     428             : 
+     429             : template<typename T>
+     430             : inline Vector3<T> operator *(T f, const Vector3<T> &v) {
+     431     3628978 :         return Vector3<T>(v.x * f, v.y * f, v.z * f);
+     432             : }
+     433             : 
+     434             : typedef Vector3<double> Vector3d;
+     435             : typedef Vector3<float> Vector3f;
+     436             : 
+     437             : /** @}*/
+     438             : }  // namespace crpropa
+     439             : 
+     440             : #endif  // CRPROPA_VECTOR3_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html new file mode 100644 index 000000000..429d191a5 --- /dev/null +++ b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/advectionField/AdvectionField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/advectionField - AdvectionField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html new file mode 100644 index 000000000..74fd9621e --- /dev/null +++ b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/advectionField/AdvectionField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/advectionField - AdvectionField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html new file mode 100644 index 000000000..4be5bf68f --- /dev/null +++ b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html @@ -0,0 +1,367 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/advectionField/AdvectionField.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/advectionField - AdvectionField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_ADVECTIONFIELD_H
+       2             : #define CRPROPA_ADVECTIONFIELD_H
+       3             : 
+       4             : 
+       5             : #include <string>
+       6             : #include <iostream>
+       7             : #include <cmath>
+       8             : #include <cstdlib>
+       9             : #include <sstream>
+      10             : 
+      11             : #include "crpropa/Vector3.h"
+      12             : #include "crpropa/Referenced.h"
+      13             : #include "crpropa/Units.h"
+      14             : 
+      15             : namespace crpropa {
+      16             : 
+      17             : /**
+      18             :  @class AdvectionField
+      19             :  @brief Abstract base class for advection fields. These are used to model 
+      20             :         the deterministic part of the Fokker-Planck equation. The getDivergence()
+      21             :         method is used to model the adibatic cooling/heating.
+      22             :  */
+      23             : class AdvectionField: public Referenced {
+      24             : public:
+      25             :         virtual ~AdvectionField() {
+      26             :         }
+      27             :         virtual Vector3d getField(const Vector3d &position) const = 0;
+      28             :         virtual double getDivergence(const Vector3d &position) const = 0;
+      29             : };
+      30             : 
+      31             : 
+      32             : /**
+      33             :  @class AdvectionFieldList
+      34             :  @brief Advection field decorator implementing a superposition of fields.
+      35             :  */
+      36           2 : class AdvectionFieldList: public AdvectionField {
+      37             :         std::vector<ref_ptr<AdvectionField> > fields;
+      38             : public:
+      39             :         void addField(ref_ptr<AdvectionField> field);
+      40             :         Vector3d getField(const Vector3d &position) const;
+      41             :         double getDivergence(const Vector3d &position) const;
+      42             : };
+      43             : 
+      44             : 
+      45             : /**
+      46             :  @class UniformAdvectionField
+      47             :  @brief Advection field with one velocity/advection-field vector.
+      48             :  */
+      49           1 : class UniformAdvectionField: public AdvectionField {
+      50             :         Vector3d value;
+      51             : public:
+      52             :         UniformAdvectionField(const Vector3d &value);
+      53             :         Vector3d getField(const Vector3d &position) const;
+      54             :         double getDivergence(const Vector3d &position) const;
+      55             : 
+      56             :         std::string getDescription() const;
+      57             : };
+      58             : 
+      59             : 
+      60             : /**
+      61             : @class ConstantSphericalAdvectionField
+      62             : @brief Spherical advection field with a constant wind speed
+      63             : */
+      64             : 
+      65           1 : class ConstantSphericalAdvectionField: public AdvectionField {
+      66             :         Vector3d origin; //origin of the advection sphere
+      67             :         double vWind; // wind velocity
+      68             : public:
+      69             :         /** Constructor
+      70             :          @param origin  Origin of the advection field
+      71             :          @param vWind   Constant wind velocity
+      72             : 
+      73             : */
+      74             : 
+      75             :         ConstantSphericalAdvectionField(const Vector3d origin, double vWind);
+      76             :         Vector3d getField(const Vector3d &position) const;
+      77             :         double getDivergence(const Vector3d &position) const;
+      78             : 
+      79             :         void setOrigin(const Vector3d origin);
+      80             :         void setVWind(double vMax);
+      81             : 
+      82             :         Vector3d getOrigin() const;
+      83             :         double getVWind() const;
+      84             : 
+      85             :         std::string getDescription() const;
+      86             : 
+      87             :         
+      88             : };
+      89             :         
+      90             : /**
+      91             :  @class SphericalAdvectionField
+      92             :  @brief Spherical advection with a exponentially increasing and
+      93             :         exponentially constant velocity.
+      94             : */
+      95             : 
+      96           1 : class SphericalAdvectionField: public AdvectionField {
+      97             :         Vector3d origin; //origin of the advection sphere
+      98             :         double radius; //radius of the advection sphere
+      99             :         double vMax; // maximum wind velocity
+     100             :         double tau; // transition distance
+     101             :         double alpha; //tuning parameter
+     102             : public:
+     103             :         /** Constructor
+     104             :         @param origin   Origin of the advection sphere
+     105             :         @param radius   Radius of the advection sphere
+     106             :         @param vMax     Maximum wind velocity
+     107             :         @param tau      Transition distance
+     108             :         @param alpha    Tuning parameter
+     109             : */
+     110             :         SphericalAdvectionField(const Vector3d origin, double radius, double vMax, double tau, double alpha);
+     111             :         Vector3d getField(const Vector3d &position) const;
+     112             :         double getDivergence(const Vector3d &position) const;
+     113             : 
+     114             :         double getV(const double &r) const;
+     115             : 
+     116             :         void setOrigin(const Vector3d origin);
+     117             :         void setRadius(double radius);
+     118             :         void setVMax(double vMax);
+     119             :         void setTau(double tau);
+     120             :         void setAlpha(double alpha);
+     121             : 
+     122             :         Vector3d getOrigin() const;
+     123             :         double getRadius() const;
+     124             :         double getVMax() const;
+     125             :         double getTau() const;
+     126             :         double getAlpha() const;
+     127             :         
+     128             :         std::string getDescription() const;
+     129             : };
+     130             : 
+     131             : /**
+     132             :  @class OneDimensionalCartesianShock
+     133             :  @brief Advection field in x-direction with shock at x = 0 and width lShock approximated by tanh() 
+     134             :                 with variable compression ratio vUp/vDown
+     135             :  */
+     136             : class OneDimensionalCartesianShock: public AdvectionField {
+     137             :         double compressionRatio; //compression ratio of shock
+     138             :         double vUp; //upstream velocity 
+     139             :         double lShock; //shock width
+     140             : public:
+     141             : /** Constructor
+     142             :         @param compressionRatio //compression ratio of shock
+     143             :         @param vUp //upstream velocity 
+     144             :         @param lShock //shock width
+     145             : */
+     146             :         OneDimensionalCartesianShock(double compressionRatio, double vUp, double lShock);
+     147             :         Vector3d getField(const Vector3d &position) const;
+     148             :         double getDivergence(const Vector3d &position) const;
+     149             : 
+     150             :         void setComp(double compressionRatio);
+     151             :         void setVup(double vUp);
+     152             :         void setShockwidth(double lShock);
+     153             : 
+     154             :         double getComp() const;
+     155             :         double getVup() const; 
+     156             :         double getShockwidth() const;
+     157             : 
+     158             :         std::string getDescription() const;
+     159             : };
+     160             : 
+     161             : /**
+     162             :  @class OneDimensionalSphericalShock
+     163             :  @brief Advection field in x-direction with shock at rShock and width lShock approximated by tanh() 
+     164             :                 with variable compression ratio ratio vUp/vDown
+     165             :  */
+     166             : class OneDimensionalSphericalShock: public AdvectionField {
+     167             :         double compressionRatio;        //compression ratio of shock
+     168             :         double vUp;     //upstream velocity 
+     169             :         double lShock;  //shock width
+     170             :         double rShock;  //shock radius
+     171             :         bool coolUpstream;      //flag for upstream cooling
+     172             : public:
+     173             : /** Constructor
+     174             :         @param compressionRatio //compression ratio of shock
+     175             :         @param vUp      //upstream velocity 
+     176             :         @param lShock   //shock width
+     177             :         @param rShock   //shock radius
+     178             :         @param coolUpstream //flag for upstream cooling
+     179             : */
+     180             :         OneDimensionalSphericalShock(double rShock, double vUp, double compressionRatio, double lShock, bool coolUpstream);
+     181             :         Vector3d getField(const Vector3d &position) const;
+     182             :         double getDivergence(const Vector3d &position) const;
+     183             : 
+     184             :         void setComp(double compressionRatio);
+     185             :         void setVup(double vUp);
+     186             :         void setShockwidth(double lShock);
+     187             :         void setShockRadius(double rShock);
+     188             :         void setCooling(bool coolUpstream);
+     189             : 
+     190             :         double getComp() const; 
+     191             :         double getVup() const;
+     192             :         double getShockwidth() const;
+     193             :         double getShockRadius() const;
+     194             :         bool getCooling() const;
+     195             : 
+     196             :         std::string getDescription() const;
+     197             : };
+     198             : 
+     199             : /**
+     200             :  @class ObliqueAdvectionShock
+     201             :  @brief Advection field in x-y-direction with shock at x = 0 and width x_sh approximated by tanh() 
+     202             :                 with variable compression ratio r_comp = vx_up/vx_down. The y component vy is not shocked 
+     203             :                 and remains constant. 
+     204             :  */
+     205             : class ObliqueAdvectionShock: public AdvectionField {
+     206             :         double compressionRatio; //compression ratio of shock
+     207             :         double vXUp; //upstream velocity x-component
+     208             :         double vY; //constant velocity y-component
+     209             :         double lShock; //shock width
+     210             :         
+     211             : public:
+     212             : /** Constructor
+     213             :         @param compressionRatio //compression ratio of shock
+     214             :         @param vXUp //upstream velocity x-component
+     215             :         @param vY //constant velocity y-component
+     216             :         @param lShock //shock width
+     217             :         
+     218             : */
+     219             :         ObliqueAdvectionShock(double compressionRatio, double vXUp, double vY, double lShock);
+     220             :         Vector3d getField(const Vector3d &position) const;
+     221             :         double getDivergence(const Vector3d &position) const;
+     222             : 
+     223             :         void setComp(double compressionRatio);
+     224             :         void setVup(double vXUp);
+     225             :         void setVy(double vY);
+     226             :         void setShockwidth(double lShock);
+     227             : 
+     228             :         double getComp() const; 
+     229             :         double getVup() const;
+     230             :         double getVy() const;
+     231             :         double getShockwidth() const;
+     232             :         
+     233             :         std::string getDescription() const;
+     234             : };
+     235             : 
+     236             : /**
+     237             :  @class SphericalAdvectionShock
+     238             :  @brief Spherical advection with a constant velocity for r<r_0
+     239             :         at the the shock the velocity drops to v_0/4. followed by
+     240             :         a decrease proportional to 1/r^2.
+     241             : */
+     242             : 
+     243           1 : class SphericalAdvectionShock: public AdvectionField {
+     244             :         Vector3d origin; // origin of the advection sphere
+     245             :         double r_0; // position of the shock
+     246             :         double v_0; // constant velocity
+     247             :         double lambda; //transition width
+     248             :         double r_rot; // normalization radius for rotation speed
+     249             :         double v_phi; // rotation speed at r_rot
+     250             : 
+     251             : public:
+     252             :         /** Constructor
+     253             :         @param origin   Origin of the advection sphere
+     254             :         @param r_0      Position of the shock
+     255             :         @param v_0      Constant velocity (r<<r_o)
+     256             :         @param lambda   Transition width / width of the shock
+     257             : */
+     258             :         SphericalAdvectionShock(const Vector3d origin, double r_0, double v_0, double lambda);
+     259             : 
+     260             :         Vector3d getField(const Vector3d &position) const;
+     261             :         double getDivergence(const Vector3d &position) const;
+     262             : 
+     263             :         double g(double R) const;
+     264             :         double g_prime(double R) const;
+     265             : 
+     266             :         void setOrigin(const Vector3d Origin);
+     267             :         void setR0(double r);
+     268             :         void setV0(double v);
+     269             :         void setLambda(double l);
+     270             :         void setRRot(double r);
+     271             :         void setAzimuthalSpeed(double vPhi);
+     272             : 
+     273             :         Vector3d getOrigin() const;
+     274             :         double getR0() const;
+     275             :         double getV0() const;
+     276             :         double getLambda() const;
+     277             :         /**
+     278             :          * @param r Normalization radius for rotation speed
+     279             :         */      
+     280             :         double getRRot() const;
+     281             :         /**
+     282             :          * @param vPhi  Rotation speed at r_rot
+     283             :         */      
+     284             :         double getAzimuthalSpeed() const;
+     285             : 
+     286             :         std::string getDescription() const;
+     287             : };
+     288             : 
+     289             : } // namespace crpropa
+     290             : 
+     291             : #endif // CRPROPA_ADVECTIONFIELD_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/advectionField/index-sort-f.html b/doc/coverageReport/include/crpropa/advectionField/index-sort-f.html new file mode 100644 index 000000000..4f7addbb4 --- /dev/null +++ b/doc/coverageReport/include/crpropa/advectionField/index-sort-f.html @@ -0,0 +1,93 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/advectionField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.h +
100.0%
+
100.0 %5 / 5-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/advectionField/index-sort-l.html b/doc/coverageReport/include/crpropa/advectionField/index-sort-l.html new file mode 100644 index 000000000..dd1aafc93 --- /dev/null +++ b/doc/coverageReport/include/crpropa/advectionField/index-sort-l.html @@ -0,0 +1,93 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/advectionField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.h +
100.0%
+
100.0 %5 / 5-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/advectionField/index.html b/doc/coverageReport/include/crpropa/advectionField/index.html new file mode 100644 index 000000000..b7333515c --- /dev/null +++ b/doc/coverageReport/include/crpropa/advectionField/index.html @@ -0,0 +1,93 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/advectionField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.h +
100.0%
+
100.0 %5 / 5-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/index-sort-f.html b/doc/coverageReport/include/crpropa/index-sort-f.html new file mode 100644 index 000000000..3e4666a0f --- /dev/null +++ b/doc/coverageReport/include/crpropa/index-sort-f.html @@ -0,0 +1,233 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropaHitTotalCoverage
Test:coverage.info.cleanedLines:40855473.6 %
Date:2024-04-08 14:58:22Functions:7716646.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Source.h +
77.8%77.8%
+
77.8 %14 / 180.0 %0 / 1
Geometry.h +
75.0%75.0%
+
75.0 %3 / 40.0 %0 / 1
Logging.h +
0.0%
+
0.0 %0 / 180.0 %0 / 6
Variant.h +
37.1%37.1%
+
37.1 %13 / 3525.0 %4 / 16
Vector3.h +
65.6%65.6%
+
65.6 %99 / 15139.0 %16 / 41
Grid.h +
88.7%88.7%
+
88.7 %173 / 19541.1 %23 / 56
Referenced.h +
73.2%73.2%
+
73.2 %41 / 5652.6 %10 / 19
PhotonBackground.h +
81.5%81.5%
+
81.5 %22 / 2789.5 %17 / 19
ParticleState.h +
100.0%
+
100.0 %1 / 1-0 / 0
Module.h +
25.0%25.0%
+
25.0 %2 / 8-0 / 0
Candidate.h +
100.0%
+
100.0 %1 / 1-0 / 0
EmissionMap.h +
100.0%
+
100.0 %1 / 1-0 / 0
Random.h +
87.5%87.5%
+
87.5 %7 / 8-0 / 0
Common.h +
100.0%
+
100.0 %10 / 10100.0 %2 / 2
AssocVector.h +
100.0%
+
100.0 %21 / 21100.0 %5 / 5
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/index-sort-l.html b/doc/coverageReport/include/crpropa/index-sort-l.html new file mode 100644 index 000000000..f2d075e22 --- /dev/null +++ b/doc/coverageReport/include/crpropa/index-sort-l.html @@ -0,0 +1,233 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropaHitTotalCoverage
Test:coverage.info.cleanedLines:40855473.6 %
Date:2024-04-08 14:58:22Functions:7716646.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Logging.h +
0.0%
+
0.0 %0 / 180.0 %0 / 6
Module.h +
25.0%25.0%
+
25.0 %2 / 8-0 / 0
Variant.h +
37.1%37.1%
+
37.1 %13 / 3525.0 %4 / 16
Vector3.h +
65.6%65.6%
+
65.6 %99 / 15139.0 %16 / 41
Referenced.h +
73.2%73.2%
+
73.2 %41 / 5652.6 %10 / 19
Geometry.h +
75.0%75.0%
+
75.0 %3 / 40.0 %0 / 1
Source.h +
77.8%77.8%
+
77.8 %14 / 180.0 %0 / 1
PhotonBackground.h +
81.5%81.5%
+
81.5 %22 / 2789.5 %17 / 19
Random.h +
87.5%87.5%
+
87.5 %7 / 8-0 / 0
Grid.h +
88.7%88.7%
+
88.7 %173 / 19541.1 %23 / 56
ParticleState.h +
100.0%
+
100.0 %1 / 1-0 / 0
Candidate.h +
100.0%
+
100.0 %1 / 1-0 / 0
EmissionMap.h +
100.0%
+
100.0 %1 / 1-0 / 0
Common.h +
100.0%
+
100.0 %10 / 10100.0 %2 / 2
AssocVector.h +
100.0%
+
100.0 %21 / 21100.0 %5 / 5
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/index.html b/doc/coverageReport/include/crpropa/index.html new file mode 100644 index 000000000..e5683710b --- /dev/null +++ b/doc/coverageReport/include/crpropa/index.html @@ -0,0 +1,233 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropaHitTotalCoverage
Test:coverage.info.cleanedLines:40855473.6 %
Date:2024-04-08 14:58:22Functions:7716646.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AssocVector.h +
100.0%
+
100.0 %21 / 21100.0 %5 / 5
Candidate.h +
100.0%
+
100.0 %1 / 1-0 / 0
Common.h +
100.0%
+
100.0 %10 / 10100.0 %2 / 2
EmissionMap.h +
100.0%
+
100.0 %1 / 1-0 / 0
Geometry.h +
75.0%75.0%
+
75.0 %3 / 40.0 %0 / 1
Grid.h +
88.7%88.7%
+
88.7 %173 / 19541.1 %23 / 56
Logging.h +
0.0%
+
0.0 %0 / 180.0 %0 / 6
Module.h +
25.0%25.0%
+
25.0 %2 / 8-0 / 0
ParticleState.h +
100.0%
+
100.0 %1 / 1-0 / 0
PhotonBackground.h +
81.5%81.5%
+
81.5 %22 / 2789.5 %17 / 19
Random.h +
87.5%87.5%
+
87.5 %7 / 8-0 / 0
Referenced.h +
73.2%73.2%
+
73.2 %41 / 5652.6 %10 / 19
Source.h +
77.8%77.8%
+
77.8 %14 / 180.0 %0 / 1
Variant.h +
37.1%37.1%
+
37.1 %13 / 3525.0 %4 / 16
Vector3.h +
65.6%65.6%
+
65.6 %99 / 15139.0 %16 / 41
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html new file mode 100644 index 000000000..afe0c0f07 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/GalacticMagneticField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - GalacticMagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3838100.0 %
Date:2024-04-08 14:58:22Functions:44100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22LogarithmicSpiralField11updatePhaseEv1
_ZN7crpropa22LogarithmicSpiralField16updatePitchAngleEv1
_ZNK7crpropa22LogarithmicSpiralField8getFieldENS_7Vector3IdEE1
_ZN7crpropa17ToroidalHaloField8getFieldENS_7Vector3IdEE2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html new file mode 100644 index 000000000..d44a00d58 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/GalacticMagneticField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - GalacticMagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3838100.0 %
Date:2024-04-08 14:58:22Functions:44100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ToroidalHaloField8getFieldENS_7Vector3IdEE2
_ZN7crpropa22LogarithmicSpiralField11updatePhaseEv1
_ZN7crpropa22LogarithmicSpiralField16updatePitchAngleEv1
_ZNK7crpropa22LogarithmicSpiralField8getFieldENS_7Vector3IdEE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html new file mode 100644 index 000000000..6ae2c08a8 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html @@ -0,0 +1,210 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/GalacticMagneticField.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - GalacticMagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3838100.0 %
Date:2024-04-08 14:58:22Functions:44100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_GALACTICMAGNETICFIELD_H
+       2             : #define CRPROPA_GALACTICMAGNETICFIELD_H
+       3             : 
+       4             : #include "crpropa/magneticField/MagneticField.h"
+       5             : #include <cmath>
+       6             : 
+       7             : namespace crpropa {
+       8             : /**
+       9             :  * \addtogroup MagneticFields
+      10             :  * @{
+      11             :  */
+      12             : 
+      13             : /**
+      14             :  @class ToroidalHaloField
+      15             :  @brief Galactic halo field model from Prouza & Smida 2003 and Sun et al. 2008
+      16             :  */
+      17             : class ToroidalHaloField: public MagneticField {
+      18             :         double b0; // halo field strength
+      19             :         double z0; // vertical position
+      20             :         double z1; // vertical scale
+      21             :         double r0; // radial scale
+      22             : 
+      23             : public:
+      24             :         /**
+      25             :          * Constructor
+      26             :          * @param b0 halo field strength
+      27             :          * @param z0 vertical position
+      28             :          * @param z1 vertical scale
+      29             :          * @param r0 radial scale
+      30             :         */
+      31           1 :         ToroidalHaloField(double b0 = 1., double z0 = 1., double z1 = 1., double r0 = 1.) {
+      32             :                 setParameters(b0, z0, z1, r0);
+      33             :         }
+      34             : 
+      35             :         void setParameters(double b0, double z0, double z1, double r0) {
+      36           1 :                 this->b0 = b0;
+      37           1 :                 this->z0 = z0;
+      38           1 :                 this->z1 = z1;
+      39           1 :                 this->r0 = r0;
+      40             :         }
+      41             : 
+      42           2 :         Vector3d getField(Vector3d pos) {
+      43           2 :                 double r = sqrt(pos.x * pos.x + pos.y * pos.y) / r0; // in-plane radius in units of the radial scale
+      44           2 :                 double b = b0 / (1 + pow((std::fabs(pos.z) - z0) / z1, 2)) * r * exp(1 - r);
+      45           2 :                 double phi = pos.getPhi(); // azimuth
+      46           2 :                 return Vector3d(cos(phi), sin(phi), 0) * b;
+      47             :         }
+      48             : };
+      49             : /** @} */
+      50             : 
+      51             : /**
+      52             :  * \addtogroup MagneticFields
+      53             :  * @{
+      54             :  */
+      55             : 
+      56             : /**
+      57             :  @class LogarithmicSpiralField
+      58             :  @brief Galactic disk field model of axisymmetric (ASS) or bisymmetric (BSS) logarithmic spiral shape
+      59             :  */
+      60             : class LogarithmicSpiralField: public MagneticField {
+      61             : private:
+      62             :         bool isBSS;   // true for BSS, false for ASS
+      63             :         double b0;    // field strength
+      64             :         double pitch; // pitch angle [rad]
+      65             :         double rsol;  // distance of sun to galactic center
+      66             :         double rc;    // radius of central region with constant field strength
+      67             :         double d;     // distance to the first field reversal
+      68             :         double z0;    // vertical attenuation length
+      69             : 
+      70             :         double phase; // phase of the spiral arms
+      71             :         double cosPhase;
+      72             :         double sinPitch;
+      73             :         double cosPitch;
+      74             :         double tanPitch;
+      75             : 
+      76           1 :         void updatePitchAngle() {
+      77           1 :                 sinPitch = sin(pitch);
+      78           1 :                 cosPitch = cos(pitch);
+      79           1 :                 tanPitch = tan(pitch);
+      80           1 :         }
+      81             : 
+      82           1 :         void updatePhase() {
+      83           1 :                 phase = log(1 + d / rsol) / tanPitch - M_PI / 2;
+      84           1 :                 cosPhase = cos(phase);
+      85           1 :         }
+      86             : 
+      87             : public:
+      88             :         /**
+      89             :          * Constructor
+      90             :          * @param isBSS switch for the magnetic field model
+      91             :          *                              true for BSS, false for ASS
+      92             :          * @param b0    magnetic field strength
+      93             :          * @param pitch pitch angle [rad]
+      94             :          * @param rsol  distance of sun from Galactic center
+      95             :          * @param rc    radius of central region with constant field
+      96             :          * @param d             distance to first field reversal
+      97             :          * @param z0    vertical attenuation length
+      98             :         */
+      99             :         LogarithmicSpiralField(bool isBSS = true, double b0 = 1., double pitch = M_1_PI/4.,
+     100           1 :                 double rsol = 8.5*kpc, double rc = 3*kpc, double d = 5*kpc, double z0 = 3*kpc) {
+     101             :                 setParameters(isBSS, b0, pitch, rsol, rc, d, z0);
+     102             :         }
+     103             : 
+     104             :         void setParameters(bool isBSS, double b0, double pitch, double rsol,
+     105             :                         double rc, double d, double z0) {
+     106           1 :                 this->isBSS = isBSS;
+     107           1 :                 this->b0 = b0;
+     108           1 :                 this->pitch = pitch;
+     109           1 :                 this->rsol = rsol;
+     110           1 :                 this->rc = rc;
+     111           1 :                 this->d = d;
+     112           1 :                 this->z0 = z0;
+     113           1 :                 updatePitchAngle();
+     114           1 :                 updatePhase();
+     115             :         }
+     116             : 
+     117           1 :         Vector3d getField(Vector3d pos) const {
+     118           1 :                 double r = sqrt(pos.x * pos.x + pos.y * pos.y); // in-plane radius
+     119           1 :                 double b = b0 / cosPhase * rsol / std::max(r, rc);
+     120             : 
+     121           1 :                 double phi = pos.getPhi();
+     122           1 :                 double c = cos(phi - log(r / rsol) / tanPitch + phase);
+     123           1 :                 if (isBSS)
+     124           1 :                         c = std::fabs(c);
+     125           1 :                 b *= c * exp(-std::fabs(pos.z) / z0);
+     126             : 
+     127           1 :                 return Vector3d(cosPitch * cos(phi), sinPitch * sin(phi), 0) * b;
+     128             :         }
+     129             : };
+     130             : /** @} */
+     131             : 
+     132             : }// namespace crpropa
+     133             : 
+     134             : #endif // CRPROPA_GALACTICMAGNETICFIELD_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html new file mode 100644 index 000000000..841410136 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - MagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:121770.6 %
Date:2024-04-08 14:58:22Functions:3742.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MagneticFieldD0Ev0
_ZN7crpropa13MagneticFieldD2Ev0
_ZN7crpropa24RenormalizeMagneticFieldD0Ev0
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEE0
_ZN7crpropa24RenormalizeMagneticFieldD2Ev1
_ZNK7crpropa20UniformMagneticField8getFieldERKNS_7Vector3IdEE5760340
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEEd5760379
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html new file mode 100644 index 000000000..8ed4d10b3 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - MagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:121770.6 %
Date:2024-04-08 14:58:22Functions:3742.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MagneticFieldD0Ev0
_ZN7crpropa13MagneticFieldD2Ev0
_ZN7crpropa24RenormalizeMagneticFieldD0Ev0
_ZN7crpropa24RenormalizeMagneticFieldD2Ev1
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEEd5760379
_ZNK7crpropa20UniformMagneticField8getFieldERKNS_7Vector3IdEE5760340
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html new file mode 100644 index 000000000..2866a8501 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html @@ -0,0 +1,248 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticField.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - MagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:121770.6 %
Date:2024-04-08 14:58:22Functions:3742.9 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_MAGNETICFIELD_H
+       2             : #define CRPROPA_MAGNETICFIELD_H
+       3             : 
+       4             : #include "crpropa/Units.h"
+       5             : #include "crpropa/Vector3.h"
+       6             : #include "crpropa/Referenced.h"
+       7             : 
+       8             : #ifdef CRPROPA_HAVE_MUPARSER
+       9             : #include "muParser.h"
+      10             : #endif
+      11             : 
+      12             : namespace crpropa {
+      13             : /**
+      14             :  * \addtogroup MagneticFields
+      15             :  * @{
+      16             :  */
+      17             : 
+      18             : /**
+      19             :  @class MagneticField
+      20             :  @brief Abstract base class for magnetic fields.
+      21             :  */
+      22           0 : class MagneticField: public Referenced {
+      23             : public:
+      24           0 :         virtual ~MagneticField() {
+      25           0 :         }
+      26           0 :         virtual Vector3d getField(const Vector3d &position) const {
+      27           0 :                 return Vector3d(0,0,0);
+      28             :         };
+      29     5760379 :         virtual Vector3d getField(const Vector3d &position, double z) const {
+      30     5760379 :                 return getField(position);
+      31             :         };
+      32             : };
+      33             : 
+      34             : /**
+      35             :  @class PeriodicMagneticField
+      36             :  @brief Magnetic field decorator implementing periodic fields.
+      37             : 
+      38             :  The periodic cube is defined by its origin (Vector3d) and an
+      39             :  extends parameter (Vector3d). All points x=(x_1, x_2, x_3) 
+      40             :  that are described by x_i = origin_i + epsilon * extend_i, 
+      41             :  with epsilon = 0...1 are within the base cube. Magnetic field
+      42             :  strengths for all positions outside of this cube are calculated 
+      43             :  based on the values in the base cube. 
+      44             :  This can be done periodically or reflectively.
+      45             : */
+      46             : 
+      47             : class PeriodicMagneticField: public MagneticField {
+      48             :         ref_ptr<MagneticField> field;
+      49             :         Vector3d origin, extends;
+      50             :         bool reflective;
+      51             : public:
+      52             :         /**
+      53             :          * Constructor
+      54             :          * @param field magnetic field reference pointer
+      55             :          * @param extends length, width, and height of the base cube 
+      56             :         */
+      57             :         PeriodicMagneticField(ref_ptr<MagneticField> field,
+      58             :                         const Vector3d &extends);
+      59             :         /**
+      60             :          * Constructor
+      61             :          * @param field magnetic field reference pointer
+      62             :          * @param extends length, width, and height of the base cube
+      63             :          * @param origin defines the reference position 
+      64             :          * @param reflective for periodic or reflective behavior  
+      65             :         */
+      66             :         PeriodicMagneticField(ref_ptr<MagneticField> field, const Vector3d &extends,
+      67             :                         const Vector3d &origin, bool reflective);
+      68             :         Vector3d &getOrigin();
+      69             :         void setOrigin(const Vector3d &origin);
+      70             :         Vector3d &getExtends();
+      71             :         void setExtends(const Vector3d &origin);
+      72             :         bool isReflective();
+      73             :         void setReflective(bool reflective);
+      74             :         Vector3d getField(const Vector3d &position) const;
+      75             : };
+      76             : 
+      77             : /**
+      78             :  @class MagneticFieldList
+      79             :  @brief Magnetic field decorator implementing a superposition of fields.
+      80             :  */
+      81           2 : class MagneticFieldList: public MagneticField {
+      82             :         std::vector<ref_ptr<MagneticField> > fields;
+      83             : public:
+      84             :         void addField(ref_ptr<MagneticField> field);
+      85             :         Vector3d getField(const Vector3d &position) const;
+      86             : };
+      87             : 
+      88             : /**
+      89             :  @class MagneticFieldEvolution
+      90             :  @brief Magnetic field decorator implementing an evolution of type (1+z)^m.
+      91             :  */
+      92           2 : class MagneticFieldEvolution: public MagneticField {
+      93             :         ref_ptr<MagneticField> field;
+      94             :         double m;
+      95             : public:
+      96             :         /**
+      97             :          * Constructor
+      98             :          * @param field magnetic field reference pointer
+      99             :          * @param m cosmic evolution parameter 
+     100             :         */
+     101             :         MagneticFieldEvolution(ref_ptr<MagneticField> field, double m);
+     102             :         Vector3d getField(const Vector3d &position, double z = 0) const;
+     103             : };
+     104             : 
+     105             : /**
+     106             :  @class UniformMagneticField
+     107             :  @brief Magnetic field with one B-field vector.
+     108             :  */
+     109             : class UniformMagneticField: public MagneticField {
+     110             :         Vector3d value;
+     111             : public:
+     112             :         /**
+     113             :          * Constructor
+     114             :          * @param value magnetic field strength
+     115             :         */
+     116          33 :         UniformMagneticField(const Vector3d &value) :
+     117          33 :                         value(value) {
+     118             :         }
+     119     5760340 :         Vector3d getField(const Vector3d &position) const {
+     120     5760340 :                 return value;
+     121             :         }
+     122             : };
+     123             : 
+     124             : /**
+     125             :  @class MagneticDipoleField
+     126             :  @brief Magnetic dipole field defined by the magnetic moment and the 'core' radius.
+     127             :  */
+     128           1 : class MagneticDipoleField: public MagneticField {
+     129             :         Vector3d origin;
+     130             :         Vector3d moment;
+     131             :         double radius;
+     132             : public:
+     133             :         /**
+     134             :          * Constructor
+     135             :          * @param origin        singularity of the dipole field
+     136             :          * @param moment        magnetic moment of the dipole field
+     137             :          * @param radius        inside a radius around the origin the 
+     138             :          *                                      magnetic field is constant: moment * 2 * mu0 / 3  
+     139             :         */
+     140           1 :         MagneticDipoleField(const Vector3d &origin, const Vector3d &moment, const double radius) :
+     141           1 :                         origin(origin), moment(moment), radius(radius) {
+     142             :         }
+     143             :         Vector3d getField(const Vector3d &position) const;
+     144             : };
+     145             : 
+     146             : #ifdef CRPROPA_HAVE_MUPARSER
+     147             : /**
+     148             :  @class RenormalizeMagneticField
+     149             :  @brief Renormalize strength of a given field by expression in which B is the strength variable.
+     150             :  */
+     151             : class RenormalizeMagneticField: public MagneticField {
+     152             :         ref_ptr<MagneticField> field;
+     153             :         std::string expression;
+     154             :         mu::Parser *p;
+     155             :         double Bmag;
+     156             : public:
+     157             :         /**
+     158             :          * Constructor
+     159             :          * @param field                 magnetic field reference pointer
+     160             :          * @param expression    muParser expression used to renormalize the field, 
+     161             :          *                                              e.g., "gauss". 
+     162             :         */
+     163             :         RenormalizeMagneticField(ref_ptr<MagneticField> field, std::string expression);
+     164           1 :         ~RenormalizeMagneticField() { delete p; }
+     165             :         Vector3d getField(const Vector3d &position);
+     166             : };
+     167             : #endif
+     168             : 
+     169             : /** @} */
+     170             : } // namespace crpropa
+     171             : 
+     172             : #endif // CRPROPA_MAGNETICFIELD_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html new file mode 100644 index 000000000..62ce25a19 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticFieldGrid.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - MagneticFieldGrid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html new file mode 100644 index 000000000..04a253ccc --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticFieldGrid.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - MagneticFieldGrid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html new file mode 100644 index 000000000..7d0df9558 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html @@ -0,0 +1,139 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticFieldGrid.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField - MagneticFieldGrid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_MAGNETICFIELDGRID_H
+       2             : #define CRPROPA_MAGNETICFIELDGRID_H
+       3             : 
+       4             : #include "crpropa/magneticField/MagneticField.h"
+       5             : #include "crpropa/Grid.h"
+       6             : 
+       7             : namespace crpropa {
+       8             : /**
+       9             :  * \addtogroup MagneticFields
+      10             :  * @{
+      11             :  */
+      12             : 
+      13             : /**
+      14             :  @class MagneticFieldGrid
+      15             :  @brief Magnetic field on a periodic (or reflective), cartesian grid with trilinear interpolation.
+      16             : 
+      17             :  This class wraps a Grid3f to serve as a MagneticField.
+      18             :  */
+      19             : class MagneticFieldGrid: public MagneticField {
+      20             :         ref_ptr<Grid3f> grid;
+      21             : public:
+      22             :         /**
+      23             :          *Constructor
+      24             :          @param grid Grid3f storing the magnetic field vectors
+      25             :         */
+      26             :         MagneticFieldGrid(ref_ptr<Grid3f> grid);
+      27             :         void setGrid(ref_ptr<Grid3f> grid);
+      28             :         ref_ptr<Grid3f> getGrid();
+      29             :         Vector3d getField(const Vector3d &position) const;
+      30             : };
+      31             : 
+      32             : /**
+      33             :  @class ModulatedMagneticFieldGrid
+      34             :  @brief Modulated magnetic field on a periodic grid.
+      35             : 
+      36             :  This class wraps a Grid3f to serve as a MagneticField.
+      37             :  The field is modulated on-the-fly with a Grid1f.
+      38             :  The Grid3f and Grid1f do not need to share the same origin, spacing or size.
+      39             :  */
+      40             : class ModulatedMagneticFieldGrid: public MagneticField {
+      41             :         ref_ptr<Grid3f> grid;
+      42             :         ref_ptr<Grid1f> modGrid;
+      43             : public:
+      44           0 :         ModulatedMagneticFieldGrid() {
+      45             :         }
+      46             :         /**
+      47             :          *Constructor
+      48             :          @param grid    Grid3f storing the magnetic field vectors
+      49             :          @param modGrid Grid1f used to scale the magnetic field strength
+      50             :                                         B^new_i = B^old_i * scale 
+      51             :         */
+      52             :         ModulatedMagneticFieldGrid(ref_ptr<Grid3f> grid, ref_ptr<Grid1f> modGrid);
+      53             :         void setGrid(ref_ptr<Grid3f> grid);
+      54             :         void setModulationGrid(ref_ptr<Grid1f> modGrid);
+      55             :         ref_ptr<Grid3f> getGrid();
+      56             :         ref_ptr<Grid1f> getModulationGrid();
+      57             :         void setReflective(bool gridReflective, bool modGridReflective);
+      58             :         Vector3d getField(const Vector3d &position) const;
+      59             : };
+      60             : /** @} */
+      61             : } // namespace crpropa
+      62             : 
+      63             : #endif // CRPROPA_MAGNETICFIELDGRID_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/index-sort-f.html b/doc/coverageReport/include/crpropa/magneticField/index-sort-f.html new file mode 100644 index 000000000..08da227af --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/index-sort-f.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:505689.3 %
Date:2024-04-08 14:58:22Functions:71163.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticField.h +
70.6%70.6%
+
70.6 %12 / 1742.9 %3 / 7
MagneticFieldGrid.h +
0.0%
+
0.0 %0 / 1-0 / 0
GalacticMagneticField.h +
100.0%
+
100.0 %38 / 38100.0 %4 / 4
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/index-sort-l.html b/doc/coverageReport/include/crpropa/magneticField/index-sort-l.html new file mode 100644 index 000000000..3a378c7d3 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/index-sort-l.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:505689.3 %
Date:2024-04-08 14:58:22Functions:71163.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticFieldGrid.h +
0.0%
+
0.0 %0 / 1-0 / 0
MagneticField.h +
70.6%70.6%
+
70.6 %12 / 1742.9 %3 / 7
GalacticMagneticField.h +
100.0%
+
100.0 %38 / 38100.0 %4 / 4
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/index.html b/doc/coverageReport/include/crpropa/magneticField/index.html new file mode 100644 index 000000000..9cd37eb4a --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/index.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:505689.3 %
Date:2024-04-08 14:58:22Functions:71163.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
GalacticMagneticField.h +
100.0%
+
100.0 %38 / 38100.0 %4 / 4
MagneticField.h +
70.6%70.6%
+
70.6 %12 / 1742.9 %3 / 7
MagneticFieldGrid.h +
0.0%
+
0.0 %0 / 1-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html new file mode 100644 index 000000000..3432fc3a9 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/GridTurbulence.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - GridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html new file mode 100644 index 000000000..fd3be85af --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/GridTurbulence.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - GridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html new file mode 100644 index 000000000..29f802928 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html @@ -0,0 +1,151 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/GridTurbulence.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - GridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_GRIDTURBULENCE_H
+       2             : #define CRPROPA_GRIDTURBULENCE_H
+       3             : 
+       4             : #ifdef CRPROPA_HAVE_FFTW3F
+       5             : 
+       6             : #include "crpropa/Grid.h"
+       7             : #include "crpropa/magneticField/turbulentField/TurbulentField.h"
+       8             : 
+       9             : #include "fftw3.h"
+      10             : 
+      11             : namespace crpropa {
+      12             : /**
+      13             :  * \addtogroup MagneticFields
+      14             :  * @{
+      15             :  */
+      16             : 
+      17             : /**
+      18             :  @class GridTurbulence
+      19             :  @brief Turbulent grid-based magnetic field with a general energy spectrum
+      20             :  */
+      21           6 : class GridTurbulence : public TurbulentField {
+      22             :   protected:
+      23             :         unsigned int seed;
+      24             :         ref_ptr<Grid3f> gridPtr;
+      25             : 
+      26             :         void initGrid(const GridProperties &grid);
+      27             :         void initTurbulence();
+      28             : 
+      29             :   public:
+      30             :         /**
+      31             :          Create a random initialization of a turbulent field.
+      32             :          @param spectrum    TurbulenceSpectrum instance to define the spectrum of
+      33             :          turbulence
+      34             :          @param gridProp        GridProperties instance to define the underlying grid
+      35             :          @param seed     Random seed
+      36             :          */
+      37             :         GridTurbulence(const TurbulenceSpectrum &spectrum,
+      38             :                        const GridProperties &gridProp, unsigned int seed = 0);
+      39             : 
+      40             :         Vector3d getField(const Vector3d &pos) const;
+      41             : 
+      42             :         /** Return a const reference to the grid */
+      43             :         const ref_ptr<Grid3f> &getGrid() const;
+      44             : 
+      45             :         /* Helper functions for synthetic turbulent field models */
+      46             :         // Check the grid properties before the FFT procedure
+      47             :         static void checkGridRequirements(ref_ptr<Grid3f> grid, double lMin,
+      48             :                                           double lMax);
+      49             :         // Execute inverse discrete FFT in-place for a 3D grid, from complex to real
+      50             :         // space
+      51             :         static void executeInverseFFTInplace(ref_ptr<Grid3f> grid,
+      52             :                                              fftwf_complex *Bkx, fftwf_complex *Bky,
+      53             :                                              fftwf_complex *Bkz);
+      54             : 
+      55             :         // Usefull checks for a grid field
+      56             :         /** Evaluate the mean vector of all grid points */
+      57             :         Vector3f getMeanFieldVector() const;
+      58             :         /** Evaluate the mean of all grid points */
+      59             :         double getMeanFieldStrength() const;
+      60             :         /** Evaluate the RMS of all grid points */
+      61             :         double getRmsFieldStrength() const;
+      62             :         /** Evaluate the RMS of all grid points per axis */
+      63             :         std::array<float, 3> getRmsFieldStrengthPerAxis() const;
+      64             :         /** Evaluate generated power-spectrum */
+      65             :         std::vector<std::pair<int, float>> getPowerSpectrum() const;
+      66             :         /** Dump a Grid3f to a binary file */
+      67             :         void dumpToFile(std::string filename) const;
+      68             : };
+      69             : 
+      70             : /** @}*/
+      71             : } // namespace crpropa
+      72             : 
+      73             : #endif // CRPROPA_HAVE_FFTW3F
+      74             : 
+      75             : #endif // CRPROPA_GRIDTURBULENCE_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html new file mode 100644 index 000000000..0c515e402 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - HelicalGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21initHelicalTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html new file mode 100644 index 000000000..b4ddcbe9c --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - HelicalGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21initHelicalTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html new file mode 100644 index 000000000..f2108a9f4 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html @@ -0,0 +1,147 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - HelicalGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_HELICALGRIDTURBULENCE_H
+       2             : #define CRPROPA_HELICALGRIDTURBULENCE_H
+       3             : 
+       4             : #ifdef CRPROPA_HAVE_FFTW3F
+       5             : 
+       6             : #include "crpropa/Grid.h"
+       7             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
+       8             : 
+       9             : #include "kiss/logger.h"
+      10             : #include "kiss/string.h"
+      11             : 
+      12             : namespace crpropa {
+      13             : /**
+      14             :  * \addtogroup MagneticFields
+      15             :  * @{
+      16             :  */
+      17             : 
+      18             : /**
+      19             :  @class HelicalGridTurbulence
+      20             :  @brief Turbulent grid-based magnetic field with a simple power-law spectrum
+      21             :  */
+      22             : class HelicalGridTurbulence : public SimpleGridTurbulence {
+      23             :   private:
+      24             :         double H;
+      25             : 
+      26             :   public:
+      27             :         /**
+      28             :          Create a random initialization of a turbulent field.
+      29             :          @param spectrum    TurbulenceSpectrum instance to define the spectrum of
+      30             :          turbulence
+      31             :          @param gridProp        GridProperties instance to define the underlying grid
+      32             :          @param H       Helicity
+      33             :          @param seed     Random seed
+      34             :          */
+      35             :         HelicalGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
+      36             :                               const GridProperties &gridProp, double H,
+      37             :                               unsigned int seed = 0);
+      38             : 
+      39             :         static void initTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
+      40             :                                    double lMax, double alpha, int seed, double H);
+      41             : };
+      42             : 
+      43             : // Compatibility with old functions from GridTurbulence:
+      44             : 
+      45             : /**
+      46             :  Create a random initialization of a turbulent field including helicity
+      47             :  @param grid    grid on which the turbulence is calculated
+      48             :  @param Brms    RMS field strength
+      49             :  @param lMin    Minimum wavelength of the turbulence
+      50             :  @param lMax    Maximum wavelength of the turbulence
+      51             :  @param alpha   Power law index of <B^2(k)> ~ k^alpha (alpha = -11/3 corresponds
+      52             :  to a Kolmogorov spectrum)
+      53             :  @param seed    Random seed
+      54             :  @param H               Helicity
+      55             : */
+      56           0 : void initHelicalTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
+      57             :                            double lMax, double alpha = -11 / 3., int seed = 0,
+      58             :                            double H = 0) {
+      59           0 :         KISS_LOG_WARNING
+      60             :             << "initTurbulence is deprecated and will be removed in the future. "
+      61           0 :                "Replace it with a more appropriate turbulent field model instance.";
+      62           0 :         HelicalGridTurbulence::initTurbulence(grid, Brms, lMin, lMax, alpha, seed,
+      63             :                                               H);
+      64           0 : }
+      65             : 
+      66             : /** @}*/
+      67             : } // namespace crpropa
+      68             : 
+      69             : #endif // CRPROPA_HAVE_FFTW3F
+      70             : 
+      71             : #endif // CRPROPA_HELICALGRIDTURBULENCE_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html new file mode 100644 index 000000000..e3787874e --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - SimpleGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:172181.0 %
Date:2024-04-08 14:58:22Functions:4757.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa24SimpleTurbulenceSpectrumD0Ev0
_ZN7crpropa24SimpleTurbulenceSpectrumD2Ev0
_ZNK7crpropa24SimpleTurbulenceSpectrum20getCorrelationLengthEv0
_ZN7crpropa24SimpleTurbulenceSpectrum26turbulentCorrelationLengthEddd1
_ZN7crpropa26turbulentCorrelationLengthEddd1
_ZN7crpropa14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi4
_ZNK7crpropa24SimpleTurbulenceSpectrum14energySpectrumEd206961
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html new file mode 100644 index 000000000..c913f5f27 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - SimpleGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:172181.0 %
Date:2024-04-08 14:58:22Functions:4757.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi4
_ZN7crpropa24SimpleTurbulenceSpectrum26turbulentCorrelationLengthEddd1
_ZN7crpropa24SimpleTurbulenceSpectrumD0Ev0
_ZN7crpropa24SimpleTurbulenceSpectrumD2Ev0
_ZN7crpropa26turbulentCorrelationLengthEddd1
_ZNK7crpropa24SimpleTurbulenceSpectrum14energySpectrumEd206961
_ZNK7crpropa24SimpleTurbulenceSpectrum20getCorrelationLengthEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html new file mode 100644 index 000000000..57422a4cb --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html @@ -0,0 +1,192 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - SimpleGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:172181.0 %
Date:2024-04-08 14:58:22Functions:4757.1 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_SIMPLEGRIDTURBULENCE_H
+       2             : #define CRPROPA_SIMPLEGRIDTURBULENCE_H
+       3             : 
+       4             : #ifdef CRPROPA_HAVE_FFTW3F
+       5             : 
+       6             : #include "crpropa/magneticField/turbulentField/GridTurbulence.h"
+       7             : 
+       8             : #include "kiss/logger.h"
+       9             : #include "kiss/string.h"
+      10             : 
+      11             : namespace crpropa {
+      12             : /**
+      13             :  * \addtogroup MagneticFields
+      14             :  * @{
+      15             :  */
+      16             : 
+      17             : /**
+      18             :  @class SimpleTurbulenceSpectrum
+      19             :  @brief Defines the energy spectrum of simple power-law turbulence
+      20             :  */
+      21             : class SimpleTurbulenceSpectrum : public TurbulenceSpectrum {
+      22             :         const int constScaleBendover = 1000;    // define the bandover scale as 1000 * lMax to ensure k * lBendover >> 1. The bendover scale is necessary for the implementation of PlaneWaveTurbulence. 
+      23             :   public:
+      24             :         /**
+      25             :          * The bend-over scale is set to 1000 times lMax to ensure to be in the inertial range. This should not be changed.
+      26             :          @param Brms            Root mean square field strength for generated field
+      27             :          @param lMin            Minimum physical scale of the turbulence
+      28             :          @param lMax            Maximum physical scale of the turbulence
+      29             :          @param sIndex          Spectral index of the energy spectrum in the inertial range
+      30             :         */
+      31             :         SimpleTurbulenceSpectrum(double Brms, double lMin, double lMax,
+      32             :                                  double sIndex = 5. / 3)
+      33           2 :             : TurbulenceSpectrum(Brms, lMin, lMax, constScaleBendover * lMax, sIndex, 0) {}
+      34           0 :         ~SimpleTurbulenceSpectrum() {}
+      35             : 
+      36             :         /**
+      37             :         General energy spectrum for synthetic turbulence models
+      38             :         */
+      39      206961 :         double energySpectrum(double k) const {
+      40      206961 :                 return std::pow(k, -getSindex() - 2);
+      41             :         }
+      42             : 
+      43             :         /**
+      44             :             @brief       compute the magnetic field coherence length according to
+      45             :            the formula in  Harari et al. JHEP03(2002)045
+      46             :             @return Lc   coherence length of the magnetic field
+      47             :         */
+      48           0 :         double getCorrelationLength() const {
+      49           0 :                 return turbulentCorrelationLength(getLmin(), getLmax(),
+      50           0 :                                                   getSindex());
+      51             :         }
+      52           1 :         static double turbulentCorrelationLength(double lMin, double lMax,
+      53             :                                                  double s) {
+      54           1 :                 double r = lMin / lMax;
+      55           1 :                 return lMax / 2 * (s - 1) / s * (1 - pow(r, s)) / (1 - pow(r, s - 1));
+      56             :         }
+      57             : };
+      58             : 
+      59             : /**
+      60             :  @class SimpleGridTurbulence
+      61             :  @brief Turbulent grid-based magnetic field with a simple power-law spectrum
+      62             :  */
+      63           3 : class SimpleGridTurbulence : public GridTurbulence {
+      64             :   public:
+      65             :         /**
+      66             :          Create a random initialization of a turbulent field.
+      67             :          @param spectrum    TurbulenceSpectrum instance to define the spectrum of
+      68             :          turbulence
+      69             :          @param gridProp        GridProperties instance to define the underlying grid
+      70             :          @param seed     Random seed
+      71             :          */
+      72             :         SimpleGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
+      73             :                              const GridProperties &gridProp, unsigned int seed = 0);
+      74             : 
+      75             :         static void initTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
+      76             :                                    double lMax, double alpha, int seed);
+      77             : };
+      78             : 
+      79             : // Compatibility with old functions from GridTurbulence:
+      80             : 
+      81             : /** Analytically calculate the correlation length of the simple model turbulent
+      82             :  * field */
+      83           1 : inline double turbulentCorrelationLength(double lMin, double lMax,
+      84             :                                          double alpha = -11 / 3.) {
+      85           2 :         KISS_LOG_WARNING
+      86             :             << "turbulentCorrelationLength is deprecated and will be "
+      87             :                "removed in the future. Replace it with a more appropriate "
+      88           1 :                "turbulent field model and call getCorrelationLength().";
+      89           1 :         return SimpleTurbulenceSpectrum::turbulentCorrelationLength(lMin, lMax,
+      90           1 :                                                                     -alpha - 2);
+      91             : }
+      92             : 
+      93             : /**
+      94             :  Create a random initialization of a turbulent field.
+      95             :  @param grid    grid on which the turbulence is calculated
+      96             :  @param lMin    Minimum wavelength of the turbulence
+      97             :  @param lMax    Maximum wavelength of the turbulence
+      98             :  @param alpha   Power law index of <B^2(k)> ~ k^alpha (alpha = -11/3 corresponds
+      99             :  to a Kolmogorov spectrum)
+     100             :  @param Brms    RMS field strength
+     101             :  @param seed    Random seed
+     102             :  */
+     103           4 : inline void initTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
+     104             :                            double lMax, double alpha = -11 / 3., int seed = 0) {
+     105           8 :         KISS_LOG_WARNING
+     106             :             << "initTurbulence is deprecated and will be removed in the future. "
+     107           4 :                "Replace it with a more appropriate turbulent field model instance.";
+     108           4 :         SimpleGridTurbulence::initTurbulence(grid, Brms, lMin, lMax, alpha, seed);
+     109           1 : }
+     110             : 
+     111             : /** @}*/
+     112             : } // namespace crpropa
+     113             : 
+     114             : #endif // CRPROPA_HAVE_FFTW3F
+     115             : 
+     116             : #endif // CRPROPA_SIMPLEGRIDTURBULENCE_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html new file mode 100644 index 000000000..e588a9cfb --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html @@ -0,0 +1,108 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/TurbulentField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - TurbulentField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:253278.1 %
Date:2024-04-08 14:58:22Functions:4944.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14TurbulentFieldD0Ev0
_ZN7crpropa14TurbulentFieldD2Ev0
_ZN7crpropa18TurbulenceSpectrumD2Ev0
_ZNK7crpropa14TurbulentField20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum21spectrumNormalizationEv1
_ZN7crpropa18TurbulenceSpectrumD0Ev2
_ZN7crpropa18TurbulenceSpectrumC2Edddddd9
_ZNK7crpropa18TurbulenceSpectrum14energySpectrumEd208128
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html new file mode 100644 index 000000000..6e9224a7c --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html @@ -0,0 +1,108 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/TurbulentField.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - TurbulentField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:253278.1 %
Date:2024-04-08 14:58:22Functions:4944.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14TurbulentFieldD0Ev0
_ZN7crpropa14TurbulentFieldD2Ev0
_ZN7crpropa18TurbulenceSpectrumC2Edddddd9
_ZN7crpropa18TurbulenceSpectrumD0Ev2
_ZN7crpropa18TurbulenceSpectrumD2Ev0
_ZNK7crpropa14TurbulentField20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum14energySpectrumEd208128
_ZNK7crpropa18TurbulenceSpectrum20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum21spectrumNormalizationEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html new file mode 100644 index 000000000..dd676ef0c --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html @@ -0,0 +1,195 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/TurbulentField.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentField - TurbulentField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:253278.1 %
Date:2024-04-08 14:58:22Functions:4944.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_TURBULENTFIELD_H
+       2             : #define CRPROPA_TURBULENTFIELD_H
+       3             : 
+       4             : #include "crpropa/magneticField/MagneticField.h"
+       5             : #include <cmath>
+       6             : 
+       7             : namespace crpropa {
+       8             : /**
+       9             :  * \addtogroup MagneticFields
+      10             :  * @{
+      11             :  */
+      12             : 
+      13             : /**
+      14             :  @class TurbulenceSpectrum
+      15             :  @brief Defines the energy spectrum of turbulence parametrizied by A(k) ~ k^q /(1 + k^2)^{(s + q)/2 + 1}
+      16             :  */
+      17             : class TurbulenceSpectrum : public Referenced {
+      18             :   private:
+      19             :         const double Brms; /**< Brms value of the turbulent field (normalization) */
+      20             :         const double sIndex; /**< Spectral index for the inertial range, for example
+      21             :                           s=5/3 for Kolmogorov spectrum; in some parts of the code this
+      22             :                           parameter is referred by alpha which is the total 3D isotropic
+      23             :                           spectrum with additional k^2 and the minus sign, e.g.,
+      24             :                           for Kolmogorov: alpha = -(s + 2) */
+      25             :         const double qIndex; /**< Spectral index for the injection range, for
+      26             :                           example q=4 for 3D homogeneous turbulence */
+      27             :         const double lBendover;  /**< the bend-over scale */
+      28             :         const double lMin, lMax; /**< Min and Max scale of turbulence */
+      29             : 
+      30             :   protected:
+      31             :         /**
+      32             :         Normalization for the below defined Lc
+      33             :         */
+      34           1 :         double spectrumNormalization() const {
+      35           1 :                 return std::tgamma((sIndex + qIndex) / 2.0) /
+      36           1 :                        (2.0 * std::tgamma((sIndex - 1) / 2.0) *
+      37           1 :                         std::tgamma((qIndex + 1) / 2.0));
+      38             :         }
+      39             : 
+      40             :   public:
+      41             :         /**
+      42             :          * @param Brms         root mean square field strength for generated field
+      43             :          * @param lMin   Minimum physical scale of the turbulence
+      44             :          * @param lMax   Maximum physical scale of the turbulence
+      45             :          * @param lBendover        the bend-over scale
+      46             :          * @param sIndex         Spectral index of the energy spectrum in the inertial range
+      47             :          * @param qIndex         Spectral index of the energy spectrum in the energy range
+      48             :         */
+      49           9 :         TurbulenceSpectrum(double Brms, double lMin, double lMax,
+      50             :                            double lBendover = 1, double sIndex = (5. / 3.),
+      51             :                            double qIndex = 4)
+      52           9 :             : Brms(Brms), lMin(lMin), lMax(lMax), lBendover(lBendover),
+      53           9 :               sIndex(sIndex), qIndex(qIndex) {
+      54           9 :                 if (lMin > lMax) {
+      55           0 :                         throw std::runtime_error("TurbulenceSpectrum: lMin > lMax");
+      56             :                 }
+      57           9 :                 if (lMin <= 0) {
+      58           0 :                         throw std::runtime_error("TurbulenceSpectrum: lMin <= 0");
+      59             :                 }
+      60           9 :         }
+      61             : 
+      62           7 :         ~TurbulenceSpectrum() {}
+      63             : 
+      64          31 :         double getBrms() const { return Brms; }
+      65          19 :         double getLmin() const { return lMin; }
+      66          19 :         double getLmax() const { return lMax; }
+      67          22 :         double getLbendover() const { return lBendover; }
+      68           5 :         double getSindex() const { return sIndex; }
+      69           2 :         double getQindex() const { return qIndex; }
+      70             :         
+      71             :         /**
+      72             :         General energy spectrum for synthetic turbulence models (not normalized!)
+      73             :         with normalized ^k = k*lBendover
+      74             :         */
+      75      208128 :         virtual double energySpectrum(double k) const {
+      76      208128 :                 double kHat = k * lBendover;
+      77      208128 :                 return std::pow(kHat, qIndex) /
+      78      208128 :                                        std::pow(1.0 + kHat * kHat,
+      79      208128 :                                         (sIndex + qIndex) / 2.0 + 1.0);
+      80             :         }
+      81             : 
+      82             :         /**
+      83             :   Computes the magnetic field coherence length
+      84             :         Obtained from the definition of \f$l_c = 1/B_{\rm rms}^2 \int_0^\infty dr\langleB(0)B^*(r)\rangle \f$
+      85             :         Approximates the true value correctly as long as lBendover <= lMax/8 (~5%
+      86             :   error) (for the true value the above integral should go from lMin to lMax)
+      87             :         */
+      88           0 :         virtual double getCorrelationLength() const {
+      89           1 :                 return 4 * M_PI / ((sIndex + 2.0) * sIndex) * spectrumNormalization() *
+      90           1 :                        lBendover;
+      91             :         }
+      92             : };
+      93             : 
+      94             : /**
+      95             :  @class TurbulentField
+      96             :  @brief An abstract base class for different models of turbulent magnetic fields
+      97             : 
+      98             :  This module provides common methods for all turbulent (synthetic) magnetic
+      99             :  fields. Does not actually implement any turbulent field.
+     100             :  */
+     101             : class TurbulentField : public MagneticField {
+     102             :   protected:
+     103             :         const TurbulenceSpectrum &spectrum;
+     104             : 
+     105             :   public:
+     106           8 :         TurbulentField(const TurbulenceSpectrum &spectrum) : spectrum(spectrum) {}
+     107           0 :         virtual ~TurbulentField() {}
+     108             : 
+     109           0 :         double getBrms() const { return spectrum.getBrms(); }
+     110           0 :         virtual double getCorrelationLength() const {
+     111           0 :                 return spectrum.getCorrelationLength();
+     112             :         }
+     113             : };
+     114             : 
+     115             : /** @}*/
+     116             : 
+     117             : } // namespace crpropa
+     118             : 
+     119             : #endif // CRPROPA_TURBULENTFIELD_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html new file mode 100644 index 000000000..297188998 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:435972.9 %
Date:2024-04-08 14:58:22Functions:81747.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.h +
0.0%
+
0.0 %0 / 50.0 %0 / 1
TurbulentField.h +
78.1%78.1%
+
78.1 %25 / 3244.4 %4 / 9
SimpleGridTurbulence.h +
81.0%81.0%
+
81.0 %17 / 2157.1 %4 / 7
GridTurbulence.h +
100.0%
+
100.0 %1 / 1-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html new file mode 100644 index 000000000..133acd288 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:435972.9 %
Date:2024-04-08 14:58:22Functions:81747.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.h +
0.0%
+
0.0 %0 / 50.0 %0 / 1
TurbulentField.h +
78.1%78.1%
+
78.1 %25 / 3244.4 %4 / 9
SimpleGridTurbulence.h +
81.0%81.0%
+
81.0 %17 / 2157.1 %4 / 7
GridTurbulence.h +
100.0%
+
100.0 %1 / 1-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html new file mode 100644 index 000000000..c75493324 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:435972.9 %
Date:2024-04-08 14:58:22Functions:81747.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
GridTurbulence.h +
100.0%
+
100.0 %1 / 1-0 / 0
HelicalGridTurbulence.h +
0.0%
+
0.0 %0 / 50.0 %0 / 1
SimpleGridTurbulence.h +
81.0%81.0%
+
81.0 %17 / 2157.1 %4 / 7
TurbulentField.h +
78.1%78.1%
+
78.1 %25 / 3244.4 %4 / 9
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html new file mode 100644 index 000000000..1aa082456 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/MagneticLens.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - MagneticLens.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:204247.6 %
Date:2024-04-08 14:58:22Functions:4666.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLensC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa8LensPartC2Ev0
_ZN7crpropa12MagneticLensC2Eh3
_ZN7crpropa12MagneticLensD2Ev3
_ZN7crpropa8LensPartC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd3
_ZN7crpropa8LensPartD2Ev3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html new file mode 100644 index 000000000..41eba5bb7 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/MagneticLens.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - MagneticLens.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:204247.6 %
Date:2024-04-08 14:58:22Functions:4666.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLensC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa12MagneticLensC2Eh3
_ZN7crpropa12MagneticLensD2Ev3
_ZN7crpropa8LensPartC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd3
_ZN7crpropa8LensPartC2Ev0
_ZN7crpropa8LensPartD2Ev3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html new file mode 100644 index 000000000..1a6c474df --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html @@ -0,0 +1,352 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/MagneticLens.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - MagneticLens.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:204247.6 %
Date:2024-04-08 14:58:22Functions:4666.7 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : //----------------------------------------------------------------------
+       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
+       3             : // a parametrized simulation engine for cosmic rays.
+       4             : //
+       5             : // Copyright (C) 2011   Martin Erdmann, Peter Schiffer, Tobias Winchen
+       6             : //                                                                               RWTH Aachen University, Germany
+       7             : // Contact: winchen@physik.rwth-aachen.de
+       8             : //
+       9             : //      This program is free software: you can redistribute it and/or
+      10             : //      modify it under the terms of the GNU General Public License as
+      11             : //      published by the Free Software Foundation, either version 3 of
+      12             : //      the License, or (at your option) any later version.
+      13             : //
+      14             : //      This program is distributed in the hope that it will be useful,
+      15             : //      but WITHOUT ANY WARRANTY; without even the implied warranty of
+      16             : //      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.    See the
+      17             : //      GNU General Public License for more details.
+      18             : //
+      19             : //      You should have received a copy of the GNU General Public License
+      20             : //      along with this program. If not, see <http://www.gnu.org/licenses/>.
+      21             : //----------------------------------------------------------------------
+      22             : 
+      23             : #ifndef MAGNETICLENS_HH
+      24             : #define MAGNETICLENS_HH
+      25             : 
+      26             : #include "crpropa/magneticLens/ModelMatrix.h"
+      27             : #include "crpropa/magneticLens/Pixelization.h"
+      28             : #include "crpropa/Units.h"
+      29             : #include "crpropa/Vector3.h"
+      30             : 
+      31             : #include <vector>
+      32             : #include <string>
+      33             : #include <stdexcept>
+      34             : #include <fstream>
+      35             : #include <sstream>
+      36             : #include <iostream>
+      37             : #include <stdint.h>
+      38             : 
+      39             : 
+      40             : namespace crpropa
+      41             : {
+      42             : 
+      43             : /// Holds one matrix for the lens and information about the rigidity range
+      44             : class LensPart
+      45             : {
+      46             :         string _filename;
+      47             :         double _rigidityMin;
+      48             :         double _rigidityMax;
+      49             :         ModelMatrixType M;
+      50             :         double _maximumSumOfColumns;
+      51             :         bool _maximumSumOfColumns_calculated;
+      52             : 
+      53             : public:
+      54           0 :         LensPart()
+      55           0 :         {
+      56           0 :         }
+      57             :         /// File containing the matrix to be used in the range rigidityMin,
+      58             :         /// rigidityMax in Joule
+      59           3 :         LensPart(const std::string &filename, double rigidityMin, double rigidityMax) :
+      60           3 :                         _filename(filename), _rigidityMin(rigidityMin), _rigidityMax(rigidityMax), _maximumSumOfColumns_calculated(
+      61           3 :                                         false), _maximumSumOfColumns(0)
+      62             :         {
+      63           3 :         }
+      64             : 
+      65           3 :         ~LensPart()
+      66             :         {
+      67           3 :         }
+      68             : 
+      69             :         /// Loads the matrix from file
+      70             :         void loadMatrixFromFile()
+      71             :         {
+      72           0 :                 deserialize(_filename, M);
+      73           0 :         }
+      74             : 
+      75             :         /// Returns the filename of the matrix
+      76             :         const std::string& getFilename()
+      77             :         {
+      78             :                 return _filename;
+      79             :         }
+      80             : 
+      81             :         /// Calculates the maximum of the sums of columns for the matrix
+      82             :         double getMaximumOfSumsOfColumns()
+      83             :         {
+      84           0 :                 if (!_maximumSumOfColumns_calculated)
+      85             :                 { // lazy calculation of maximum
+      86           0 :                         _maximumSumOfColumns = maximumOfSumsOfColumns(M);
+      87           0 :                         _maximumSumOfColumns_calculated = true;
+      88             :                 }
+      89           0 :                 return _maximumSumOfColumns;
+      90             :         }
+      91             : 
+      92             :         /// Returns the minimum of the rigidity range for the lenspart in eV
+      93             :         double getMinimumRigidity()
+      94             :         {
+      95       12293 :                 return _rigidityMin / eV;
+      96             :         }
+      97             : 
+      98             :         /// Returns the maximum of the rigidity range for the lenspart in eV
+      99             :         double getMaximumRigidity()
+     100             :         {
+     101       12292 :                 return _rigidityMax / eV;
+     102             :         }
+     103             : 
+     104             :         /// Returns the modelmatrix
+     105             :         ModelMatrixType& getMatrix()
+     106             :         {
+     107           0 :                 return M;
+     108             :         }
+     109             : 
+     110             :         /// Sets the modelmatrix
+     111             :         void setMatrix(const ModelMatrixType& m)
+     112             :         {
+     113           3 :                 M = m;
+     114           0 :         }
+     115             : 
+     116             : 
+     117             : };
+     118             : 
+     119             : /// Function to calculate the mean deflection [rad] of the matrix M, given a pixelization
+     120             : //double calculateMeanDeflection(const ModelMatrix &M,
+     121             : //              const Pixelization &pixelization)
+     122             : //{
+     123             : //      double totalDeflection = 0;
+     124             : //      double weightSum = 0;
+     125             : //      for (const_i2_t it1 = M.begin2(); it1 != (M.end2()); it1++)
+     126             : //      {
+     127             : //              for (const_i1_t it2 = it1.begin(); it2 != it1.end(); it2++)
+     128             : //              {
+     129             : //                      totalDeflection+= pixelization.angularDistance(it2.index1(),
+     130             : //                                      it2.index2()) * (*it2) ;
+     131             : //                      weightSum+= (*it2);
+     132             : //              }
+     133             : //      }
+     134             : //      return totalDeflection / weightSum;
+     135             : //}
+     136             : 
+     137             : typedef std::vector<LensPart*>::iterator LensPartIter;
+     138             : typedef std::vector<LensPart*>::const_iterator const_LensPartIter;
+     139             : 
+     140             : /**
+     141             :  * \addtogroup MagneticLenses 
+     142             :  * @{
+     143             :  */
+     144             : 
+     145             : /// The lens for the galactic magnetic field.
+     146             : /// Note that the energies refer to protons (Z=1). To be used with other particles with a different charge number please select the rigidity accordingly.
+     147             : class MagneticLens
+     148             : {
+     149             : 
+     150             :         void updateRigidityBounds(double rigidityMin, double rigidityMax);
+     151             : 
+     152             :         /// Loads part of a lens (one matrix) from file to use it in given rigidity range.
+     153             :         void loadLensPart(const string &filename, double rigidityMin,
+     154             :                         double rigidityMax);
+     155             : 
+     156             :         // Stores the individual lenses
+     157             :         std::vector<LensPart*> _lensParts;
+     158             :         Pixelization* _pixelization;
+     159             :         // Checks Matrix, raises Errors if not ok - also generate
+     160             :         // _pixelization if called first time
+     161             :         void _checkMatrix(const ModelMatrixType &M);
+     162             :         // minimum / maximum rigidity that is covered by the lens [Joule]
+     163             :         double _minimumRigidity;
+     164             :         double _maximumRigidity;
+     165             :         static bool _randomSeeded;
+     166             :         double _norm;
+     167             : 
+     168             : public:
+     169             :         /// Default constructor
+     170           0 :         MagneticLens() :
+     171           0 :                         _pixelization(NULL), _minimumRigidity(DBL_MAX), _maximumRigidity(DBL_MIN), _norm(1)
+     172             :         {
+     173             :         }
+     174             : 
+     175             :         /// Constructs lens with predefined healpix order
+     176           3 :         MagneticLens(uint8_t healpixorder) :
+     177           3 :                         _pixelization(NULL), _minimumRigidity(DBL_MAX), _maximumRigidity(DBL_MIN)
+     178             :         {
+     179           3 :                 _pixelization = new Pixelization(healpixorder);
+     180           3 :         }
+     181             : 
+     182             :         /// Construct lens and load lens from file
+     183           0 :         MagneticLens(const string &filename) :
+     184           0 :                         _pixelization(NULL), _minimumRigidity(DBL_MAX), _maximumRigidity(DBL_MIN)
+     185             :         {
+     186           0 :                 loadLens(filename);
+     187           0 :         }
+     188             : 
+     189             :         /// Returns the pixelization used
+     190             :         const Pixelization& getPixelization() const
+     191             :         {
+     192           0 :                 return (*_pixelization);
+     193             :         }
+     194             : 
+     195             :         /// Default destructor
+     196           3 :         ~MagneticLens()
+     197             :         {
+     198           3 :                 if (_pixelization)
+     199           3 :                         delete _pixelization;
+     200           3 :                 for (std::vector<LensPart*>::iterator iter = _lensParts.begin();
+     201           6 :                                 iter != _lensParts.end(); iter++)
+     202             :                 {
+     203           3 :                         delete (*iter);
+     204             :                 }
+     205             :                 _lensParts.clear();
+     206           3 :         }
+     207             : 
+     208             :         /// Try to transform the comsic ray to a new direction.
+     209             :         /// Returns false and does not change phi and theta if the cosmic ray is
+     210             :         /// lost due to conservation of cosmic ray flux.
+     211             :         /// Rigidity is given in Joule, phi and theta in rad
+     212             :         bool transformCosmicRay(double rigidity, double& phi, double& theta);
+     213             : 
+     214             :         /// Tries transform a cosmic ray with momentum vector p
+     215             :         bool transformCosmicRay(double rigidity, Vector3d &p);
+     216             : 
+     217             :         /// transforms the model array assuming that model points to an array of the
+     218             :         /// correct size. Rigidity is given in Joule
+     219             :         void transformModelVector(double* model, double rigidity) const;
+     220             : 
+     221             :         /// Loads M as part of a lens and use it in given rigidity range with
+     222             :         /// rigidities given in Joule
+     223             :         void setLensPart(const ModelMatrixType &M, double rigidityMin, double rigidityMax);
+     224             : 
+     225             :         /// Loads a lens from a given file, containing lines like
+     226             :         /// lensefile.MLDAT rigidityMin rigidityMax
+     227             :         /// rigidities are given in logarithmic units [log10(E / eV)]
+     228             :         void loadLens(const string &filename);
+     229             : 
+     230             :         /// Normalizes the lens parts to the maximum of sums of columns of
+     231             :         /// every lenspart. By doing this, the lens won't distort the spectrum
+     232             :         void normalizeLens();
+     233             : 
+     234             :         /// Normalizes the lens parts individually. Normalized this way, the
+     235             :         /// lens generally distorts the spectrum of the sources, but deflects
+     236             :         /// the UHECR more efficiently.
+     237             :         void normalizeLensparts();
+     238             : 
+     239             :         /// Checks if rigidity [Joule] is covered by lens
+     240             :         bool rigidityCovered(double rigidity) const;
+     241             : 
+     242             :         /// Normalizes all matrix columns - the lens will then create fake
+     243             :         /// anisotropies, but won't drop particles
+     244             :         void normalizeMatrixColumns();
+     245             : 
+     246             :         /// Returns minimum rigidity covered by lens, in eV
+     247             :         double getMinimumRigidity() const
+     248             :         {
+     249           0 :                 return _minimumRigidity / eV;
+     250             :         }
+     251             :         /// Returns maximum rigidity covered by lens, in eV
+     252             :         double getMaximumRigidity() const
+     253             :         {
+     254           0 :                 return _maximumRigidity / eV;
+     255             :         }
+     256             : 
+     257             :         //      returns the norm used for the lenses
+     258             :         double getNorm()
+     259             :         {
+     260           0 :                 return _norm;
+     261             :         }
+     262             : 
+     263             :         /// Returns iterator to the lens part with rigidity Joule
+     264             :         LensPart* getLensPart(double rigidity) const;
+     265             : 
+     266             :         /// Returns all lens parts
+     267             :         const std::vector<LensPart*>& getLensParts() const
+     268             :         {
+     269           0 :                 return _lensParts;
+     270             :         }
+     271             : };
+     272             : 
+     273             : /** @}*/
+     274             : } // namespace
+     275             : 
+     276             : #endif // MAGNETICLENS_HH
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html new file mode 100644 index 000000000..907daed16 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/ParticleMapsContainer.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - ParticleMapsContainer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21020.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer9getWeightEid0
_ZN7crpropa21ParticleMapsContainerC2Edd2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html new file mode 100644 index 000000000..1197e3fa1 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/ParticleMapsContainer.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - ParticleMapsContainer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21020.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer9getWeightEid0
_ZN7crpropa21ParticleMapsContainerC2Edd2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html new file mode 100644 index 000000000..b652fe992 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html @@ -0,0 +1,221 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/ParticleMapsContainer.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - ParticleMapsContainer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21020.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_PARTICLEMAPSCONTAINER_HH
+       2             : #define CRPROPA_PARTICLEMAPSCONTAINER_HH
+       3             : 
+       4             : #include <map>
+       5             : #include <vector>
+       6             : #include "crpropa/magneticLens/Pixelization.h"
+       7             : #include "crpropa/magneticLens/MagneticLens.h"
+       8             : 
+       9             : #include "crpropa/Vector3.h"
+      10             : 
+      11             : namespace crpropa {
+      12             : /**
+      13             :  * \addtogroup MagneticLenses 
+      14             :  * @{
+      15             :  */
+      16             : 
+      17             : /** 
+      18             :  @class ParticleMapsContainer
+      19             :  @brief A container for particle maps
+      20             : 
+      21             :  The maps are stored with discrete energies on a logarithmic scale. The
+      22             :  default energy width is 0.02 with an energy bin from 10**17.99 - 10**18.01 eV.
+      23             :  */
+      24             : class ParticleMapsContainer {
+      25             : private:
+      26             :         std::map<int, std::map <int, double*> > _data;
+      27             :         Pixelization _pixelization;
+      28             :         double _deltaLogE;
+      29             :         double _bin0lowerEdge;
+      30             : 
+      31             :         // get the bin number of the energy
+      32             :         int energy2Idx(double energy) const;
+      33             :         double idx2Energy(int idx) const;
+      34             : 
+      35             :         // weights of the particles
+      36             :         double _sumOfWeights;
+      37             :         std::map<int, double > _weightsPID;
+      38             :         std::map<int, map<int, double> > _weights_pidEnergy;
+      39             : 
+      40             :         // lazy update of weights
+      41             :         bool _weightsUpToDate;
+      42             :         void _updateWeights();
+      43             : 
+      44             : public:
+      45             :         /** Constructor.
+      46             :          @param deltaLogE               width of logarithmic energy bin [in eV]
+      47             :          @param bin0lowerEdge   logarithm of energy of the lower edge of first bin [in log(eV)]
+      48             :          */
+      49           2 :         ParticleMapsContainer(double deltaLogE = 0.02, double bin0lowerEdge = 17.99) : _deltaLogE(deltaLogE), _bin0lowerEdge(bin0lowerEdge), _pixelization(6), _weightsUpToDate(false), _sumOfWeights(0) {
+      50           2 :         }
+      51             :         /** Destructor.
+      52             :          */
+      53             :         ~ParticleMapsContainer();
+      54             : 
+      55             :         size_t getNumberOfPixels() {
+      56           0 :                 return _pixelization.getNumberOfPixels();
+      57             :         }
+      58             : 
+      59             :         /** Get the map for the particleId with the given energy.
+      60             :          @param particleId              id of the particle following the PDG numbering scheme
+      61             :          @param energy                  the energy of the particle [in Joules]
+      62             :          @returns The map for a given particleId with a given energy
+      63             :          */
+      64             :         double *getMap(const int particleId, double energy);
+      65             : 
+      66             :         /** Adds a particle to the map container.
+      67             :          @param particleId                      id of the particle following the PDG numbering scheme
+      68             :          @param energy                          the energy of the particle [in Joules]
+      69             :          @param galacticLongitude       galactic longitude [radians]
+      70             :          @param galacticLatitude        galactic latitude [radians]
+      71             :          @param weight                          relative weight for the specific particle
+      72             :         */
+      73             :         void addParticle(const int particleId, double energy, double galacticLongitude, double galacticLatitude, double weight = 1);
+      74             :         /** Adds a particle to the map container.
+      75             :          @param particleId                      id of the particle following the PDG numbering scheme
+      76             :          @param energy                          the energy of the particle [in Joules]
+      77             :          @param v                                       vector containing the arrival directions of a particle
+      78             :          @param weight                          relative weight for the specific particle
+      79             :         */
+      80             :         void addParticle(const int particleId, double energy, const Vector3d &v, double weight = 1);
+      81             : 
+      82             :         /** Get all particle ids in the map.
+      83             :          @returns Vector of all ids.
+      84             :          */
+      85             :         std::vector<int> getParticleIds();
+      86             : 
+      87             :         /** Get energies in map.
+      88             :          @param pid     id of the particle following the PDG numbering scheme
+      89             :          @returns Energies are returned in units of eV (unlike in other CRPropa modules) for performance reasons
+      90             :          */
+      91             :         std::vector<double> getEnergies(int pid);
+      92             : 
+      93             :         void applyLens(MagneticLens &lens);;
+      94             : 
+      95             :         /** Get random particles from map.
+      96             :          The arguments are the vectors where the information will be stored.
+      97             :          @param N                                       number of particles to be selected
+      98             :          @param particleId                      id of the particle following the PDG numbering scheme
+      99             :          @param energy                          energy of interest [in eV]
+     100             :          @param galacticLongitudes      longitude in the interval [-pi, pi] [in radians]
+     101             :          @param galacticLatitudes       latitude in the interval [-pi/2, pi/2] [in radians]
+     102             :          */
+     103             :         void getRandomParticles(size_t N, vector<int> &particleId,
+     104             :                 vector<double> &energy, vector<double> &galacticLongitudes,
+     105             :                 vector<double> &galacticLatitudes);
+     106             : 
+     107             :         /** Places a particle with given id and energy according to the  probability maps. 
+     108             :          @param pid                                     id of the particle following the PDG numbering scheme
+     109             :          @param energy                          energy of interest [in eV]
+     110             :          @param galacticLongitude       longitude in the interval [-pi, pi] [in radians]
+     111             :          @param galacticLatitude        latitude in the interval [-pi/2, pi/2] [in radians]
+     112             :          @returns Returns false if operation not possible; true otherwise.
+     113             :          */
+     114             :         bool placeOnMap(int pid, double energy, double &galacticLongitude, double &galacticLatitude);
+     115             : 
+     116             :         /** Force weight update prior to getting random particles. 
+     117             :          Only necessary when reusing pointer to maps after calculating weights.
+     118             :         */
+     119             :         void forceWeightUpdate();
+     120             : 
+     121             :         /** Get sum of weights of the maps.
+     122             :          @returns Sum of all weights.
+     123             :          */
+     124             :         double getSumOfWeights() {
+     125           0 :                 if (!_weightsUpToDate)
+     126           0 :                         _updateWeights();
+     127           0 :                 return _sumOfWeights;
+     128             :         }
+     129             : 
+     130             :         /** Get weight for a given particle and energy
+     131             :          @param pid                                     id of the particle following the PDG numbering scheme
+     132             :          @param energy                          energy of interest [in eV]
+     133             :          @returns Weight for the chosen particle and energy.
+     134             :          */
+     135           0 :         double getWeight(int pid, double energy) {
+     136           0 :                 if (!_weightsUpToDate)
+     137           0 :                         _updateWeights();
+     138           0 :                 return _weights_pidEnergy[pid][energy2Idx(energy)];
+     139             :         }
+     140             : };
+     141             : /** @}*/
+     142             : 
+     143             : } // namespace crpropa
+     144             : 
+     145             : #endif // CRPROPA_PARTICLEMAPSCONTAINER_HH
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html new file mode 100644 index 000000000..728ad5e1e --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/Pixelization.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - Pixelization.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81844.4 %
Date:2024-04-08 14:58:22Functions:1333.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization15getPixelsInConeEdddRSt6vectorIiSaIiEE0
_ZN7crpropa12PixelizationC2Ev0
_ZN7crpropa12PixelizationC2Eh10
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html new file mode 100644 index 000000000..cc5239816 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/Pixelization.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - Pixelization.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81844.4 %
Date:2024-04-08 14:58:22Functions:1333.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization15getPixelsInConeEdddRSt6vectorIiSaIiEE0
_ZN7crpropa12PixelizationC2Eh10
_ZN7crpropa12PixelizationC2Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html new file mode 100644 index 000000000..370ed122b --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html @@ -0,0 +1,217 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens/Pixelization.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLens - Pixelization.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81844.4 %
Date:2024-04-08 14:58:22Functions:1333.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : //----------------------------------------------------------------------
+       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
+       3             : // a parametrized simulation engine for cosmic rays.
+       4             : //
+       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
+       6             : //                     RWTH Aachen University, Germany
+       7             : // Contact: winchen@physik.rwth-aachen.de
+       8             : //
+       9             : //  This program is free software: you can redistribute it and/or
+      10             : //  modify it under the terms of the GNU General Public License as
+      11             : //  published by the Free Software Foundation, either version 3 of
+      12             : //  the License, or (at your option) any later version.
+      13             : //
+      14             : //  This program is distributed in the hope that it will be useful,
+      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      17             : //  GNU General Public License for more details.
+      18             : //
+      19             : //  You should have received a copy of the GNU General Public License
+      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
+      21             : //----------------------------------------------------------------------
+      22             : 
+      23             : 
+      24             : #ifndef PIXELIZATION_HH
+      25             : #define PIXELIZATION_HH
+      26             : 
+      27             : #include "healpix_base/healpix_base.h"
+      28             : #include <cmath>
+      29             : #include <stdint.h>
+      30             : 
+      31             : namespace crpropa
+      32             : {
+      33             : /**
+      34             :  * \addtogroup MagneticLenses
+      35             :  * @{
+      36             :  */
+      37             : 
+      38             : /// Helpers to makes work with Healpix smooth
+      39             : const uint8_t _nOrder_max = 13;
+      40             : const uint32_t _nPix[] =
+      41             : {
+      42             :                 48,
+      43             :                 192,
+      44             :                 768,
+      45             :                 3072,
+      46             :                 12288,
+      47             :                 49152,
+      48             :                 196608,
+      49             :                 786432,
+      50             :                 3145728,
+      51             :                 12582912,
+      52             :                 50331648,
+      53             :                 201326592,
+      54             :                 805306368
+      55             : };
+      56             : 
+      57             : /// Every communication with healpix is done through this class to avoid
+      58             : /// bugs with missmatching coordinates (and make python hooks easier)
+      59             : class Pixelization
+      60             : {
+      61             : public:
+      62           0 :         Pixelization()
+      63           0 :         {
+      64           0 :                 _healpix = new healpix::T_Healpix_Base<int>(6, healpix::RING);
+      65           0 :         }
+      66             : 
+      67             :         /// Constructor creating Pixelization with healpix order 6 (about
+      68             :         /// 50000 pixels)
+      69          10 :         Pixelization(uint8_t order)
+      70          10 :         {
+      71          10 :                 _healpix = new healpix::T_Healpix_Base<int>(order, healpix::RING);
+      72          10 :         }
+      73             : 
+      74             :         ~Pixelization()
+      75             :         {
+      76          10 :                 delete _healpix;
+      77          10 :         }
+      78             : 
+      79             :         /// Returns the number of the pixel which includes the direction (phi,theta)
+      80             :         /// phi in [-pi, pi], theta in [-pi/2, pi/2]
+      81             :         uint32_t direction2Pix(double longitude, double latitude) const;
+      82             : 
+      83             :         /// Returns the number of pixels of the pixelization
+      84             :         uint32_t nPix() const
+      85             :         {
+      86       86026 :                 return _healpix->Npix();
+      87             :         }
+      88             : 
+      89             :         /// Returns the number of pixels given by healpix order
+      90             :         static uint32_t nPix(uint8_t order);
+      91             : 
+      92             :         /// Returns the number of pixels of the pixelization
+      93             :         int getNumberOfPixels()
+      94             :         {
+      95    10317737 :                 return _healpix->Npix();
+      96             :         }
+      97             : 
+      98             :         /// Returns the order, a given pixel number corresponds to. 0 if no
+      99             :         /// match!
+     100             :         static uint8_t pix2Order(uint32_t pix);
+     101             : 
+     102             :         /// Gives the center of pixel i in longitude [rad] and latitude [rad]
+     103             :         void pix2Direction(uint32_t i, double &longitude, double &latitude) const;
+     104             : 
+     105             :         /// Calculate the angle [rad] between the vectors pointing to pixels i and j
+     106             :         double angularDistance(uint32_t i, uint32_t j) const;
+     107             : 
+     108             :         /// Returns the maximum possible pixelization order
+     109             :         uint8_t getMaxOrder() const
+     110             :         {
+     111             :                 return _nOrder_max;
+     112             :         }
+     113             : 
+     114             :   /// Returns healpix order
+     115             :   uint8_t getOrder() const
+     116             :   {
+     117           0 :     return _healpix->Order();
+     118             :   }
+     119             : 
+     120             :         void getRandomDirectionInPixel(uint32_t pixel, double &longitude, double &latitude);
+     121             : 
+     122           0 :         void getPixelsInCone(double longitude, double latitude,double radius, std::vector<int>& listpix)
+     123             :         {
+     124             :                 healpix::vec3 v;
+     125           0 :                 spherCo2Vec(longitude, latitude, v);
+     126             :                 healpix::pointing p;
+     127           0 :                 p.from_vec3(v);
+     128           0 :                 _healpix->query_disc(p, radius, listpix);
+     129           0 :         }
+     130             : 
+     131             : private:
+     132             :         void spherCo2Vec(double phi, double theta, healpix::vec3 &V) const;
+     133             :         void vec2SphereCo(double &phi , double &theta, const healpix::vec3 &V) const;
+     134             :         healpix::T_Healpix_Base<int> *_healpix;
+     135             :         static healpix::T_Healpix_Base<healpix::int64> _healpix_nest;
+     136             : };
+     137             : 
+     138             : 
+     139             : /** @}*/
+     140             : } // namespace
+     141             : #endif // PIXELIZATION_HH
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html b/doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html new file mode 100644 index 000000000..6f02276e0 --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:307042.9 %
Date:2024-04-08 14:58:22Functions:61154.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Pixelization.h +
44.4%44.4%
+
44.4 %8 / 1833.3 %1 / 3
ParticleMapsContainer.h +
20.0%20.0%
+
20.0 %2 / 1050.0 %1 / 2
MagneticLens.h +
47.6%47.6%
+
47.6 %20 / 4266.7 %4 / 6
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html b/doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html new file mode 100644 index 000000000..053630cae --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:307042.9 %
Date:2024-04-08 14:58:22Functions:61154.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ParticleMapsContainer.h +
20.0%20.0%
+
20.0 %2 / 1050.0 %1 / 2
Pixelization.h +
44.4%44.4%
+
44.4 %8 / 1833.3 %1 / 3
MagneticLens.h +
47.6%47.6%
+
47.6 %20 / 4266.7 %4 / 6
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/magneticLens/index.html b/doc/coverageReport/include/crpropa/magneticLens/index.html new file mode 100644 index 000000000..279e0695b --- /dev/null +++ b/doc/coverageReport/include/crpropa/magneticLens/index.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/magneticLens + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:307042.9 %
Date:2024-04-08 14:58:22Functions:61154.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticLens.h +
47.6%47.6%
+
47.6 %20 / 4266.7 %4 / 6
ParticleMapsContainer.h +
20.0%20.0%
+
20.0 %2 / 1050.0 %1 / 2
Pixelization.h +
44.4%44.4%
+
44.4 %8 / 1833.3 %1 / 3
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html new file mode 100644 index 000000000..2d2c7d39b --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Cordes.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Cordes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html new file mode 100644 index 000000000..8ec13117b --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Cordes.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Cordes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html new file mode 100644 index 000000000..0ec8b1bff --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html @@ -0,0 +1,121 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Cordes.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Cordes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_CORDES_H
+       2             : #define CRPROPA_CORDES_H
+       3             : 
+       4             : #include "crpropa/massDistribution/Density.h"
+       5             : 
+       6             : #include <cmath>
+       7             : #include <string>
+       8             : 
+       9             : namespace crpropa {
+      10             : /**
+      11             :         @class Cordes
+      12             :         @brief Cylindrical symetrical model of the density of ionised hydrogen (HII) of the Milky Way
+      13             :         Cordes et al., 1991, Nature 353,737
+      14             :         */
+      15           1 : class Cordes: public Density {
+      16             : private:
+      17             :         // DO NOT CHANGE model type!
+      18             :         bool isforHI = false;
+      19             :         bool isforHII = true;
+      20             :         bool isforH2 = false;
+      21             : 
+      22             : public:
+      23             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      24             :          @return density in parts/m^3 */
+      25             :         double getDensity(const Vector3d &position) const;
+      26             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      27             :          @return density of ionised hydrogen in parts/m^3, equal getDensity thus no other type is included for Cordes */
+      28             :         double getHIIDensity(const Vector3d &position) const;
+      29             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      30             :          @return density of nucleons in parts/m^3, equal getDensity thus only HII is included for Cordes */
+      31             :         double getNucleonDensity(const Vector3d &position) const;
+      32             : 
+      33             :         /** @return activation status of HI */
+      34             :         bool getIsForHI();
+      35             :         /** @return activation status of HII */
+      36             :         bool getIsForHII();
+      37             :         /** @return activation status of H2 */
+      38             :         bool getIsForH2();
+      39             : 
+      40             :         std::string getDescription();
+      41             : };
+      42             : 
+      43             : }  // namespace crpropa
+      44             : 
+      45             : #endif  // CRPROPA_CORDES_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html new file mode 100644 index 000000000..61d743401 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Density.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Density.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Density10getIsForH2Ev0
_ZN7crpropa7Density10getIsForHIEv0
_ZN7crpropa7Density11getIsForHIIEv0
_ZN7crpropa7Density14getDescriptionB5cxx11Ev0
_ZN7crpropa7DensityD0Ev0
_ZN7crpropa7DensityD2Ev0
_ZNK7crpropa7Density10getDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getH2DensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getHIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density13getHIIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density17getNucleonDensityERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html new file mode 100644 index 000000000..f9ed0dff3 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Density.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Density.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Density10getIsForH2Ev0
_ZN7crpropa7Density10getIsForHIEv0
_ZN7crpropa7Density11getIsForHIIEv0
_ZN7crpropa7Density14getDescriptionB5cxx11Ev0
_ZN7crpropa7DensityD0Ev0
_ZN7crpropa7DensityD2Ev0
_ZNK7crpropa7Density10getDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getH2DensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getHIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density13getHIIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density17getNucleonDensityERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html new file mode 100644 index 000000000..5b9e5404b --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html @@ -0,0 +1,134 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Density.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Density.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_DENSITY_H
+       2             : #define CRPROPA_DENSITY_H
+       3             : 
+       4             : #include "crpropa/Units.h"
+       5             : #include "crpropa/Vector3.h"
+       6             : #include "crpropa/Referenced.h"
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10             : /**
+      11             :  @class Density
+      12             :  @brief Abstract base class for target densities
+      13             :  */
+      14           0 : class Density: public Referenced {
+      15             : public:
+      16           0 :         virtual ~Density() {
+      17           0 :         }
+      18             : 
+      19           0 :         virtual double getDensity(const Vector3d &position) const {  // sum of all densities
+      20           0 :                 return 0;
+      21             :         }
+      22             : 
+      23           0 :         virtual double getHIDensity(const Vector3d &position) const {
+      24           0 :                 return 0;
+      25             :         }
+      26             : 
+      27           0 :         virtual double getHIIDensity(const Vector3d &position) const {
+      28           0 :                 return 0;
+      29             :         }
+      30             : 
+      31           0 :         virtual double getH2Density(const Vector3d &position) const {
+      32           0 :                 return 0;
+      33             :         }
+      34             : 
+      35           0 :         virtual double getNucleonDensity(const Vector3d &position) const {  // sum of nucleons (H2 with factor 2)
+      36           0 :                 return 0;
+      37             :         }
+      38             : 
+      39           0 :         virtual bool getIsForHI() {
+      40           0 :                 return false;
+      41             :         }
+      42             : 
+      43           0 :         virtual bool getIsForHII() {
+      44           0 :                 return false;
+      45             :         }
+      46             : 
+      47           0 :         virtual bool getIsForH2() {
+      48           0 :                 return false;
+      49             :         }
+      50             : 
+      51           0 :         virtual std::string getDescription() {
+      52           0 :                 return "Abstract Density Module\n";
+      53             :         }
+      54             : };
+      55             : 
+      56             : }  // namespace crpropa
+      57             : 
+      58             : #endif  // CRPROPA_DENSITY_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html new file mode 100644 index 000000000..7bb1afb24 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Ferriere.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Ferriere.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html new file mode 100644 index 000000000..9357468f5 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Ferriere.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Ferriere.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html new file mode 100644 index 000000000..f69801f4a --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html @@ -0,0 +1,153 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Ferriere.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Ferriere.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_FERRIERE_H
+       2             : #define CRPROPA_FERRIERE_H
+       3             : 
+       4             : #include "crpropa/massDistribution/Density.h"
+       5             : 
+       6             : #include <cmath>
+       7             : #include <string>
+       8             : 
+       9             : namespace crpropa {
+      10             : /**
+      11             :  @class Ferriere
+      12             :  @brief model of the distribution of hydrogen in the Milky Way
+      13             :   Here in model Ferriere 2007
+      14             :   seperated in 2 regions (inner, outer). The border is for R=3 kpc in galactocentric radius.
+      15             :   model is discribed in
+      16             : outer: ApJ, 497, 759
+      17             : inner:  arxiv:  astro-ph/0702532
+      18             : */
+      19           2 : class Ferriere: public Density {
+      20             : private:
+      21             :         // standard for all types of distribution
+      22             :         bool isforHI = true;
+      23             :         bool isforHII = true;
+      24             :         bool isforH2 = true;
+      25             :         double Rsun = 8.5 * kpc;  // distance sun-galactic center
+      26             : 
+      27             : public:
+      28             :         /** Coordinate transformation for the CentralMolecularZone region. Rotation arround z-axis such that X is the major axis and Y is the minor axis
+      29             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      30             :         @return position in local coordinates for the CMZ region
+      31             :         */
+      32             :         Vector3d CMZTransformation(const Vector3d &position) const;
+      33             :         
+      34             :         /** Coordinate transformation for the galactic bulge disk region in galactic center. Rotation arround the x-axis, the y'-axis and the x''-axis. Difened with X along the major axis, Y along the minor axis and Z along the northern normal
+      35             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      36             :         @return position in local coordinates for the GB disk region
+      37             :         */
+      38             :         Vector3d DiskTransformation(const Vector3d &position) const;
+      39             : 
+      40             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      41             :          @return density in parts/m^3, only acitvated parts are summed up */
+      42             :         double getDensity(const Vector3d &position) const;
+      43             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      44             :          @return density of atomic hydrogen in parts/m^3 */
+      45             :         double getHIDensity(const Vector3d &position) const;
+      46             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      47             :          @return density of ionised hydrogen in parts/m^3 */
+      48             :         double getHIIDensity(const Vector3d &position) const;
+      49             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      50             :          @return density of molecular hydrogen in parts/m^3 */
+      51             :         double getH2Density(const Vector3d &position) const;
+      52             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      53             :          @return nucleon density in parts/m^3, only activated parts are summed up and H2 is weighted twice */
+      54             :         double getNucleonDensity(const Vector3d &position) const;
+      55             : 
+      56             :         /** changes activation status for atomic hydrogen */
+      57             :         void setIsForHI(bool HI);
+      58             :         /** changes activation status for ionised hydrogen */
+      59             :         void setIsForHII(bool HII);
+      60             :         /** changes activation status for molecular hydrogen */
+      61             :         void setIsForH2(bool H2);
+      62             : 
+      63             :         /** @return activation status for atomic hydrogen */
+      64             :         bool getIsForHI();
+      65             :         /** @return activation status for ionised hydrogen */
+      66             :         bool getIsForHII();
+      67             :         /** @return activation status for molecular hydrogen */
+      68             :         bool getIsForH2();
+      69             : 
+      70             :         std::string getDescription();
+      71             : };
+      72             : 
+      73             : }  // namespace crpropa
+      74             : 
+      75             : #endif  // CRPROPA_FERRIERE_H
+      76             : 
+      77             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html new file mode 100644 index 000000000..f746939ad --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Massdistribution.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Massdistribution.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html new file mode 100644 index 000000000..af406a149 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Massdistribution.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Massdistribution.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html new file mode 100644 index 000000000..a34abbae2 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html @@ -0,0 +1,212 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Massdistribution.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Massdistribution.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_MASSDISTRIBUTION_H
+       2             : #define CRPROPA_MASSDISTRIBUTION_H
+       3             : 
+       4             : #include "crpropa/massDistribution/Density.h"
+       5             : #include "crpropa/Vector3.h"
+       6             : #include "crpropa/Grid.h"
+       7             : 
+       8             : #include "kiss/logger.h"
+       9             : 
+      10             : #include <vector>
+      11             : 
+      12             : namespace crpropa {
+      13             : 
+      14             : /**
+      15             :  @class DensityList
+      16             :  @brief Superposition of density models.
+      17             :  The addDensity function adds a new density to the list.
+      18             :  The getDensity function handles the activated types in loaded densities, whereas get(type)Density disregards the activation state.
+      19             : */
+      20           2 : class DensityList: public Density {
+      21             : private:
+      22             :         std::vector<ref_ptr<Density> > DensityList ;
+      23             : 
+      24             : public:
+      25             :         /** Add new density to list.
+      26             :          @param density density to add
+      27             :         */
+      28             :         void addDensity(ref_ptr<Density> density);
+      29             : 
+      30             :         /** Get density at a given position.
+      31             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      32             :          @returns Density in particles/m^3, sum up densities from added densities 
+      33             :         */
+      34             :         double getDensity(const Vector3d &position) const;
+      35             :         /** Get HI density at a given position.
+      36             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      37             :          @returns Density of HI at given position in particles/m^3, sum up all HI densities from added densities
+      38             :          */
+      39             :         double getHIDensity(const Vector3d &position) const;
+      40             :         /** Get HII density at a given position.
+      41             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      42             :          @returns Density of HII at given position in particles/m^3, sum up all HII densities from added densities 
+      43             :          */
+      44             :         double getHIIDensity(const Vector3d &position) const;
+      45             :         /** Get H2 density at a given position.
+      46             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      47             :          @returns Density of H2 at given position in particles/m^3, sum up all H2 densities from added densities 
+      48             :          */
+      49             :         double getH2Density(const Vector3d &position) const;
+      50             :         /** Get the density of nucleons.
+      51             :          This is the number of nucleons per volume, summed up all activated density and weight molecular hydrogyen twice
+      52             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      53             :          @returns Density of nucleons at given position in particles/m^3, sum up all nucleon densities from added densities 
+      54             :          */
+      55             :         double getNucleonDensity(const Vector3d &position) const;
+      56             : 
+      57             :         std::string getDescription();
+      58             : };
+      59             : 
+      60             : /**
+      61             :  @class DensityGrid
+      62             :  @brief Wrapper to use a Grid1f for a density
+      63             : 
+      64             :  The DensityGrid uses a given grid for the chosen density type. More than one type can be chosen to follow the same distribution.
+      65             :  If no type is chosen a warning will be raised and all densities are 0.
+      66             : */
+      67           4 : class DensityGrid: public Density {
+      68             : private: 
+      69             :         ref_ptr<Grid1f> grid; //< Grid with data
+      70             :         bool isForHI, isForHII, isForH2; 
+      71             :         void checkAndWarn(); //< raise a warning if all density types are deactivated.
+      72             : 
+      73             : public:
+      74             :         DensityGrid(ref_ptr<Grid1f> grid, bool isForHI = false, bool isForHII = false, bool isForH2 = false);
+      75             :         
+      76             :         /** Get HI density at a given position.
+      77             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      78             :          @returns Density of HI at given position in particles/m^3, sum up all HI densities from added densities
+      79             :          */
+      80             :         double getHIDensity(const Vector3d &position) const;
+      81             :         
+      82             :         /** Get HII density at a given position.
+      83             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      84             :          @returns Density of HII at given position in particles/m^3, sum up all HII densities from added densities 
+      85             :          */
+      86             :         double getHIIDensity(const Vector3d &position) const;
+      87             :         
+      88             :         /** Get H2 density at a given position.
+      89             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      90             :          @returns Density of H2 at given position in particles/m^3, sum up all H2 densities from added densities 
+      91             :          */
+      92             :         double getH2Density(const Vector3d &position) const;
+      93             : 
+      94             :         /** Get density at a given position.
+      95             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+      96             :          @returns Density in particles/m^3, sum up densities from added densities 
+      97             :         */
+      98             :         double getDensity(const Vector3d &position) const;
+      99             :         
+     100             :         /** Get the density of nucleons.
+     101             :          This is the number of nucleons per volume, summed up all activated density and weight molecular hydrogyen twice
+     102             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
+     103             :          @returns Density of nucleons at given position in particles/m^3, sum up all nucleon densities from added densities 
+     104             :          */
+     105             :         double getNucleonDensity(const Vector3d &position) const;
+     106             : 
+     107             :         bool getIsForHI();
+     108             :         bool getIsForHII();
+     109             :         bool getIsForH2();
+     110             : 
+     111             :         /* set if the density is for HI type. 
+     112             :          @param b if True the density is used for HI
+     113             :         */
+     114             :         void setIsForHI(bool b);
+     115             : 
+     116             :         /* set if the density is for HII type. 
+     117             :          @param b if True the density is used for HII
+     118             :         */
+     119             :         void setIsForHII(bool b);
+     120             : 
+     121             :         /* set if the density is for H2 type. 
+     122             :          @param b if True the density is used for H2
+     123             :         */
+     124             :         void setIsForH2(bool b);
+     125             :         
+     126             :         /* Change the grid for the density
+     127             :          @param grid (Grid1f) new grid for the density. 
+     128             :         */
+     129             :         void setGrid(ref_ptr<Grid1f> grid);
+     130             : 
+     131             :         std::string getDescription();
+     132             : };
+     133             : 
+     134             : }  // namespace crpropa
+     135             : 
+     136             : #endif  // CRPROPA_MASSDISTRIBUTION_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html new file mode 100644 index 000000000..6bb472b29 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Nakanishi.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Nakanishi.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html new file mode 100644 index 000000000..4a26d7662 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Nakanishi.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Nakanishi.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html new file mode 100644 index 000000000..b3dc30cd8 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html @@ -0,0 +1,150 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Nakanishi.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistribution - Nakanishi.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_NAKANISHI_H
+       2             : #define CRPROPA_NAKANISHI_H
+       3             : 
+       4             : #include "crpropa/massDistribution/Density.h"
+       5             : 
+       6             : #include <cmath>
+       7             : #include <string>
+       8             : 
+       9             : namespace crpropa {
+      10             : /**
+      11             :  @class Nakanishi
+      12             :  @brief Cylindrical symetrical model of the density distribution of the Milky Way for atomic (HI) and molecular (H2) hydrogen
+      13             :         Modell for HI arXiv:astro-ph/0304338
+      14             :         Modell for H2 arxiv:astro-ph/0610769
+      15             :         fit of the models given in arXiv:1607.07886
+      16             : */
+      17           1 : class Nakanishi: public Density {
+      18             : private:
+      19             :         bool isforHI = true;
+      20             :         bool isforHII = false;
+      21             :         bool isforH2 = true;
+      22             : 
+      23             : public:
+      24             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      25             :          @returns density in parts/m^3, only activated parts are summed up */
+      26             :         double getDensity(const Vector3d &position) const;
+      27             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      28             :          @returns density of atomic hydrogen in parts/m^3 */
+      29             :         double getHIDensity(const Vector3d &position) const;
+      30             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      31             :          @returns density of molecular hydrogen in parts/m^3 */
+      32             :         double getH2Density(const Vector3d &position) const;
+      33             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      34             :          @returns nucleon density in parts/m^3, only activated parts are summed up and H2 is weighted twice */
+      35             :         double getNucleonDensity(const Vector3d &position) const;
+      36             : 
+      37             :         /** the scale height over the galactic plane of atomic hydrogen is fitted by polynom of degree 3
+      38             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      39             :         @returns scale height at given position */
+      40             :         double getHIScaleheight(const Vector3d &position)const;
+      41             :         /** the plane density is fittet by two exponential components with e^-R and e^-(R^2)
+      42             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      43             :         @returns plane density in parts/m^3 */
+      44             :         double getHIPlanedensity(const Vector3d &position)const;
+      45             : 
+      46             :         /** the scale height over the galactic plane of molecular hydrogen is fitted by exponential function
+      47             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      48             :         @returns scale height at given position */
+      49             :         double getH2Scaleheight(const Vector3d &position)const;
+      50             :         /** the plane density is fitted by two exponential components
+      51             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
+      52             :         @returns plane density in parts/m^3 */
+      53             :         double getH2Planedensity(const Vector3d &position)const;
+      54             : 
+      55             :         /** changes activation status for atomic hydrogen */
+      56             :         void setIsForHI(bool HI);
+      57             :         /** changes activation status for molecular hydrogen */
+      58             :         void setIsForH2(bool H2);
+      59             : 
+      60             :         /** @returns activation status for atomic hydrogen */
+      61             :         bool getIsForHI();
+      62             :         /** @returns activation status for ionised hydrogen */
+      63             :         bool getIsForHII();
+      64             :         /** @returns activation status for molecular hydrogen */
+      65             :         bool getIsForH2();
+      66             :         std::string getDescription();
+      67             : };
+      68             : 
+      69             : }  // namespace crpropa
+      70             : 
+      71             : #endif  // CRPROPA_NAKANISHI_H
+      72             : 
+      73             : 
+      74             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html b/doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html new file mode 100644 index 000000000..3be7402d0 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html @@ -0,0 +1,133 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:52619.2 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Density.h +
0.0%
+
0.0 %0 / 210.0 %0 / 11
Nakanishi.h +
100.0%
+
100.0 %1 / 1-0 / 0
Cordes.h +
100.0%
+
100.0 %1 / 1-0 / 0
Ferriere.h +
100.0%
+
100.0 %1 / 1-0 / 0
Massdistribution.h +
100.0%
+
100.0 %2 / 2-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html b/doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html new file mode 100644 index 000000000..5bc81ca8e --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html @@ -0,0 +1,133 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:52619.2 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Density.h +
0.0%
+
0.0 %0 / 210.0 %0 / 11
Nakanishi.h +
100.0%
+
100.0 %1 / 1-0 / 0
Cordes.h +
100.0%
+
100.0 %1 / 1-0 / 0
Ferriere.h +
100.0%
+
100.0 %1 / 1-0 / 0
Massdistribution.h +
100.0%
+
100.0 %2 / 2-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/massDistribution/index.html b/doc/coverageReport/include/crpropa/massDistribution/index.html new file mode 100644 index 000000000..b39e47962 --- /dev/null +++ b/doc/coverageReport/include/crpropa/massDistribution/index.html @@ -0,0 +1,133 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/massDistribution + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:52619.2 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Cordes.h +
100.0%
+
100.0 %1 / 1-0 / 0
Density.h +
0.0%
+
0.0 %0 / 210.0 %0 / 11
Ferriere.h +
100.0%
+
100.0 %1 / 1-0 / 0
Massdistribution.h +
100.0%
+
100.0 %2 / 2-0 / 0
Nakanishi.h +
100.0%
+
100.0 %1 / 1-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html new file mode 100644 index 000000000..e449df2d8 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Boundary.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Boundary.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:66100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Boundary.h.func.html b/doc/coverageReport/include/crpropa/module/Boundary.h.func.html new file mode 100644 index 000000000..18325e255 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Boundary.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Boundary.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Boundary.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:66100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html b/doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html new file mode 100644 index 000000000..2eb065210 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html @@ -0,0 +1,283 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Boundary.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Boundary.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:66100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_BOUNDARY_H
+       2             : #define CRPROPA_BOUNDARY_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : 
+       6             : namespace crpropa {
+       7             : /**
+       8             :  * \addtogroup Condition
+       9             :  * @{
+      10             :  */
+      11             : 
+      12             : /**
+      13             :  @class PeriodicBox
+      14             :  @brief Rectangular box with periodic boundaries.
+      15             : 
+      16             :  If a particle passes on of the sides it is placed at the opposite side and its initial (source) position changed accordingly.
+      17             :  This implements periodic boundaries, that keep the particle inside the box and instead move the source away periodically.
+      18             :  Particles can overshoot (be outside of the box during the step) since the step size is not limited by this module.
+      19             :  */
+      20           2 : class PeriodicBox: public Module {
+      21             : private:
+      22             :         Vector3d origin;
+      23             :         Vector3d size;
+      24             : 
+      25             : public:
+      26             :         /** Default constructor
+      27             :          */
+      28             :         PeriodicBox();
+      29             :         /** Constructor
+      30             :          @param origin  vector corresponding to the lower box corner
+      31             :          @param size    vector corresponding to the box sizes along each direction
+      32             :          */
+      33             :         PeriodicBox(Vector3d origin, Vector3d size);
+      34             :         void process(Candidate *candidate) const;
+      35             :         void setOrigin(Vector3d origin);
+      36             :         void setSize(Vector3d size);
+      37             :         std::string getDescription() const;
+      38             : };
+      39             : 
+      40             : /**
+      41             :  @class ReflectiveBox
+      42             :  @brief Rectangular box with reflective boundaries.
+      43             : 
+      44             :  If a particle passes on of the sides it is reflected back inside (position and velocity) and its initial position changed as if the particle had come from that side.
+      45             :  This implements periodic boundaries, that keep the particle inside the box and instead move the source away reflectively.
+      46             :  Particles can overshoot (be outside of the box during the step) since the step size is not limited by this module.
+      47             :  */
+      48           1 : class ReflectiveBox: public Module {
+      49             : private:
+      50             :         Vector3d origin;
+      51             :         Vector3d size;
+      52             : 
+      53             : public:
+      54             :         /** Default constructor
+      55             :          */
+      56             :         ReflectiveBox();
+      57             :         /** Constructor
+      58             :          @param origin  vector corresponding to the lower box corner
+      59             :          @param size    vector corresponding to the box sizes along each direction
+      60             :          */
+      61             :         ReflectiveBox(Vector3d origin, Vector3d size);
+      62             :         void process(Candidate *candidate) const;
+      63             :         void setOrigin(Vector3d origin);
+      64             :         void setSize(Vector3d size);
+      65             :         std::string getDescription() const;
+      66             : };
+      67             : 
+      68             : /**
+      69             :  @class CubicBoundary
+      70             :  @brief Flags a particle when exiting the cube.
+      71             : 
+      72             :  The particle is made inactive and flagged as "Rejected".
+      73             :  By default the module prevents overshooting the boundary by more than a margin of 0.1 kpc.
+      74             :  This corresponds to the default minimum step size of the propagation modules (PropagationCK and SimplePropagation).
+      75             :  */
+      76           4 : class CubicBoundary: public AbstractCondition {
+      77             : private:
+      78             :         Vector3d origin;
+      79             :         double size;
+      80             :         double margin;
+      81             :         bool limitStep;
+      82             : 
+      83             : public:
+      84             :         /** Default constructor
+      85             :          */
+      86             :         CubicBoundary();
+      87             :         /** Constructor
+      88             :          @param origin  vector corresponding to the lower box corner
+      89             :          @param size    vector corresponding to the box sizes along each direction
+      90             :          */
+      91             :         CubicBoundary(Vector3d origin, double size);
+      92             :         void process(Candidate *candidate) const;
+      93             :         void setOrigin(Vector3d origin);
+      94             :         void setSize(double size);
+      95             :         void setMargin(double margin);
+      96             :         void setLimitStep(bool limitStep);
+      97             :         std::string getDescription() const;
+      98             : };
+      99             : 
+     100             : /**
+     101             :  @class SphericalBoundary
+     102             :  @brief Flag a particle when leaving the sphere.
+     103             : 
+     104             :  The particle is made inactive and flagged as "Rejected".
+     105             :  By default the module prevents overshooting the boundary by more than a margin of 0.1 kpc.
+     106             :  This corresponds to the default minimum step size of the propagation modules (PropagationCK and SimplePropagation).
+     107             :  */
+     108           3 : class SphericalBoundary: public AbstractCondition {
+     109             : private:
+     110             :         Vector3d center;
+     111             :         double radius;
+     112             :         double margin;
+     113             :         bool limitStep;
+     114             : 
+     115             : public:
+     116             :         /** Default constructor
+     117             :          */
+     118             :         SphericalBoundary();
+     119             :         /** Constructor
+     120             :          @param center          vector containing the coordinates of the center of the sphere
+     121             :          @param radius          radius of the sphere
+     122             :          */
+     123             :         SphericalBoundary(Vector3d center, double radius);
+     124             :         void process(Candidate *candidate) const;
+     125             :         void setCenter(Vector3d center);
+     126             :         void setRadius(double size);
+     127             :         void setMargin(double margin);
+     128             :         void setLimitStep(bool limitStep);
+     129             :         std::string getDescription() const;
+     130             : };
+     131             : 
+     132             : /**
+     133             :  @class EllipsoidalBoundary
+     134             :  @brief Flags a particle when leaving the ellipsoid.
+     135             : 
+     136             :  This module flags particles when outside of the ellipsoid, defined by two focal points and a major axis (length).
+     137             :  The particle is made inactive and flagged as "Rejected".
+     138             :  By default the module prevents overshooting the boundary by more than a margin of 0.1 kpc.
+     139             :  This corresponds to the default minimum step size of the propagation modules (PropagationCK and SimplePropagation).
+     140             :  */
+     141           3 : class EllipsoidalBoundary: public AbstractCondition {
+     142             : private:
+     143             :         Vector3d focalPoint1;
+     144             :         Vector3d focalPoint2;
+     145             :         double majorAxis;
+     146             :         double margin;
+     147             :         bool limitStep;
+     148             : 
+     149             : public:
+     150             :         /** Default constructor
+     151             :          */
+     152             :         EllipsoidalBoundary();
+     153             :         /** Constructor
+     154             :          @param focalPoint1             one of the foci of the ellipsoid
+     155             :          @param focalPoint2             the other foci of the ellipsoid
+     156             :          @param majorAxis               length of the major axis of the ellipsoid
+     157             :          */
+     158             :         EllipsoidalBoundary(Vector3d focalPoint1, Vector3d focalPoint2,
+     159             :                         double majorAxis);
+     160             :         void process(Candidate *candidate) const;
+     161             :         void setFocalPoints(Vector3d focalPoint1, Vector3d focalPoint2);
+     162             :         void setMajorAxis(double size);
+     163             :         void setMargin(double margin);
+     164             :         void setLimitStep(bool limitStep);
+     165             :         std::string getDescription() const;
+     166             : };
+     167             : 
+     168             : 
+     169             : /**
+     170             :  @class CylindricalBoundary
+     171             :  @brief Flags a particle when leaving the cylinder whose axis is along the z-axis.
+     172             :  This module flags particles when outside of the cylinder, defined by a radius and a height.
+     173             :  The particle is made inactive and by default is flagged "OutOfBounds".
+     174             :  Optionally the module can ensure the candidate does not overshoot the boundary by more than a set margin.
+     175             :  */
+     176           3 : class CylindricalBoundary: public AbstractCondition {
+     177             : private:
+     178             :         Vector3d origin;
+     179             :         double height;
+     180             :         double radius;
+     181             :         double margin;
+     182             :         bool limitStep;
+     183             : 
+     184             : public:
+     185             :         /** Default constructor
+     186             :          */
+     187             :         CylindricalBoundary();
+     188             :         /** Constructor
+     189             :          @param origin  vector corresponding to the lower part of the cylinder axis
+     190             :          @param height  height of the cylinder
+     191             :          @param radius  radius of the cylinder
+     192             :          */
+     193             :         CylindricalBoundary(Vector3d origin, double height,
+     194             :                         double radius);
+     195             :         void process(Candidate *candidate) const;
+     196             :         void setOrigin(Vector3d origin);
+     197             :         void setHeight(double height);
+     198             :         void setRadius(double radius);
+     199             :         void setMargin(double margin);
+     200             :         void setLimitStep(bool limitStep);
+     201             :         std::string getDescription() const;
+     202             : };
+     203             : /** @}*/
+     204             : 
+     205             : } // namespace crpropa
+     206             : 
+     207             : #endif // CRPROPA_BOUNDARY_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html new file mode 100644 index 000000000..5eddfe368 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/BreakCondition.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - BreakCondition.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:44100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html b/doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html new file mode 100644 index 000000000..bcf7545eb --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/BreakCondition.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - BreakCondition.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:44100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html b/doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html new file mode 100644 index 000000000..58e693670 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html @@ -0,0 +1,221 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/BreakCondition.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - BreakCondition.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:44100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_BREAKCONDITION_H
+       2             : #define CRPROPA_BREAKCONDITION_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : 
+       6             : namespace crpropa {
+       7             : /**
+       8             :  * \addtogroup Condition 
+       9             :  * @{
+      10             :  */
+      11             : 
+      12             : /**
+      13             :  @class MaximumTrajectoryLength
+      14             :  @brief Deactivates the candidate beyond a maximum trajectory length
+      15             : 
+      16             :  This module deactivates the candidate at a given maximum trajectory length.
+      17             :  In that case the property ("Deactivated", module::description) is set.
+      18             :  It also limits the candidates next step size to ensure the maximum trajectory length is not exceeded.
+      19             :  */
+      20             : class MaximumTrajectoryLength: public AbstractCondition {
+      21             :         double maxLength;
+      22             :         std::vector<Vector3d> observerPositions;
+      23             : public:
+      24             :         MaximumTrajectoryLength(double length = 0);
+      25             :         void setMaximumTrajectoryLength(double length);
+      26             :         double getMaximumTrajectoryLength() const;
+      27             :         void addObserverPosition(const Vector3d &position);
+      28             :         const std::vector<Vector3d>& getObserverPositions() const;
+      29             :         std::string getDescription() const;
+      30             :         void process(Candidate *candidate) const;
+      31             : };
+      32             : 
+      33             : /**
+      34             :  @class MinimumEnergy
+      35             :  @brief Deactivates the candidate below a minimum energy
+      36             : 
+      37             :  This module deactivates the candidate below a given minimum energy.
+      38             :  In that case the property ("Deactivated", module::description) is set.
+      39             :  */
+      40           1 : class MinimumEnergy: public AbstractCondition {
+      41             :         double minEnergy;
+      42             : public:
+      43             :         MinimumEnergy(double minEnergy = 0);
+      44             :         void setMinimumEnergy(double energy);
+      45             :         double getMinimumEnergy() const;
+      46             :         std::string getDescription() const;
+      47             :         void process(Candidate *candidate) const;
+      48             : };
+      49             : 
+      50             : 
+      51             : /**
+      52             :  @class MinimumRigidity
+      53             :  @brief Deactivates the candidate below a minimum rigidity
+      54             : 
+      55             :  This module deactivates the candidate below a given minimum rigidity (E/Z in EeV).
+      56             :  In that case the property ("Deactivated", module::description) is set.
+      57             :  */
+      58             : class MinimumRigidity: public AbstractCondition {
+      59             :         double minRigidity;
+      60             : public:
+      61             :         MinimumRigidity(double minRigidity = 0);
+      62             :         void setMinimumRigidity(double minRigidity);
+      63             :         double getMinimumRigidity() const;
+      64             :         std::string getDescription() const;
+      65             :         void process(Candidate *candidate) const;
+      66             : };
+      67             : 
+      68             : /**
+      69             :  @class MinimumRedshift
+      70             :  @brief Deactivates the candidate below a minimum redshift
+      71             : 
+      72             :  This module deactivates the candidate below a given minimum redshift.
+      73             :  In that case the property ("Deactivated", module::description) is set.
+      74             :  */
+      75           1 : class MinimumRedshift: public AbstractCondition {
+      76             :         double zmin;
+      77             : public:
+      78             :         MinimumRedshift(double zmin = 0);
+      79             :         void setMinimumRedshift(double z);
+      80             :         double getMinimumRedshift();
+      81             :         std::string getDescription() const;
+      82             :         void process(Candidate *candidate) const;
+      83             : };
+      84             : 
+      85             : /**
+      86             :  @class MinimumChargeNumber
+      87             :  @brief Deactivates the candidate below a minimum number
+      88             : 
+      89             :  This module deactivates the candidate below a given minimum charge number.
+      90             :  A minimum charge number of 26 deactivates all (anti-) isotopes which 
+      91             :  are ranked in the periodic table before iron (Fe). 
+      92             :  In that case the property ("Deactivated", module::description) is set.
+      93             :  */
+      94           1 : class MinimumChargeNumber: public AbstractCondition {
+      95             :         int minChargeNumber;
+      96             : public:
+      97             :         MinimumChargeNumber(int minChargeNumber = 0);
+      98             :         void setMinimumChargeNumber(int chargeNumber);
+      99             :         int getMinimumChargeNumber() const;
+     100             :         std::string getDescription() const;
+     101             :         void process(Candidate *candidate) const;
+     102             : };
+     103             : 
+     104             : /**
+     105             :  @class MinimumEnergyPerParticleId
+     106             :  @brief Deactivates the candidate below a minimum energy for specific particle Ids.
+     107             : 
+     108             :  This module deactivates the candidate below a given minimum energy for specific particle types.
+     109             :  In that case the property ("Deactivated", module::description) is set.
+     110             :  All particles whose minimum energy is not specified follow the more general minEnergyOthers condition.
+     111             :  */
+     112             : class MinimumEnergyPerParticleId: public AbstractCondition {
+     113             :         std::vector<double> minEnergies;
+     114             :         std::vector<int> particleIds;
+     115             :         double minEnergyOthers;
+     116             : public:
+     117             :         MinimumEnergyPerParticleId(double minEnergyOthers = 0);
+     118             :         void setMinimumEnergyOthers(double energy);
+     119             :         double getMinimumEnergyOthers() const;
+     120             :         void add(int id, double energy);
+     121             :         std::string getDescription() const;
+     122             :         void process(Candidate *candidate) const;
+     123             : };
+     124             : 
+     125             : 
+     126             : /**
+     127             :  @class DetectionLength
+     128             :  @brief Detects the candidate at a given trajectoryLength
+     129             :  
+     130             :  This break condition can be used for non-regular time observation of the particle density. See also ObserverTimeEvolution.
+     131             :  */
+     132           1 : class DetectionLength: public AbstractCondition {
+     133             :         double detLength;
+     134             : public:
+     135             :         DetectionLength(double length = 0);
+     136             :         void setDetectionLength(double length);
+     137             :         double getDetectionLength() const;
+     138             :         std::string getDescription() const;
+     139             :         void process(Candidate *candidate) const;
+     140             : };
+     141             : /** @}*/
+     142             : 
+     143             : } // namespace crpropa
+     144             : 
+     145             : #endif // CRPROPA_BREAKCONDITION_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html new file mode 100644 index 000000000..6be660edc --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/HDF5Output.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - HDF5Output.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html b/doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html new file mode 100644 index 000000000..b0f0e622a --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/HDF5Output.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - HDF5Output.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html b/doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html new file mode 100644 index 000000000..1db93380e --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html @@ -0,0 +1,217 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/HDF5Output.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - HDF5Output.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifdef CRPROPA_HAVE_HDF5
+       2             : 
+       3             : #ifndef CRPROPA_HDF5OUTPUT_H
+       4             : #define CRPROPA_HDF5OUTPUT_H
+       5             : 
+       6             : 
+       7             : #include "crpropa/module/Output.h"
+       8             : #include <stdint.h>
+       9             : #include <ctime>
+      10             : 
+      11             : #include <H5Ipublic.h>
+      12             : 
+      13             : namespace crpropa {
+      14             : 
+      15             : const size_t propertyBufferSize = 1024;
+      16             : 
+      17             : /**
+      18             :  * \addtogroup Output
+      19             :  * @{
+      20             :  */
+      21             : 
+      22             : /**
+      23             :  @class HDF5Output
+      24             :  @brief Output to HDF5 Format.
+      25             : The base class gives an overview of possible columns
+      26             : 
+      27             : HDF5 structure:
+      28             : ```
+      29             : HDF5 "FILENAME.h5" {
+      30             : GROUP "/" {
+      31             : DATASET "OUTPUTTYPE" {
+      32             :   DATATYPE  H5T_COMPOUND {
+      33             :   ...
+      34             :  }
+      35             :  DATASPACE  SIMPLE { ( 1 ) / ( H5S_UNLIMITED ) }
+      36             :  DATA {
+      37             :   ...
+      38             :  }
+      39             :   ATTRIBUTE "Version" {
+      40             :   DATATYPE  H5T_STRING {
+      41             :       STRSIZE 100;
+      42             :       STRPAD H5T_STR_NULLTERM;
+      43             :       CSET H5T_CSET_ASCII;
+      44             :       CTYPE H5T_C_S1;
+      45             :       }
+      46             :   DATASPACE  SCALAR
+      47             :   DATA { (0): "VERSION" }
+      48             :  }
+      49             : } } }
+      50             : ```
+      51             : 
+      52             :  */
+      53             : class HDF5Output: public Output {
+      54             : 
+      55           0 :         typedef struct OutputRow {
+      56             :                 double D;
+      57             :                 double z;
+      58             :                 uint64_t SN;
+      59             :                 int32_t ID;
+      60             :                 double E;
+      61             :                 double X;
+      62             :                 double Y;
+      63             :                 double Z;
+      64             :                 double Px;
+      65             :                 double Py;
+      66             :                 double Pz;
+      67             :                 uint64_t SN0;
+      68             :                 int32_t ID0;
+      69             :                 double E0;
+      70             :                 double X0;
+      71             :                 double Y0;
+      72             :                 double Z0;
+      73             :                 double P0x;
+      74             :                 double P0y;
+      75             :                 double P0z;
+      76             :                 uint64_t SN1;
+      77             :                 int32_t ID1;
+      78             :                 double E1;
+      79             :                 double X1;
+      80             :                 double Y1;
+      81             :                 double Z1;
+      82             :                 double P1x;
+      83             :                 double P1y;
+      84             :                 double P1z;
+      85             :                 double weight;
+      86             :                 std::string tag;
+      87             :                 unsigned char propertyBuffer[propertyBufferSize];
+      88             :         } OutputRow;
+      89             : 
+      90             :         std::string filename;
+      91             : 
+      92             :         hid_t file, sid;
+      93             :         hid_t dset, dataspace;
+      94             :         mutable std::vector<OutputRow> buffer;
+      95             : 
+      96             :         time_t lastFlush;
+      97             :         unsigned int flushLimit;
+      98             :         unsigned int candidatesSinceFlush;
+      99             : public:
+     100             :         /** Default constructor.
+     101             :                 Does not run from scratch.
+     102             :             At least open() has to be called in addition.
+     103             :                 Units of energy and length are, by default, EeV and Mpc.
+     104             :                 This can be changed with setEnergyScale and setLengthScale.
+     105             :          */
+     106             :         HDF5Output();
+     107             :         /** Constructor with the default OutputType (everything).
+     108             :                 @param filename string containing name of output hdf5 file
+     109             :          */
+     110             :         HDF5Output(const std::string &filename);
+     111             :         /** Constructor
+     112             :                 @param outputtype       type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
+     113             :                 @param filename string containing name of output hdf5 file
+     114             :          */
+     115             :         HDF5Output(const std::string &filename, OutputType outputtype);
+     116             :         ~HDF5Output();
+     117             : 
+     118             :         void process(Candidate *candidate) const;
+     119             :         herr_t insertStringAttribute(const std::string &key, const std::string &value);
+     120             :         herr_t insertDoubleAttribute(const std::string &key, const double &value);
+     121             :         std::string getDescription() const;
+     122             : 
+     123             :         /// Force flush after N events. In long running applications with scarse
+     124             :         /// output this can be set to 1 or 0 to avoid data corruption. In applications
+     125             :         /// with frequent output this should be set to a high number (default)
+     126             :         void setFlushLimit(unsigned int N);
+     127             : 
+     128             :         /** Create and prepare a file as HDF5-file.
+     129             :          */
+     130             :         void open(const std::string &filename);
+     131             :         void close();
+     132             :         void flush() const;
+     133             : 
+     134             : };
+     135             : /** @}*/
+     136             : 
+     137             : } // namespace crpropa
+     138             : 
+     139             : #endif // CRPROPA_HDF5OUTPUT_H
+     140             : 
+     141             : #endif // CRPROPA_HAVE_HDF5
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html new file mode 100644 index 000000000..7c09d8ac5 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/NuclearDecay.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - NuclearDecay.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html new file mode 100644 index 000000000..ffb262df7 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/NuclearDecay.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - NuclearDecay.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html new file mode 100644 index 000000000..9bd7d125c --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html @@ -0,0 +1,163 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/NuclearDecay.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - NuclearDecay.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_NUCLEARDECAY_H
+       2             : #define CRPROPA_NUCLEARDECAY_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : 
+       6             : #include <vector>
+       7             : 
+       8             : namespace crpropa {
+       9             : /**
+      10             :  * \addtogroup EnergyLosses
+      11             :  * @{
+      12             :  */
+      13             : 
+      14             : /**
+      15             :  @class NuclearDecay
+      16             :  @brief Nuclear decay of unstable nuclei.
+      17             : 
+      18             :  This module simulates the nuclear decay of unstable nuclei using data from NuDat2.
+      19             :  All decay modes are considered: alpha, beta+- and gamma decay, as well as proton- and neutron dripping.
+      20             :  The resulting non-hadronic secondary particles (e+, e-, neutrinos, gamma) can optionally be created.
+      21             : 
+      22             :  For details on the preprocessing of the NuDat2 data refer to "CRPropa3-data/calc_decay.py".
+      23             :  */
+      24             : class NuclearDecay: public Module {
+      25             : private:
+      26             :         double limit;
+      27             :         bool haveElectrons;
+      28             :         bool havePhotons;
+      29             :         bool haveNeutrinos;
+      30        1800 :         struct DecayMode {
+      31             :                 int channel; // (#beta- #beta+ #alpha #proton #neutron)
+      32             :                 double rate; // decay rate in [1/m]
+      33             :                 std::vector<double> energy; // photon energies of ensuing gamma decays
+      34             :                 std::vector<double> intensity; // probabilities of ensuing gamma decays
+      35             :         };
+      36             :         std::vector<std::vector<DecayMode> > decayTable; // decayTable[Z * 31 + N] = vector<DecayMode>
+      37             :         std::string interactionTag = "ND";
+      38             : 
+      39             : public:
+      40             :         /** Constructor.
+      41             :          @param electrons               if true, add secondary photons as candidates
+      42             :          @param photons                 if true, add secondary photons as candidates
+      43             :          @param neutrinos               if true, add secondary neutrinos as candidates
+      44             :          @param limit                   step size limit as fraction of mean free path
+      45             :          */
+      46             :         NuclearDecay(bool electrons = false, bool photons = false, bool neutrinos = false, double limit = 0.1);
+      47             : 
+      48             :         /** Limit the propagation step to a fraction of the mean free path
+      49             :          * @param limit fraction of the mean free path
+      50             :          */
+      51             :         void setLimit(double limit);
+      52             : 
+      53             :         // decide if secondary electrons are added to the simulation    
+      54             :         void setHaveElectrons(bool b);
+      55             : 
+      56             :         // decide if secondary photons are added to the simulation      
+      57             :         void setHavePhotons(bool b);
+      58             : 
+      59             :         // decide if secondary neutrinos are added to the simulation    
+      60             :         void setHaveNeutrinos(bool b);
+      61             : 
+      62             :         /** set a custom interaction tag to trace back this interaction
+      63             :          * @param tag string that will be added to the candidate and output
+      64             :          */
+      65             :         void setInteractionTag(std::string tag);
+      66             :         std::string getInteractionTag() const;
+      67             : 
+      68             :         void process(Candidate *candidate) const;
+      69             :         void performInteraction(Candidate *candidate, int channel) const;
+      70             :         void gammaEmission(Candidate *candidate, int channel) const;
+      71             :         void betaDecay(Candidate *candidate, bool isBetaPlus) const;
+      72             :         void nucleonEmission(Candidate *candidate, int dA, int dZ) const;
+      73             : 
+      74             :         /**
+      75             :          Return the mean free path.
+      76             :          This is not used in the simulation.
+      77             :          @param id      PDG particle id
+      78             :          @param gamma   Lorentz factor of particle
+      79             :          @returns The mean free path [in meters]
+      80             :          */
+      81             :         double meanFreePath(int id, double gamma);
+      82             : };
+      83             : /** @}*/
+      84             : 
+      85             : } // namespace crpropa
+      86             : 
+      87             : #endif // CRPROPA_NUCLEARDECAY_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html new file mode 100644 index 000000000..9075a3567 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Observer.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Observer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3837.5 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Observer.h.func.html b/doc/coverageReport/include/crpropa/module/Observer.h.func.html new file mode 100644 index 000000000..9f9969a72 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Observer.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Observer.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Observer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3837.5 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Observer.h.gcov.html b/doc/coverageReport/include/crpropa/module/Observer.h.gcov.html new file mode 100644 index 000000000..216df472e --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Observer.h.gcov.html @@ -0,0 +1,351 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Observer.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Observer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3837.5 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_OBSERVER_H
+       2             : #define CRPROPA_OBSERVER_H
+       3             : 
+       4             : #include <fstream>
+       5             : #include <limits>
+       6             : #include <string>
+       7             : #include <vector>
+       8             : 
+       9             : #include "../Candidate.h"
+      10             : #include "../Module.h"
+      11             : #include "../Referenced.h"
+      12             : #include "../Vector3.h"
+      13             : #include "../Geometry.h"
+      14             : 
+      15             : namespace crpropa {
+      16             : 
+      17             : enum DetectionState {
+      18             :         DETECTED, VETO, NOTHING
+      19             : };
+      20             : 
+      21             : /** \addtogroup Observer
+      22             :  * @{
+      23             :  */
+      24             : 
+      25             : 
+      26             : /**
+      27             :  @class ObserverFeature
+      28             :  @brief Abstract base class for features of observers
+      29             :  */
+      30           1 : class ObserverFeature: public Referenced {
+      31             : protected:
+      32             :         std::string description;
+      33             : public:
+      34             :         virtual DetectionState checkDetection(Candidate *candidate) const;
+      35             :         virtual void onDetection(Candidate *candidate) const;
+      36             :         virtual std::string getDescription() const;
+      37             : };
+      38             : 
+      39             : 
+      40             : /**
+      41             :  @class Observer
+      42             :  @brief General particle observer
+      43             :  */
+      44             : class Observer: public Module {
+      45             :         std::string flagKey;
+      46             :         std::string flagValue;
+      47             : private:
+      48             :         std::vector<ref_ptr<ObserverFeature> > features;
+      49             :         ref_ptr<Module> detectionAction;
+      50             :         bool clone;
+      51             :         bool makeInactive;
+      52             : public:
+      53             :         /** Default observer constructor
+      54             :          */
+      55             :         Observer();
+      56             :         /** Add a feature to the observer
+      57             :          @param feature         observer feature to be added to the Observer object
+      58             :          */
+      59             :         void add(ObserverFeature *feature);
+      60             :         /** Perform some specific actions upon detection of candidate
+      61             :          @param action          module that performs a given action when candidate is detected
+      62             :          @param clone           if true, clone candidate
+      63             :          */
+      64             :         void onDetection(Module *action, bool clone = false);
+      65             :         void process(Candidate *candidate) const;
+      66             :         std::string getDescription() const;
+      67             :         void setFlag(std::string key, std::string value);
+      68             :         /** Determine whether candidate should be deactivated on detection
+      69             :          @param deactivate      if true, deactivate detected particles; if false, continue tracking them
+      70             :          */
+      71             :         void setDeactivateOnDetection(bool deactivate);
+      72             : };
+      73             : 
+      74             : 
+      75             : /**
+      76             :  @class ObserverDetectAll
+      77             :  @brief Detects all particles
+      78             :  */
+      79           2 : class ObserverDetectAll: public ObserverFeature {
+      80             : public:
+      81             :         DetectionState checkDetection(Candidate *candidate) const;
+      82             :         std::string getDescription() const;
+      83             : };
+      84             : 
+      85             : 
+      86             : /**
+      87             :  @class ObserverSurface
+      88             :  @brief Detects particles crossing the boundaries of a defined surface (see, e.g., `Geometry` module)
+      89             :  */
+      90             : class ObserverSurface: public ObserverFeature {
+      91             : private:
+      92             :         ref_ptr<Surface> surface;
+      93             : public:
+      94             :         /** Constructor
+      95             :          @param surface         object with some specific geometric (see Geometry.h)
+      96             :         */
+      97             :         ObserverSurface(Surface* surface);
+      98             :         DetectionState checkDetection(Candidate *candidate) const;
+      99             :         std::string getDescription() const;
+     100             : };
+     101             : 
+     102             : 
+     103             : /**
+     104             :  @class ObserverTracking
+     105             :  @brief Tracks particles inside a sphere
+     106             :  */
+     107             : class ObserverTracking: public ObserverFeature {
+     108             : private:
+     109             :         Vector3d center;
+     110             :         double radius;
+     111             :     double stepSize;
+     112             : public:
+     113             :         /** Constructor
+     114             :          @param center          vector containing the coordinates of the center of the sphere
+     115             :          @param radius          radius of the sphere
+     116             :          @param stepSize        observer will keep track of particles at every step with this size
+     117             :         */
+     118             :         ObserverTracking(Vector3d center, double radius, double stepSize = 0);
+     119             :         DetectionState checkDetection(Candidate *candidate) const;
+     120             :         std::string getDescription() const;
+     121             : };
+     122             : 
+     123             : 
+     124             : /**
+     125             :  @class Observer1D
+     126             :  @brief Detects particles when reaching x = 0
+     127             : 
+     128             :  This module detects particles when reaching x = 0 and also limits the next step size to prevent candidates from overshooting.
+     129             :  */
+     130           3 : class Observer1D: public ObserverFeature {
+     131             : public:
+     132             :         DetectionState checkDetection(Candidate *candidate) const;
+     133             :         std::string getDescription() const;
+     134             : };
+     135             : 
+     136             : 
+     137             : /**
+     138             :  @class ObserverRedshiftWindow
+     139             :  @brief Detects particles in a given redshift window
+     140             : 
+     141             :  When added to an observer, this feature generalizes it to four dimensions.
+     142             :  The fourth dimension is the redshift, a proxy for time. This is particularly
+     143             :  useful in "4D" studies, including either time-dependence (e.g. flaring objects),
+     144             :  or in 3D studies including cosmological evolution.
+     145             :  Note that redshifts should be assigned to sources when using this feature.
+     146             :  This can be done with: SourceRedshift, SourceRedshift1D, SourceUniformRedshift,
+     147             :  and SourceRedshiftEvolution.
+     148             :  */
+     149             : class ObserverRedshiftWindow: public ObserverFeature {
+     150             : private:
+     151             :         double zmin, zmax;
+     152             : public:
+     153             :         /** Constructor
+     154             :          @param zmin    lower bound of redshift interval
+     155             :          @param zmax    upper bound of redshift interval
+     156             :          */
+     157             :         ObserverRedshiftWindow(double zmin = 0, double zmax = 0.1);
+     158             :         DetectionState checkDetection(Candidate *candidate) const;
+     159             :         std::string getDescription() const;
+     160             : };
+     161             : 
+     162             : 
+     163             : /**
+     164             :  @class ObserverInactiveVeto
+     165             :  @brief Veto for inactive candidates
+     166             :  */
+     167           0 : class ObserverInactiveVeto: public ObserverFeature {
+     168             : public:
+     169             :         DetectionState checkDetection(Candidate *candidate) const;
+     170             :         std::string getDescription() const;
+     171             : };
+     172             : 
+     173             : 
+     174             : /**
+     175             :  @class ObserverNucleusVeto
+     176             :  @brief Veto for nuclei (including protons and neutrons)
+     177             :  */
+     178           0 : class ObserverNucleusVeto: public ObserverFeature {
+     179             : public:
+     180             :         DetectionState checkDetection(Candidate *candidate) const;
+     181             :         std::string getDescription() const;
+     182             : };
+     183             : 
+     184             : 
+     185             : /**
+     186             :  @class ObserverNeutrinoVeto
+     187             :  @brief Veto for neutrinos
+     188             :  */
+     189           0 : class ObserverNeutrinoVeto: public ObserverFeature {
+     190             : public:
+     191             :         DetectionState checkDetection(Candidate *candidate) const;
+     192             :         std::string getDescription() const;
+     193             : };
+     194             : 
+     195             : 
+     196             : /**
+     197             :  @class ObserverPhotonVeto
+     198             :  @brief Veto for photons
+     199             :  */
+     200           0 : class ObserverPhotonVeto: public ObserverFeature {
+     201             : public:
+     202             :         DetectionState checkDetection(Candidate *candidate) const;
+     203             :         std::string getDescription() const;
+     204             : };
+     205             : 
+     206             : 
+     207             : /**
+     208             :  @class ObserverElectronVeto
+     209             :  @brief Veto for electrons and positrons
+     210             :  */
+     211           0 : class ObserverElectronVeto: public ObserverFeature {
+     212             : public:
+     213             :         DetectionState checkDetection(Candidate *candidate) const;
+     214             :         std::string getDescription() const;
+     215             : };
+     216             : 
+     217             : 
+     218             : /**
+     219             :  @class ObserverParticleIdVeto
+     220             :  @brief Custom veto for user-defined particle types
+     221             :  Vetoes for more than one type of particle can be added by calling this
+     222             :  feature multiple times.
+     223             :  */
+     224             : class ObserverParticleIdVeto: public ObserverFeature {
+     225             : private:
+     226             :         int vetoParticleId;
+     227             : public:
+     228             :         /** Constructor
+     229             :          @param id              id of the particle following the PDG numbering scheme
+     230             :          */
+     231             :         ObserverParticleIdVeto(int id);
+     232             :         DetectionState checkDetection(Candidate *candidate) const;
+     233             :         std::string getDescription() const;
+     234             : };
+     235             : 
+     236             : 
+     237             : /**
+     238             :  @class ObserverTimeEvolution
+     239             :  @brief Observes the time evolution of the candidates (phase-space elements)
+     240             :  This observer is very useful if the time evolution of the particle density is needed. It detects all candidates in lin-spaced, log-spaced, or user-defined time intervals and limits the nextStep of candidates to prevent overshooting of detection intervals.
+     241             :  */
+     242             : class ObserverTimeEvolution: public ObserverFeature {
+     243             : private:
+     244             :         std::vector<double> detList;
+     245             : public:
+     246             :         /** Default constructor
+     247             :          */
+     248             :         ObserverTimeEvolution();
+     249             :         /** Constructor
+     250             :          @param min             minimum time
+     251             :          @param dist    time interval for detection
+     252             :          @param numb    number of time intervals
+     253             :          */
+     254             :         ObserverTimeEvolution(double min, double dist, double numb);
+     255             :         /** Constructor
+     256             :          @param min             minimum time
+     257             :          @param max         maximum time
+     258             :          @param numb    number of time intervals
+     259             :          @param log     log (input: true) or lin (input: false) scaling between min and max with numb steps
+     260             :          */
+     261             :         ObserverTimeEvolution(double min, double max, double numb, bool log);
+     262             :         // Add a new time step to the detection time list of the observer
+     263             :         void addTime(const double &position);
+     264             :         // Using log or lin spacing of times in the range between min and
+     265             :         // max for observing particles
+     266             :         void addTimeRange(double min, double max, double numb, bool log = false);
+     267             :         const std::vector<double>& getTimes() const;
+     268             :         DetectionState checkDetection(Candidate *candidate) const;
+     269             :         std::string getDescription() const;
+     270             : };
+     271             : /** @} */
+     272             : 
+     273             : }
+     274             : 
+     275             : #endif // CRPROPA_OBSERVER_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html new file mode 100644 index 000000000..743d7dacc --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/OutputShell.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - OutputShell.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:030.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/OutputShell.h.func.html b/doc/coverageReport/include/crpropa/module/OutputShell.h.func.html new file mode 100644 index 000000000..2db467b91 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/OutputShell.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/OutputShell.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - OutputShell.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:030.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html b/doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html new file mode 100644 index 000000000..c24dcbcbf --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/OutputShell.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - OutputShell.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:030.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_OUTPUTSHELL_H
+       2             : #define CRPROPA_OUTPUTSHELL_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : #include "crpropa/AssocVector.h"
+       6             : #include "crpropa/Variant.h"
+       7             : 
+       8             : namespace crpropa {
+       9             : /**
+      10             :  * \addtogroup Output
+      11             :  * @{
+      12             :  */
+      13             : 
+      14             : /**
+      15             :  @class ShellOutput
+      16             :  @brief Show the trajectory in the shell.
+      17             :  */
+      18           0 : class ShellOutput: public Module {
+      19             : public:
+      20             :         void process(Candidate *candidate) const;
+      21             :         std::string getDescription() const;
+      22             : };
+      23             : 
+      24             : /**
+      25             :  @class ShellOutput1D
+      26             :  @brief Show the trajectory in the shell.
+      27             :  */
+      28           0 : class ShellOutput1D: public Module {
+      29             : public:
+      30             :         void process(Candidate *candidate) const;
+      31             :         std::string getDescription() const;
+      32             : };
+      33             : 
+      34             : /**
+      35             :  @class ShellPropertyOutput
+      36             :  @brief Show the candidate properties in the shell.
+      37             :  */
+      38           0 : class ShellPropertyOutput: public Module {
+      39             : public:
+      40             :         typedef Loki::AssocVector<std::string, Variant> PropertyMap;
+      41             :         void process(Candidate *candidate) const;
+      42             :         std::string getDescription() const;
+      43             : };
+      44             : /** @}*/
+      45             : 
+      46             : } // namespace cprpropa
+      47             : 
+      48             : #endif // CRPROPA_OUTPUTSHELL_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html new file mode 100644 index 000000000..182218a99 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PhotoDisintegration.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PhotoDisintegration.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html new file mode 100644 index 000000000..fa9ee8229 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PhotoDisintegration.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PhotoDisintegration.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html new file mode 100644 index 000000000..04ff87a36 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html @@ -0,0 +1,167 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PhotoDisintegration.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PhotoDisintegration.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_PHOTODISINTEGRATION_H
+       2             : #define CRPROPA_PHOTODISINTEGRATION_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : #include "crpropa/PhotonBackground.h"
+       6             : 
+       7             : #include <vector>
+       8             : #include <map>
+       9             : 
+      10             : namespace crpropa {
+      11             : /**
+      12             :  * \addtogroup EnergyLosses
+      13             :  * @{
+      14             :  */
+      15             :  
+      16             : /**
+      17             :  @class PhotoDisintegration
+      18             :  @brief Photodisintegration of nuclei by background photons.
+      19             :  */
+      20             : class PhotoDisintegration: public Module {
+      21             : private:
+      22             :         ref_ptr<PhotonField> photonField;
+      23             :         double limit; // fraction of mean free path for limiting the next step
+      24             :         bool havePhotons;
+      25             :         std::string interactionTag = "PD";
+      26             : 
+      27      203566 :         struct Branch {
+      28             :                 int channel; // number of emitted (n, p, H2, H3, He3, He4)
+      29             :                 std::vector<double> branchingRatio; // branching ratio as function of nucleus Lorentz factor
+      30             :         };
+      31             : 
+      32      858506 :         struct PhotonEmission {
+      33             :                 double energy; // energy of emitted photon [J]
+      34             :                 std::vector<double> emissionProbability; // emission probability as function of nucleus Lorentz factor
+      35             :         };
+      36             : 
+      37             :         std::vector<std::vector<double> > pdRate; // pdRate[Z * 31 + N] = total interaction rate
+      38             :         std::vector<std::vector<Branch> > pdBranch; // pdTable[Z * 31 + N] = branching ratios
+      39             :         mutable std::map<int, std::vector<PhotonEmission> > pdPhoton; // map of emitted photon energies and photon emission probabilities
+      40             : 
+      41             :         static const double lgmin; // minimum log10(Lorentz-factor)
+      42             :         static const double lgmax; // maximum log10(Lorentz-factor)
+      43             :         static const size_t nlg; // number of Lorentz-factor steps
+      44             : 
+      45             : public:
+      46             :         /** Constructor.
+      47             :          @param photonField             target photon field
+      48             :          @param havePhotons             if true, add secondary photons as candidates
+      49             :          @param limit                   step size limit as fraction of mean free path
+      50             :          */
+      51             :         PhotoDisintegration(ref_ptr<PhotonField> photonField, bool havePhotons = false, double limit = 0.1);
+      52             : 
+      53             :         // set the target photon field
+      54             :         void setPhotonField(ref_ptr<PhotonField> photonField);
+      55             : 
+      56             :         // decide if secondary photons are added to the simulation
+      57             :         void setHavePhotons(bool havePhotons);
+      58             : 
+      59             :         /** Limit the propagation step to a fraction of the mean free path
+      60             :          * @param limit fraction of the mean free path
+      61             :          */
+      62             :         void setLimit(double limit);
+      63             : 
+      64             :         /** set a custom interaction tag to trace back this interaction
+      65             :          * @param tag string that will be added to the candidate and output
+      66             :          */
+      67             :         void setInteractionTag(std::string tag);
+      68             :         std::string getInteractionTag() const;
+      69             : 
+      70             :         void initRate(std::string filename);
+      71             :         void initBranching(std::string filename);
+      72             :         void initPhotonEmission(std::string filename);
+      73             : 
+      74             :         void process(Candidate *candidate) const;
+      75             :         void performInteraction(Candidate *candidate, int channel) const;
+      76             : 
+      77             :         /**
+      78             :          Calculates the loss length E dx/dE in [m] physical distance.
+      79             :          This is not used in the simulation.
+      80             :          @param id              PDG particle id
+      81             :          @param gamma   Lorentz factor of particle
+      82             :          @param z               redshift
+      83             :          @returns E dx/dE [in meters]
+      84             :          */
+      85             :         double lossLength(int id, double gamma, double z = 0);
+      86             : };
+      87             : 
+      88             : /** @}*/
+      89             : } // namespace crpropa
+      90             : 
+      91             : #endif // CRPROPA_PHOTODISINTEGRATION_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html new file mode 100644 index 000000000..b51198676 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PropagationBP.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PropagationBP.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html b/doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html new file mode 100644 index 000000000..dbb675695 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PropagationBP.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PropagationBP.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html b/doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html new file mode 100644 index 000000000..c1056913b --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html @@ -0,0 +1,225 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PropagationBP.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PropagationBP.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_PROPAGATIONBP_H
+       2             : #define CRPROPA_PROPAGATIONBP_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : #include "crpropa/Units.h"
+       6             : #include "crpropa/magneticField/MagneticField.h"
+       7             : #include "kiss/logger.h"
+       8             : 
+       9             : namespace crpropa {
+      10             : /**
+      11             :  * \addtogroup Propagation
+      12             :  * @{
+      13             :  */
+      14             : 
+      15             : /**
+      16             :  @class PropagationBP
+      17             :  @brief Propagation through magnetic fields using the Boris method.
+      18             : 
+      19             :  This module solves the equations of motion of a relativistic charged particle when propagating through a magnetic field.\n
+      20             :  It uses the Boris push integration method.\n
+      21             :  It can be used with a fixed step size or an adaptive version which supports the step size control.
+      22             :  The step size control tries to keep the relative error close to, but smaller than the designated tolerance.
+      23             :  Additionally a minimum and maximum size for the steps can be set.
+      24             :  For neutral particles a rectilinear propagation is applied and a next step of the maximum step size proposed.
+      25             :  */
+      26             : class PropagationBP: public Module {
+      27             : 
+      28             : public:
+      29          84 :         class Y {
+      30             :         public:
+      31             :                 Vector3d x, u; /*< phase-point: position and direction */
+      32             : 
+      33             :                 Y() {
+      34             :                 }
+      35             : 
+      36          37 :                 Y(const Vector3d &x, const Vector3d &u) :
+      37             :                                 x(x), u(u) {
+      38             :                 }
+      39             : 
+      40             :                 Y(double f) :
+      41             :                                 x(Vector3d(f, f, f)), u(Vector3d(f, f, f)) {
+      42             :                 }
+      43             : 
+      44             :                 Y operator *(double f) const {
+      45             :                         return Y(x * f, u * f);
+      46             :                 }
+      47             : 
+      48             :                 Y &operator +=(const Y &y) {
+      49             :                         x += y.x;
+      50             :                         u += y.u;
+      51             :                         return *this;
+      52             :                 }
+      53             :         };
+      54             : 
+      55             : private:
+      56             :         ref_ptr<MagneticField> field;
+      57             :         double tolerance; /** target relative error of the numerical integration */
+      58             :         double minStep; /** minimum step size of the propagation */
+      59             :         double maxStep; /** maximum step size of the propagation */
+      60             : 
+      61             : public:
+      62             :         /** Default constructor for the Boris push. It is constructed with a fixed step size.
+      63             :          * @param field
+      64             :          * @param fixedStep 
+      65             :          */
+      66             :         PropagationBP(ref_ptr<MagneticField> field = NULL, double fixedStep = 1. * kpc);
+      67             : 
+      68             :         /** Constructor for the adaptive Boris push.
+      69             :          * @param field
+      70             :          * @param tolerance      tolerance is criterion for step adjustment. Step adjustment takes place only if minStep < maxStep
+      71             :          * @param minStep          minStep/c_light is the minimum integration time step
+      72             :          * @param maxStep          maxStep/c_light is the maximum integration time step. 
+      73             :          */
+      74             :     PropagationBP(ref_ptr<MagneticField> field, double tolerance, double minStep, double maxStep);
+      75             : 
+      76             :         /** Propagates the particle. Is called once per iteration.
+      77             :          * @param candidate      The Candidate is a passive object, that holds the information about the state of the cosmic ray and the simulation itself. */
+      78             :         void process(Candidate *candidate) const;
+      79             : 
+      80             :         /** Calculates the new position and direction of the particle based on the solution of the Lorentz force
+      81             :          * @param pos   current position of the candidate
+      82             :          * @param dir   current direction of the candidate
+      83             :          * @param step  current step size of the candidate
+      84             :          * @param z             current redshift is needed to calculate the magnetic field
+      85             :          * @param q             current charge of the candidate
+      86             :          * @param m             current mass of the candidate
+      87             :          * @return        return the new calculated position and direction of the candidate 
+      88             :          */
+      89             :         Y dY(Vector3d  pos, Vector3d  dir, double step, double z, double q, double m) const;
+      90             : 
+      91             :         /** comparison of the position after one step with the position after two steps with step/2.
+      92             :          * @param x1    position after one step of size step
+      93             :          * @param x2    position after two steps of size step/2
+      94             :          * @param step  current step size
+      95             :          * @return        measurement of the error of the step 
+      96             :          */
+      97             :         double errorEstimation(const Vector3d x1, const Vector3d x2, double step) const;
+      98             : 
+      99             :         /** Get magnetic field vector at current candidate position
+     100             :          * @param pos   current position of the candidate
+     101             :          * @param z      current redshift is needed to calculate the magnetic field
+     102             :          * @return        magnetic field vector at the position pos 
+     103             :          */
+     104             :         Vector3d getFieldAtPosition(Vector3d pos, double z) const;
+     105             : 
+     106             :         /** Adapt step size if required and calculates the new position and direction of the particle with the usage of the function dY
+     107             :          * @param y              current position and direction of candidate
+     108             :          * @param out      position and direction of candidate after the step
+     109             :          * @param error  error for the current step
+     110             :          * @param h              current step size
+     111             :          * @param p              current particle state
+     112             :          * @param z              current red shift
+     113             :          * @param q              current charge of the candidate 
+     114             :          * @param m              current mass of the candidate
+     115             :          */
+     116             :         void tryStep(const Y &y, Y &out, Y &error, double h, ParticleState &p, double z, double q, double m) const;
+     117             : 
+     118             :         /** Set functions for the parameters of the class PropagationBP */
+     119             : 
+     120             :         /** Set a specific magnetic field
+     121             :          * @param field  specific magnetic field 
+     122             :          */
+     123             :         void setField(ref_ptr<MagneticField> field);
+     124             :         /** Set a specific tolerance for the step size adaption
+     125             :          * @param tolerance      tolerance is criterion for step adjustment. Step adjustment takes place only if minStep < maxStep. 
+     126             :          */
+     127             :         void setTolerance(double tolerance);
+     128             :         /** Set the minimum step for the Boris push
+     129             :          * @param minStep          minStep/c_light is the minimum integration time step 
+     130             :          */
+     131             :         void setMinimumStep(double minStep);
+     132             :         /** Set the maximum step for the Boris push
+     133             :          * @param maxStep          maxStep/c_light is the maximum integration time step 
+     134             :          */
+     135             :         void setMaximumStep(double maxStep);
+     136             : 
+     137             :         /** Get functions for the parameters of the class PropagationBP, similar to the set functions */
+     138             : 
+     139             :         ref_ptr<MagneticField> getField() const;
+     140             :         double getTolerance() const;
+     141             :         double getMinimumStep() const;
+     142             :         double getMaximumStep() const;
+     143             :         std::string getDescription() const;
+     144             : };
+     145             : /** @}*/
+     146             : 
+     147             : } // namespace crpropa
+     148             : 
+     149             : #endif // PROPAGATIONBP_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html new file mode 100644 index 000000000..bd00cdf4d --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PropagationCK.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PropagationCK.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html b/doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html new file mode 100644 index 000000000..80cd4d8d7 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PropagationCK.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PropagationCK.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html b/doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html new file mode 100644 index 000000000..1703a86ae --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html @@ -0,0 +1,178 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/PropagationCK.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - PropagationCK.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_PROPAGATIONCK_H
+       2             : #define CRPROPA_PROPAGATIONCK_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : #include "crpropa/Units.h"
+       6             : #include "crpropa/magneticField/MagneticField.h"
+       7             : #include "kiss/logger.h"
+       8             : 
+       9             : namespace crpropa {
+      10             : /**
+      11             :  * \addtogroup Propagation 
+      12             :  * @{
+      13             :  */
+      14             : 
+      15             : /**
+      16             :  @class PropagationCK
+      17             :  @brief Rectilinear propagation through magnetic fields using the Cash-Karp method.
+      18             : 
+      19             :  This module solves the equations of motion of a relativistic charged particle when propagating through a magnetic field.\n
+      20             :  It uses the Runge-Kutta integration method with Cash-Karp coefficients.\n
+      21             :  The step size control tries to keep the relative error close to, but smaller than the designated tolerance.
+      22             :  Additionally a minimum and maximum size for the steps can be set.
+      23             :  For neutral particles a rectilinear propagation is applied and a next step of the maximum step size proposed.
+      24             :  */
+      25             : class PropagationCK: public Module {
+      26             : public:
+      27         286 :         class Y {
+      28             :         public:
+      29             :                 Vector3d x, u; /*< phase-point: position and direction */
+      30             : 
+      31             :                 Y() {
+      32             :                 }
+      33             : 
+      34          34 :                 Y(const Vector3d &x, const Vector3d &u) :
+      35             :                                 x(x), u(u) {
+      36             :                 }
+      37             : 
+      38             :                 Y(double f) :
+      39             :                                 x(Vector3d(f, f, f)), u(Vector3d(f, f, f)) {
+      40             :                 }
+      41             : 
+      42             :                 Y operator *(double f) const {
+      43             :                         return Y(x * f, u * f);
+      44             :                 }
+      45             : 
+      46             :                 Y &operator +=(const Y &y) {
+      47             :                         x += y.x;
+      48             :                         u += y.u;
+      49             :                         return *this;
+      50             :                 }
+      51             :         };
+      52             : 
+      53             : private:
+      54             :         std::vector<double> a, b, bs; /*< Cash-Karp coefficients */
+      55             :         ref_ptr<MagneticField> field;
+      56             :         double tolerance; /*< target relative error of the numerical integration */
+      57             :         double minStep; /*< minimum step size of the propagation */
+      58             :         double maxStep; /*< maximum step size of the propagation */
+      59             : 
+      60             : public:
+      61             :         /** Constructor for the adaptive Kash Carp.
+      62             :          * @param field
+      63             :          * @param tolerance      tolerance is criterion for step adjustment. Step adjustment takes place only if minStep < maxStep
+      64             :          * @param minStep          minStep/c_light is the minimum integration time step
+      65             :          * @param maxStep          maxStep/c_light is the maximum integration time step. 
+      66             :          */
+      67             :     PropagationCK(ref_ptr<MagneticField> field = NULL, double tolerance = 1e-4,
+      68             :                         double minStep = (0.1 * kpc), double maxStep = (1 * Gpc));
+      69             : 
+      70             :         void process(Candidate *candidate) const;
+      71             : 
+      72             :         // derivative of phase point, dY/dt = d/dt(x, u) = (v, du/dt)
+      73             :         // du/dt = q*c^2/E * (u x B)
+      74             :         Y dYdt(const Y &y, ParticleState &p, double z) const;
+      75             : 
+      76             :         void tryStep(const Y &y, Y &out, Y &error, double t,
+      77             :                         ParticleState &p, double z) const;
+      78             : 
+      79             :         void setField(ref_ptr<MagneticField> field);
+      80             :         void setTolerance(double tolerance);
+      81             :         void setMinimumStep(double minStep);
+      82             :         void setMaximumStep(double maxStep);
+      83             : 
+      84             :          /** get functions for the parameters of the class PropagationCK, similar to the set functions */
+      85             :         ref_ptr<MagneticField> getField() const;
+      86             :         
+      87             :         /** get magnetic field vector at current candidate position
+      88             :          * @param pos   current position of the candidate
+      89             :          * @param z      current redshift is needed to calculate the magnetic field
+      90             :          * @return        magnetic field vector at the position pos */
+      91             :         Vector3d getFieldAtPosition(Vector3d pos, double z) const;
+      92             : 
+      93             :         double getTolerance() const;
+      94             :         double getMinimumStep() const;
+      95             :         double getMaximumStep() const;
+      96             :         std::string getDescription() const;
+      97             : };
+      98             : /** @}*/
+      99             : 
+     100             : } // namespace crpropa
+     101             : 
+     102             : #endif // CRPROPA_PROPAGATIONCK_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html new file mode 100644 index 000000000..3041fd90b --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Redshift.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Redshift.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1250.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Redshift.h.func.html b/doc/coverageReport/include/crpropa/module/Redshift.h.func.html new file mode 100644 index 000000000..b7380b3ff --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Redshift.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Redshift.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Redshift.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1250.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html b/doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html new file mode 100644 index 000000000..9cbeaec26 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html @@ -0,0 +1,111 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Redshift.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Redshift.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1250.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_REDSHIFT_H
+       2             : #define CRPROPA_REDSHIFT_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : 
+       6             : namespace crpropa {
+       7             : /**
+       8             :  * \addtogroup EnergyLosses
+       9             :  * @{
+      10             :  */
+      11             : 
+      12             : /**
+      13             :  @class Redshift
+      14             :  @brief Updates redshift and applies adiabatic energy loss according to the traveled distance.
+      15             :  */
+      16           5 : class Redshift: public Module {
+      17             : public:
+      18             :         void process(Candidate *candidate) const;
+      19             :         std::string getDescription() const;
+      20             : };
+      21             : 
+      22             : /**
+      23             :  @class FutureRedshift
+      24             :  @brief Updates redshift and applies adiabatic energy loss according to the traveled distance. Extends to negative redshift values to allow for symmetric time windows around z=0.
+      25             :  */
+      26           0 : class FutureRedshift: public Module {
+      27             : public:
+      28             :         void process(Candidate *candidate) const;
+      29             :         std::string getDescription() const;
+      30             : };
+      31             : 
+      32             : /** @}*/
+      33             : } // namespace crpropa
+      34             : 
+      35             : #endif // CRPROPA_REDSHIFT_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html new file mode 100644 index 000000000..487472bfc --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/SimplePropagation.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - SimplePropagation.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html new file mode 100644 index 000000000..340e30412 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/SimplePropagation.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - SimplePropagation.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html new file mode 100644 index 000000000..5cd3cb7b6 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html @@ -0,0 +1,115 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/SimplePropagation.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - SimplePropagation.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef SIMPLEPROPAGATION_H
+       2             : #define SIMPLEPROPAGATION_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : #include "crpropa/Units.h"
+       6             : 
+       7             : namespace crpropa {
+       8             : /**
+       9             :  * \addtogroup Propagation 
+      10             :  * @{
+      11             :  */
+      12             : 
+      13             : /**
+      14             :  @class SimplePropagation
+      15             :  @brief Simple rectilinear propagation in absence of magnetic fields.
+      16             : 
+      17             :  This module implements rectilinear propagation.
+      18             :  The step size is guaranteed to be larger than minStep and smaller than maxStep.
+      19             :  It always proposes a next step size of maxStep.
+      20             :  */
+      21           1 : class SimplePropagation: public Module {
+      22             : private:
+      23             :         double minStep, maxStep;
+      24             : 
+      25             : public:
+      26             :         SimplePropagation(double minStep = (0.1 * kpc), double maxStep = (1 * Gpc));
+      27             :         void process(Candidate *candidate) const;
+      28             :         void setMinimumStep(double minStep);
+      29             :         void setMaximumStep(double maxStep);
+      30             :         double getMinimumStep() const;
+      31             :         double getMaximumStep() const;
+      32             :         std::string getDescription() const;
+      33             : };
+      34             : /** @}*/
+      35             : 
+      36             : } // namespace crpropa
+      37             : 
+      38             : #endif // SIMPLEPROPAGATION_H
+      39             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html new file mode 100644 index 000000000..a060bcffd --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/TextOutput.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - TextOutput.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/TextOutput.h.func.html b/doc/coverageReport/include/crpropa/module/TextOutput.h.func.html new file mode 100644 index 000000000..52ca0025f --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/TextOutput.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/TextOutput.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - TextOutput.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html b/doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html new file mode 100644 index 000000000..e9fc25846 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html @@ -0,0 +1,155 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/TextOutput.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - TextOutput.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_TEXTOUTPUT_H
+       2             : #define CRPROPA_TEXTOUTPUT_H
+       3             : 
+       4             : #include "crpropa/module/Output.h"
+       5             : #include "crpropa/module/ParticleCollector.h"
+       6             : 
+       7             : #include <fstream>
+       8             : 
+       9             : namespace crpropa {
+      10             : /**
+      11             :  * \addtogroup Output
+      12             :  * @{
+      13             :  */
+      14             : 
+      15             : /**
+      16             :  @class TextOutput
+      17             :  @brief Configurable plain text output for particle information.
+      18             :  This type of output can also be used to generate a .tar.gz file if
+      19             :  the library zlib is available. For details see:
+      20             :         http://zlib.net/
+      21             :  */
+      22             : class TextOutput: public Output {
+      23             : protected:
+      24             :         std::ostream *out;
+      25             :         std::ofstream outfile;
+      26             :         std::string filename;
+      27             :         bool storeRandomSeeds;
+      28             :         
+      29             :         void printHeader() const;
+      30             : 
+      31             : public:
+      32             :         /** Default constructor
+      33             :          */
+      34             :         TextOutput();
+      35             :         /** Constructor
+      36             :          @param outputType      type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
+      37             :          */
+      38             :         TextOutput(OutputType outputType);
+      39             :         /** Constructor
+      40             :          @param out                     output stream
+      41             :          */
+      42             :         TextOutput(std::ostream &out);
+      43             :         /** Constructor
+      44             :          @param out                     output stream
+      45             :          @param outputType      type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
+      46             :          */
+      47             :         TextOutput(std::ostream &out, OutputType outputType);
+      48             :         /** Constructor with the default OutputType (everything).
+      49             :          @param filename        string containing name of output text file
+      50             :          */
+      51             :         TextOutput(const std::string &filename);
+      52             :         /** Constructor
+      53             :          @param filename        string containing name of output text file
+      54             :          @param outputType      type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
+      55             :          */
+      56             :         TextOutput(const std::string &filename, OutputType outputType);
+      57             :         /** Destructor
+      58             :          */
+      59             :         ~TextOutput();
+      60             :         /** Whether to store the random seeds used in the simulation.
+      61             :          This enables reproducibility of each realisation of the simulation.
+      62             :          */
+      63           0 :         void enableRandomSeeds() {storeRandomSeeds = true;};
+      64             :         void close();
+      65             :         void gzip();
+      66             :         void process(Candidate *candidate) const;
+      67             :         /** Loads a file to a particle collector.
+      68             :          This is useful for analysis involving, e.g., magnetic lenses.
+      69             :          @param filename        string containing the name of the file to be loaded
+      70             :          @param collector       object of type ParticleCollector that will store the information
+      71             :          */
+      72             :         static void load(const std::string &filename, ParticleCollector *collector);
+      73             :         std::string getDescription() const;
+      74             : };
+      75             : /** @}*/
+      76             : 
+      77             : } // namespace crpropa
+      78             : 
+      79             : #endif // CRPROPA_TEXTOUTPUT_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html new file mode 100644 index 000000000..4ce957e1c --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Tools.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Tools.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Tools.h.func.html b/doc/coverageReport/include/crpropa/module/Tools.h.func.html new file mode 100644 index 000000000..d4f77327f --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Tools.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Tools.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Tools.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/Tools.h.gcov.html b/doc/coverageReport/include/crpropa/module/Tools.h.gcov.html new file mode 100644 index 000000000..ff73e05a6 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/Tools.h.gcov.html @@ -0,0 +1,150 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module/Tools.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/module - Tools.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef CRPROPA_MODULETOOLS_H
+       2             : #define CRPROPA_MODULETOOLS_H
+       3             : 
+       4             : #include "crpropa/Module.h"
+       5             : #include "crpropa/EmissionMap.h"
+       6             : 
+       7             : #include <vector>
+       8             : #include <set>
+       9             : 
+      10             : namespace crpropa {
+      11             : /**
+      12             :  * \addtogroup Tools
+      13             :  * @{
+      14             :  */
+      15             : 
+      16             : /**
+      17             :  @class PerformanceModule
+      18             :  @brief Module to monitor the simulation performance
+      19             : 
+      20             :  Add modules under investigation to this module instead of the ModuleList.
+      21             :  */
+      22           0 : class PerformanceModule: public Module {
+      23             : private:
+      24           0 :         struct _module_info {
+      25             :                 double time;
+      26             :                 ref_ptr<Module> module;
+      27             :         };
+      28             : 
+      29             :         mutable std::vector<_module_info> modules;
+      30             :         mutable size_t calls;
+      31             : 
+      32             : public:
+      33             :         ~PerformanceModule();
+      34             :         void add(Module* module);
+      35             :         void process(Candidate* candidate) const;
+      36             :         std::string getDescription() const;
+      37             : };
+      38             : 
+      39             : /**
+      40             :   @class ParticleFilter
+      41             :   @brief Reject Particles not listed in filter.
+      42             : */
+      43             : class ParticleFilter: public AbstractCondition {
+      44             :         std::set<int> ids;
+      45             : 
+      46             : public:
+      47             :         ParticleFilter();
+      48             :         ParticleFilter(const std::set<int> &ids);
+      49             :         void addId(int id);
+      50             :         void removeId(int remove);
+      51             :         std::set<int> &getIds();
+      52             : 
+      53             :         void process(Candidate* candidate) const;
+      54             :         std::string getDescription() const;
+      55             : };
+      56             : 
+      57             : 
+      58             : /**
+      59             :   @class EmissionMapFiller
+      60             :   @brief Fill EmissionMap with source particle state
+      61             : */
+      62             : class EmissionMapFiller: public Module {
+      63             :         ref_ptr<EmissionMap> emissionMap;
+      64             : public:
+      65             :         EmissionMapFiller(EmissionMap *emissionMap);
+      66             :         void setEmissionMap(EmissionMap *emissionMap);
+      67             :         void process(Candidate* candidate) const;
+      68             :         std::string getDescription() const;
+      69             : };
+      70             : 
+      71             : /** @}*/
+      72             : } // namespace crpropa
+      73             : 
+      74             : #endif // CRPROPA_MODULETOOLS_H
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/index-sort-f.html b/doc/coverageReport/include/crpropa/module/index-sort-f.html new file mode 100644 index 000000000..14233aa5e --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/index-sort-f.html @@ -0,0 +1,213 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:223562.9 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
OutputShell.h +
0.0%
+
0.0 %0 / 3-0 / 0
TextOutput.h +
0.0%
+
0.0 %0 / 1-0 / 0
SimplePropagation.h +
100.0%
+
100.0 %1 / 1-0 / 0
BreakCondition.h +
100.0%
+
100.0 %4 / 4-0 / 0
Boundary.h +
100.0%
+
100.0 %6 / 6-0 / 0
PhotoDisintegration.h +
100.0%
+
100.0 %2 / 2-0 / 0
Tools.h +
0.0%
+
0.0 %0 / 2-0 / 0
PropagationCK.h +
100.0%
+
100.0 %2 / 2-0 / 0
PropagationBP.h +
100.0%
+
100.0 %2 / 2-0 / 0
HDF5Output.h +
0.0%
+
0.0 %0 / 1-0 / 0
Observer.h +
37.5%37.5%
+
37.5 %3 / 8-0 / 0
NuclearDecay.h +
100.0%
+
100.0 %1 / 1-0 / 0
Redshift.h +
50.0%50.0%
+
50.0 %1 / 2-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/index-sort-l.html b/doc/coverageReport/include/crpropa/module/index-sort-l.html new file mode 100644 index 000000000..5ff9027ea --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/index-sort-l.html @@ -0,0 +1,213 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:223562.9 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
TextOutput.h +
0.0%
+
0.0 %0 / 1-0 / 0
HDF5Output.h +
0.0%
+
0.0 %0 / 1-0 / 0
Tools.h +
0.0%
+
0.0 %0 / 2-0 / 0
OutputShell.h +
0.0%
+
0.0 %0 / 3-0 / 0
Observer.h +
37.5%37.5%
+
37.5 %3 / 8-0 / 0
Redshift.h +
50.0%50.0%
+
50.0 %1 / 2-0 / 0
SimplePropagation.h +
100.0%
+
100.0 %1 / 1-0 / 0
NuclearDecay.h +
100.0%
+
100.0 %1 / 1-0 / 0
PhotoDisintegration.h +
100.0%
+
100.0 %2 / 2-0 / 0
PropagationCK.h +
100.0%
+
100.0 %2 / 2-0 / 0
PropagationBP.h +
100.0%
+
100.0 %2 / 2-0 / 0
BreakCondition.h +
100.0%
+
100.0 %4 / 4-0 / 0
Boundary.h +
100.0%
+
100.0 %6 / 6-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/include/crpropa/module/index.html b/doc/coverageReport/include/crpropa/module/index.html new file mode 100644 index 000000000..5483b4fa7 --- /dev/null +++ b/doc/coverageReport/include/crpropa/module/index.html @@ -0,0 +1,213 @@ + + + + + + + LCOV - coverage.info.cleaned - include/crpropa/module + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - include/crpropa/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:223562.9 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Boundary.h +
100.0%
+
100.0 %6 / 6-0 / 0
BreakCondition.h +
100.0%
+
100.0 %4 / 4-0 / 0
HDF5Output.h +
0.0%
+
0.0 %0 / 1-0 / 0
NuclearDecay.h +
100.0%
+
100.0 %1 / 1-0 / 0
Observer.h +
37.5%37.5%
+
37.5 %3 / 8-0 / 0
OutputShell.h +
0.0%
+
0.0 %0 / 3-0 / 0
PhotoDisintegration.h +
100.0%
+
100.0 %2 / 2-0 / 0
PropagationBP.h +
100.0%
+
100.0 %2 / 2-0 / 0
PropagationCK.h +
100.0%
+
100.0 %2 / 2-0 / 0
Redshift.h +
50.0%50.0%
+
50.0 %1 / 2-0 / 0
SimplePropagation.h +
100.0%
+
100.0 %1 / 1-0 / 0
TextOutput.h +
0.0%
+
0.0 %0 / 1-0 / 0
Tools.h +
0.0%
+
0.0 %0 / 2-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/index-sort-f.html b/doc/coverageReport/index-sort-f.html new file mode 100644 index 000000000..2f53c4197 --- /dev/null +++ b/doc/coverageReport/index-sort-f.html @@ -0,0 +1,293 @@ + + + + + + + LCOV - coverage.info.cleaned + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top levelHitTotalCoverage
Test:coverage.info.cleanedLines:87351426261.2 %
Date:2024-04-08 14:58:22Functions:1124206954.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Directory Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
include/crpropa/massDistribution +
19.2%19.2%
+
19.2 %5 / 260.0 %0 / 11
libs/healpix_base/include/healpix_base +
19.1%19.1%
+
19.1 %33 / 1738.1 %5 / 62
libs/healpix_base +
14.1%14.1%
+
14.1 %112 / 7929.4 %10 / 106
libs/kiss/include/kiss +
57.9%57.9%
+
57.9 %11 / 1920.9 %14 / 67
src/magneticField +
18.2%18.2%
+
18.2 %166 / 91021.0 %29 / 138
libs/HepPID/src +
11.4%11.4%
+
11.4 %50 / 44022.9 %11 / 48
libs/kiss/src +
28.1%28.1%
+
28.1 %34 / 12139.1 %9 / 23
include/crpropa +
73.6%73.6%
+
73.6 %408 / 55446.4 %77 / 166
include/crpropa/magneticField/turbulentField +
72.9%72.9%
+
72.9 %43 / 5947.1 %8 / 17
src/magneticLens +
45.7%45.7%
+
45.7 %147 / 32251.2 %21 / 41
src/advectionField +
42.5%42.5%
+
42.5 %131 / 30852.4 %44 / 84
include/crpropa/magneticLens +
42.9%42.9%
+
42.9 %30 / 7054.5 %6 / 11
src/magneticField/turbulentField +
71.1%71.1%
+
71.1 %187 / 26357.9 %11 / 19
src +
50.3%50.3%
+
50.3 %1361 / 270758.5 %251 / 429
src/module +
63.4%63.4%
+
63.4 %2250 / 354759.0 %286 / 485
include/crpropa/magneticField +
89.3%89.3%
+
89.3 %50 / 5663.6 %7 / 11
src/massDistribution +
83.9%83.9%
+
83.9 %349 / 41690.8 %69 / 76
test +
97.9%97.9%
+
97.9 %3320 / 339196.7 %264 / 273
include/crpropa/module +
62.9%62.9%
+
62.9 %22 / 35-0 / 0
include/crpropa/advectionField +
100.0%
+
100.0 %5 / 5-0 / 0
/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy +
43.8%43.8%
+
43.8 %21 / 48100.0 %2 / 2
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/index-sort-l.html b/doc/coverageReport/index-sort-l.html new file mode 100644 index 000000000..ae168257c --- /dev/null +++ b/doc/coverageReport/index-sort-l.html @@ -0,0 +1,293 @@ + + + + + + + LCOV - coverage.info.cleaned + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top levelHitTotalCoverage
Test:coverage.info.cleanedLines:87351426261.2 %
Date:2024-04-08 14:58:22Functions:1124206954.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Directory Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
libs/HepPID/src +
11.4%11.4%
+
11.4 %50 / 44022.9 %11 / 48
libs/healpix_base +
14.1%14.1%
+
14.1 %112 / 7929.4 %10 / 106
src/magneticField +
18.2%18.2%
+
18.2 %166 / 91021.0 %29 / 138
libs/healpix_base/include/healpix_base +
19.1%19.1%
+
19.1 %33 / 1738.1 %5 / 62
include/crpropa/massDistribution +
19.2%19.2%
+
19.2 %5 / 260.0 %0 / 11
libs/kiss/src +
28.1%28.1%
+
28.1 %34 / 12139.1 %9 / 23
src/advectionField +
42.5%42.5%
+
42.5 %131 / 30852.4 %44 / 84
include/crpropa/magneticLens +
42.9%42.9%
+
42.9 %30 / 7054.5 %6 / 11
/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy +
43.8%43.8%
+
43.8 %21 / 48100.0 %2 / 2
src/magneticLens +
45.7%45.7%
+
45.7 %147 / 32251.2 %21 / 41
src +
50.3%50.3%
+
50.3 %1361 / 270758.5 %251 / 429
libs/kiss/include/kiss +
57.9%57.9%
+
57.9 %11 / 1920.9 %14 / 67
include/crpropa/module +
62.9%62.9%
+
62.9 %22 / 35-0 / 0
src/module +
63.4%63.4%
+
63.4 %2250 / 354759.0 %286 / 485
src/magneticField/turbulentField +
71.1%71.1%
+
71.1 %187 / 26357.9 %11 / 19
include/crpropa/magneticField/turbulentField +
72.9%72.9%
+
72.9 %43 / 5947.1 %8 / 17
include/crpropa +
73.6%73.6%
+
73.6 %408 / 55446.4 %77 / 166
src/massDistribution +
83.9%83.9%
+
83.9 %349 / 41690.8 %69 / 76
include/crpropa/magneticField +
89.3%89.3%
+
89.3 %50 / 5663.6 %7 / 11
test +
97.9%97.9%
+
97.9 %3320 / 339196.7 %264 / 273
include/crpropa/advectionField +
100.0%
+
100.0 %5 / 5-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/index.html b/doc/coverageReport/index.html new file mode 100644 index 000000000..11a901d77 --- /dev/null +++ b/doc/coverageReport/index.html @@ -0,0 +1,293 @@ + + + + + + + LCOV - coverage.info.cleaned + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top levelHitTotalCoverage
Test:coverage.info.cleanedLines:87351426261.2 %
Date:2024-04-08 14:58:22Functions:1124206954.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Directory Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy +
43.8%43.8%
+
43.8 %21 / 48100.0 %2 / 2
include/crpropa +
73.6%73.6%
+
73.6 %408 / 55446.4 %77 / 166
include/crpropa/advectionField +
100.0%
+
100.0 %5 / 5-0 / 0
include/crpropa/magneticField +
89.3%89.3%
+
89.3 %50 / 5663.6 %7 / 11
include/crpropa/magneticField/turbulentField +
72.9%72.9%
+
72.9 %43 / 5947.1 %8 / 17
include/crpropa/magneticLens +
42.9%42.9%
+
42.9 %30 / 7054.5 %6 / 11
include/crpropa/massDistribution +
19.2%19.2%
+
19.2 %5 / 260.0 %0 / 11
include/crpropa/module +
62.9%62.9%
+
62.9 %22 / 35-0 / 0
libs/HepPID/src +
11.4%11.4%
+
11.4 %50 / 44022.9 %11 / 48
libs/healpix_base +
14.1%14.1%
+
14.1 %112 / 7929.4 %10 / 106
libs/healpix_base/include/healpix_base +
19.1%19.1%
+
19.1 %33 / 1738.1 %5 / 62
libs/kiss/include/kiss +
57.9%57.9%
+
57.9 %11 / 1920.9 %14 / 67
libs/kiss/src +
28.1%28.1%
+
28.1 %34 / 12139.1 %9 / 23
src +
50.3%50.3%
+
50.3 %1361 / 270758.5 %251 / 429
src/advectionField +
42.5%42.5%
+
42.5 %131 / 30852.4 %44 / 84
src/magneticField +
18.2%18.2%
+
18.2 %166 / 91021.0 %29 / 138
src/magneticField/turbulentField +
71.1%71.1%
+
71.1 %187 / 26357.9 %11 / 19
src/magneticLens +
45.7%45.7%
+
45.7 %147 / 32251.2 %21 / 41
src/massDistribution +
83.9%83.9%
+
83.9 %349 / 41690.8 %69 / 76
src/module +
63.4%63.4%
+
63.4 %2250 / 354759.0 %286 / 485
test +
97.9%97.9%
+
97.9 %3320 / 339196.7 %264 / 273
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html new file mode 100644 index 000000000..295e10399 --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html @@ -0,0 +1,200 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleIDMethods.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - ParticleIDMethods.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5024920.1 %
Date:2024-04-08 14:58:22Functions:113234.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID10hasStrangeERKi0
_ZN6HepPID12_GLOBAL__N_15findQERKiS2_0
_ZN6HepPID12isPentaquarkERKi0
_ZN6HepPID18hasFundamentalAntiERKi0
_ZN6HepPID5hasUpERKi0
_ZN6HepPID5jSpinERKi0
_ZN6HepPID5lSpinERKi0
_ZN6HepPID5sSpinERKi0
_ZN6HepPID6hasTopERKi0
_ZN6HepPID6isSUSYERKi0
_ZN6HepPID6lambdaERKi0
_ZN6HepPID7hasDownERKi0
_ZN6HepPID7isMesonERKi0
_ZN6HepPID7isValidERKi0
_ZN6HepPID8hasCharmERKi0
_ZN6HepPID8isBaryonERKi0
_ZN6HepPID8isHadronERKi0
_ZN6HepPID8isLeptonERKi0
_ZN6HepPID9hasBottomERKi0
_ZN6HepPID9isDiQuarkERKi0
_ZN6HepPID9isRhadronERKi0
_ZN6HepPID1AERKi202818
_ZN6HepPID1ZERKi364529
_ZN6HepPID6isDyonERKi3325562
_ZN6HepPID13fundamentalIDERKi20168250
_ZN6HepPID6chargeERKi20168251
_ZN6HepPID11threeChargeERKi20168252
_ZN6HepPID9isNucleusERKi20937352
_ZN6HepPID7isQBallERKi23493806
_ZN6HepPID9extraBitsERKi50313164
_ZN6HepPID5digitENS_8locationERKi146041016
_ZN6HepPID6abspidERKi260299484
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html new file mode 100644 index 000000000..078e3d9b7 --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html @@ -0,0 +1,200 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleIDMethods.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - ParticleIDMethods.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5024920.1 %
Date:2024-04-08 14:58:22Functions:113234.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID10hasStrangeERKi0
_ZN6HepPID11threeChargeERKi20168252
_ZN6HepPID12_GLOBAL__N_15findQERKiS2_0
_ZN6HepPID12isPentaquarkERKi0
_ZN6HepPID13fundamentalIDERKi20168250
_ZN6HepPID18hasFundamentalAntiERKi0
_ZN6HepPID1AERKi202818
_ZN6HepPID1ZERKi364529
_ZN6HepPID5digitENS_8locationERKi146041016
_ZN6HepPID5hasUpERKi0
_ZN6HepPID5jSpinERKi0
_ZN6HepPID5lSpinERKi0
_ZN6HepPID5sSpinERKi0
_ZN6HepPID6abspidERKi260299484
_ZN6HepPID6chargeERKi20168251
_ZN6HepPID6hasTopERKi0
_ZN6HepPID6isDyonERKi3325562
_ZN6HepPID6isSUSYERKi0
_ZN6HepPID6lambdaERKi0
_ZN6HepPID7hasDownERKi0
_ZN6HepPID7isMesonERKi0
_ZN6HepPID7isQBallERKi23493806
_ZN6HepPID7isValidERKi0
_ZN6HepPID8hasCharmERKi0
_ZN6HepPID8isBaryonERKi0
_ZN6HepPID8isHadronERKi0
_ZN6HepPID8isLeptonERKi0
_ZN6HepPID9extraBitsERKi50313164
_ZN6HepPID9hasBottomERKi0
_ZN6HepPID9isDiQuarkERKi0
_ZN6HepPID9isNucleusERKi20937352
_ZN6HepPID9isRhadronERKi0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html new file mode 100644 index 000000000..de197c29e --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html @@ -0,0 +1,641 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleIDMethods.cc + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - ParticleIDMethods.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5024920.1 %
Date:2024-04-08 14:58:22Functions:113234.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : // ----------------------------------------------------------------------
+       2             : //
+       3             : // ParticleIDMethods.cc
+       4             : //
+       5             : // ----------------------------------------------------------------------
+       6             : 
+       7             : #include <cmath>  // for pow()
+       8             : 
+       9             : #include "HepPID/ParticleIDMethods.hh"
+      10             : #include "HepPID/ParticleName.hh"
+      11             : 
+      12             : namespace HepPID {
+      13             : 
+      14             : namespace {
+      15             : 
+      16             : // internal function used by hasXXX methods
+      17           0 : bool findQ( const int & pid, const int & q )
+      18             : {
+      19           0 :     if( isDyon(pid) ) { return false; }
+      20           0 :     if( isRhadron(pid) ) {
+      21             :         int iz = 7;
+      22           0 :         for( int i=6; i > 1; --i ) {
+      23           0 :            if( digit(location(i),pid) == 0 ) {
+      24             :                iz = i;
+      25           0 :            } else if ( i == iz-1 ) {
+      26             :                // ignore squark or gluino
+      27             :            } else {
+      28           0 :                if( digit(location(i),pid) == q ) { return true; }
+      29             :            }
+      30             :         }
+      31             :         return false;
+      32             :     }
+      33           0 :     if( digit(nq3,pid) == q || digit(nq2,pid) == q || digit(nq1,pid) == q ) { return true; }
+      34           0 :     if( isPentaquark(pid) ) { 
+      35           0 :         if( digit(nl,pid) == q || digit(nr,pid) == q ) { return true; }
+      36             :     }
+      37             :     return false;
+      38             : }
+      39             : 
+      40             : }
+      41             : 
+      42             : // absolute value
+      43   260299484 : int abspid( const int & pid )
+      44             : {
+      45   260299484 :   return (pid < 0) ? -pid : pid;
+      46             : }
+      47             : 
+      48             : // returns everything beyond the 7th digit (e.g. outside the numbering scheme)
+      49    50313164 : int extraBits( const int & pid )
+      50             : {
+      51    50313164 :     return abspid(pid)/10000000;
+      52             : }
+      53             : 
+      54             : //  split the PID into constituent integers
+      55   146041016 : unsigned short digit( location loc, const int & pid )
+      56             : {
+      57             :     //  PID digits (base 10) are: n nr nl nq1 nq2 nq3 nj
+      58             :     //  the location enum provides a convenient index into the PID
+      59             :                 //
+      60             :                 //  Modified for CRPropa: use precalculated values isntead of pow for
+      61             :                 //  performance
+      62             :                 static unsigned int p10[] = { 1, 10, 100, 1000,  10000, 100000, 1000000,
+      63             :                         10000000, 100000000, 1000000000};
+      64   146041016 :     return (abspid(pid)/ p10[loc-1])%10;
+      65             : //    int numerator = (int) std::pow(10.0,(loc-1));
+      66             : //    return (abspid(pid)/numerator)%10;
+      67             : }
+      68             : 
+      69             : //  return the first two digits if this is a "fundamental" particle
+      70             : //  ID = 100 is a special case (internal generator ID's are 81-100)
+      71    20168250 : int fundamentalID( const int & pid )
+      72             : {
+      73    20168250 :     if( extraBits(pid) > 0 ) return 0;
+      74    20168243 :     if( digit(nq2,pid) == 0 && digit(nq1,pid) == 0) {
+      75    20168243 :         return abspid(pid)%10000;
+      76           0 :     } else if( abspid(pid) <= 100 ) {
+      77           0 :         return abspid(pid);
+      78             :     } else {
+      79             :         return 0;
+      80             :     }
+      81             : }
+      82             : 
+      83             : // Ion numbers are +/- 10LZZZAAAI. 
+      84      364529 : int Z( const int & pid )
+      85             : {
+      86             :     // a proton can also be a Hydrogen nucleus
+      87      364529 :     if( abspid(pid) == 2212 ) { return 1; }
+      88      364529 :     if( isNucleus(pid) ) return (abspid(pid)/10000)%1000;
+      89             :     return 0;
+      90             : }
+      91             : 
+      92             : // Ion numbers are +/- 10LZZZAAAI. 
+      93      202818 : int A( const int & pid )
+      94             : {
+      95             :     // a proton can also be a Hydrogen nucleus
+      96      202818 :     if( abspid(pid) == 2212 ) { return 1; }
+      97      202818 :     if( isNucleus(pid) ) return (abspid(pid)/10)%1000;
+      98             :     return 0;
+      99             : }
+     100             : 
+     101             : // if this is a nucleus (ion), get nLambda
+     102             : // Ion numbers are +/- 10LZZZAAAI. 
+     103           0 : int lambda( const int & pid )
+     104             : {
+     105             :     // a proton can also be a Hydrogen nucleus
+     106           0 :     if( abspid(pid) == 2212 ) { return 0; }
+     107           0 :     if( isNucleus(pid) ) return digit(n8,pid);
+     108             :     return 0;
+     109             : }
+     110             : 
+     111             : 
+     112             : // ---  boolean methods:
+     113             : //
+     114             : 
+     115             : //  check to see if this is a valid PID
+     116           0 : bool isValid( const int & pid )
+     117             : {
+     118           0 :     if( extraBits(pid) > 0 ) {
+     119           0 :         if( isNucleus(pid) )   { return true; }
+     120           0 :         if( isQBall(pid) )   { return true; }
+     121           0 :         return false; 
+     122             :     }
+     123           0 :     if( isSUSY(pid) ) { return true; }
+     124           0 :     if( isRhadron(pid) ) { return true; }
+     125           0 :     if( isDyon(pid) ) { return true; }
+     126             :     // Meson signature
+     127           0 :     if( isMeson(pid) )   { return true; }
+     128             :     // Baryon signature
+     129           0 :     if( isBaryon(pid) )  { return true; }
+     130             :     // DiQuark signature
+     131           0 :     if( isDiQuark(pid) ) { return true; }
+     132             :     // fundamental particle
+     133           0 :     if( fundamentalID(pid) > 0 ) { 
+     134           0 :       if(pid > 0 ) { 
+     135             :         return true; 
+     136             :       } else {
+     137           0 :         if( hasFundamentalAnti(pid) ) { return true; }
+     138           0 :         return false;
+     139             :       }
+     140             :     }
+     141             :     // pentaquark
+     142           0 :     if( isPentaquark(pid) ) { return true; }
+     143             :     // don't recognize this number
+     144             :     return false;
+     145             : }
+     146             : 
+     147             : // if this is a fundamental particle, does it have a valid antiparticle?
+     148           0 : bool hasFundamentalAnti( const int & pid )
+     149             : {
+     150             :     // these are defined by the generator and therefore are always valid
+     151           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) >= 80 ) { return true; }
+     152             :     // check id's from 1 to 79
+     153           0 :     if( fundamentalID(pid) > 0 && fundamentalID(pid) < 80 ) { 
+     154           0 :        if( validParticleName(-pid) ) { return true; }
+     155             :     }
+     156             :     return false;
+     157             : }
+     158             : 
+     159             : //  check to see if this is a valid meson
+     160           0 : bool isMeson( const int & pid )
+     161             : {
+     162           0 :     if( extraBits(pid) > 0 ) { return false; }
+     163           0 :     if( abspid(pid) <= 100 ) { return false; }
+     164           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) > 0 ) { return false; }
+     165           0 :     if( isRhadron(pid) ) { return false; }
+     166           0 :     int aid = abspid(pid);
+     167           0 :     if( aid == 130 || aid == 310 || aid == 210 ) { return true; }
+     168             :     // EvtGen uses some odd numbers
+     169           0 :     if( aid == 150 || aid == 350 || aid == 510 || aid == 530 ) { return true; }
+     170             :     // pomeron, etc.
+     171           0 :     if( pid == 110 || pid == 990 || pid == 9990 ) { return true; }
+     172           0 :     if(    digit(nj,pid) > 0 && digit(nq3,pid) > 0 
+     173           0 :         && digit(nq2,pid) > 0 && digit(nq1,pid) == 0 ) {
+     174             :         // check for illegal antiparticles
+     175           0 :         if( digit(nq3,pid) == digit(nq2,pid) && pid < 0 ) {
+     176           0 :             return false;
+     177             :         } else {
+     178             :             return true;
+     179             :         }
+     180             :     }
+     181             :     return false;
+     182             : }
+     183             : 
+     184             : //  check to see if this is a valid baryon
+     185           0 : bool isBaryon( const int & pid )
+     186             : {
+     187           0 :     if( extraBits(pid) > 0 ) { return false; }
+     188           0 :     if( abspid(pid) <= 100 ) { return false; }
+     189           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) > 0 ) { return false; }
+     190           0 :     if( isRhadron(pid) ) { return false; }
+     191           0 :     if( isPentaquark(pid) ) { return false; }
+     192           0 :     if( abspid(pid) == 2110 || abspid(pid) == 2210 ) { return true; }
+     193           0 :     if(    digit(nj,pid) > 0  && digit(nq3,pid) > 0 
+     194           0 :         && digit(nq2,pid) > 0 && digit(nq1,pid) > 0 ) { return true; }
+     195             :     return false;
+     196             : }
+     197             : 
+     198             : //  check to see if this is a valid diquark
+     199           0 : bool isDiQuark( const int & pid )
+     200             : {
+     201           0 :     if( extraBits(pid) > 0 ) { return false; }
+     202           0 :     if( abspid(pid) <= 100 ) { return false; }
+     203           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) > 0 ) { return false; }
+     204           0 :     if(    digit(nj,pid) > 0  && digit(nq3,pid) == 0 
+     205           0 :         && digit(nq2,pid) > 0 && digit(nq1,pid) > 0 ) {  // diquark signature
+     206             :        // EvtGen uses the diquarks for quark pairs, so, for instance, 
+     207             :        //   5501 is a valid "diquark" for EvtGen
+     208             :        //if( digit(nj) == 1 && digit(nq2) == digit(nq1) ) {     // illegal
+     209             :        //   return false; 
+     210             :        //} else {
+     211           0 :           return true;
+     212             :        //}
+     213             :     }
+     214             :     return false;
+     215             : }
+     216             : 
+     217             : // is this a valid hadron ID?
+     218           0 : bool isHadron( const int & pid )
+     219             : {
+     220           0 :     if( extraBits(pid) > 0 ) { return false; }
+     221           0 :     if( isMeson(pid) )   { return true; }
+     222           0 :     if( isBaryon(pid) )  { return true; }
+     223           0 :     if( isPentaquark(pid) ) { return true; }
+     224           0 :     if( isRhadron(pid) ) { return true; }
+     225             :     return false;
+     226             : }
+     227             : // is this a valid lepton ID?
+     228           0 : bool isLepton( const int & pid )
+     229             : {
+     230           0 :     if( extraBits(pid) > 0 ) { return false; }
+     231           0 :     if( fundamentalID(pid) >= 11 && fundamentalID(pid) <= 18 ) { return true; }
+     232             :     return false;
+     233             : }
+     234             : 
+     235             : //
+     236             : // This implements the 2006 Monte Carlo nuclear code scheme.
+     237             : // Ion numbers are +/- 10LZZZAAAI. 
+     238             : // AAA is A - total baryon number
+     239             : // ZZZ is Z - total charge
+     240             : // L is the total number of strange quarks.
+     241             : // I is the isomer number, with I=0 corresponding to the ground state.
+     242    20937352 : bool isNucleus( const int & pid )
+     243             : {
+     244             :      // a proton can also be a Hydrogen nucleus
+     245    20937352 :      if( abspid(pid) == 2212 ) { return true; }
+     246             :      // new standard: +/- 10LZZZAAAI
+     247    20937336 :      if( ( digit(n10,pid) == 1 ) && ( digit(n9,pid) == 0 ) ) {
+     248             :         // charge should always be less than or equal to baryon number
+     249             :         // the following line is A >= Z
+     250      769143 :         if( (abspid(pid)/10)%1000 >= (abspid(pid)/10000)%1000 ) { return true; }
+     251             :      }
+     252             :      return false;
+     253             : }
+     254             : 
+     255             : //  check to see if this is a valid pentaquark
+     256           0 : bool isPentaquark( const int & pid )
+     257             : {
+     258             :     // a pentaquark is of the form 9abcdej,
+     259             :     // where j is the spin and a, b, c, d, and e are quarks
+     260           0 :     if( extraBits(pid) > 0 ) { return false; }
+     261           0 :     if( digit(n,pid) != 9 )  { return false; }
+     262           0 :     if( digit(nr,pid) == 9 || digit(nr,pid) == 0 )  { return false; }
+     263           0 :     if( digit(nj,pid) == 9 || digit(nl,pid) == 0 )  { return false; }
+     264           0 :     if( digit(nq1,pid) == 0 )  { return false; }
+     265           0 :     if( digit(nq2,pid) == 0 )  { return false; }
+     266           0 :     if( digit(nq3,pid) == 0 )  { return false; }
+     267           0 :     if( digit(nj,pid) == 0 )  { return false; }
+     268             :     // check ordering
+     269           0 :     if( digit(nq2,pid) > digit(nq1,pid) )  { return false; }
+     270           0 :     if( digit(nq1,pid) > digit(nl,pid) )  { return false; }
+     271           0 :     if( digit(nl,pid) > digit(nr,pid) )  { return false; }
+     272             :     return true;
+     273             : }
+     274             : 
+     275             : // is this a SUSY?
+     276           0 : bool isSUSY( const int & pid )
+     277             : {
+     278             :     // fundamental SUSY particles have n = 1 or 2
+     279           0 :     if( extraBits(pid) > 0 ) { return false; }
+     280           0 :     if( digit(n,pid) != 1 && digit(n,pid) != 2 )  { return false; }
+     281           0 :     if( digit(nr,pid) != 0 )  { return false; }
+     282             :     // check fundamental part
+     283           0 :     if( fundamentalID(pid) == 0 )  { return false; }
+     284             :     return true;
+     285             : }
+     286             : 
+     287             : // is this an R-hadron?
+     288           0 : bool isRhadron( const int & pid )
+     289             : {
+     290             :     // an R-hadron is of the form 10abcdj, 100abcj, or 1000abj
+     291             :     // where j is the spin, b, c, and d are quarks or gluons,
+     292             :     // and a (the digit following the zero's) is a SUSY particle
+     293           0 :     if( extraBits(pid) > 0 ) { return false; }
+     294           0 :     if( digit(n,pid) != 1 )  { return false; }
+     295           0 :     if( digit(nr,pid) != 0 )  { return false; }
+     296             :     // make sure this isn't a SUSY particle
+     297           0 :     if( isSUSY(pid) ) { return false; }
+     298             :     // All R-hadrons have at least 3 core digits
+     299           0 :     if( digit(nq2,pid) == 0 )  { return false; }
+     300           0 :     if( digit(nq3,pid) == 0 )  { return false; }
+     301           0 :     if( digit(nj,pid) == 0 )  { return false; }
+     302             :     return true;
+     303             : }
+     304             : 
+     305             : // is this a Dyon (magnetic monopole)?
+     306     3325562 : bool isDyon( const int & pid )
+     307             : {
+     308             :     ///Magnetic monopoles and Dyons are assumed to have one unit of 
+     309             :     ///Dirac monopole charge and a variable integer number xyz units 
+     310             :     ///of electric charge.  
+     311             :     ///
+     312             :     ///Codes 411xyz0 are then used when the magnetic and electrical 
+     313             :     ///charge sign agree and 412xyz0 when they disagree, 
+     314             :     ///with the overall sign of the particle set by the magnetic charge.  
+     315             :     ///For now no spin information is provided.
+     316             :     ///
+     317     3325562 :     if( extraBits(pid) > 0 ) { return false; }
+     318     3325562 :     if( digit(n,pid) != 4 )  { return false; }
+     319           0 :     if( digit(nr,pid) != 1 )  { return false; }
+     320           0 :     if( (digit(nl,pid) != 1) && (digit(nl,pid) != 2) )  { return false; }
+     321             :     // All Dyons have at least 1 core digit
+     322           0 :     if( digit(nq3,pid) == 0 )  { return false; }
+     323             :     // Dyons have spin zero for now
+     324           0 :     if( digit(nj,pid) != 0 )  { return false; }
+     325             :     return true;
+     326             : }
+     327             : 
+     328             : // Check for QBalls
+     329             : // Ad-hoc numbering for such particles is 100xxxx0, 
+     330             : // where xxxx is the charge in tenths. 
+     331    23493806 : bool isQBall( const int & pid )
+     332             : {
+     333    23493806 :     if( extraBits(pid) != 1 ) { return false; }
+     334           0 :     if( digit(n,pid) != 0 )  { return false; }
+     335           0 :     if( digit(nr,pid) != 0 )  { return false; }
+     336             :     // check the core number
+     337           0 :     if( (abspid(pid)/10)%10000 == 0 )  { return false; }
+     338             :     // these particles have spin zero for now
+     339           0 :     if( digit(nj,pid) != 0 )  { return false; }
+     340             :     return true;
+     341             : }
+     342             : 
+     343             : // does this particle contain an up quark?
+     344           0 : bool hasUp( const int & pid)
+     345             : {
+     346           0 :     if( extraBits(pid) > 0 ) { return false; }
+     347           0 :     if( fundamentalID(pid) > 0 ) { return false; }
+     348           0 :     return findQ(pid,2);
+     349             : }
+     350             : // does this particle contain a down quark?
+     351           0 : bool hasDown( const int & pid)
+     352             : {
+     353           0 :     if( extraBits(pid) > 0 ) { return false; }
+     354           0 :     if( fundamentalID(pid) > 0 ) { return false; }
+     355           0 :     return findQ(pid,1);
+     356             : }
+     357             : // does this particle contain a strange quark?
+     358           0 : bool hasStrange( const int & pid )
+     359             : {
+     360           0 :     if( extraBits(pid) > 0 ) { return false; }
+     361           0 :     if( fundamentalID(pid) > 0 ) { return false; }
+     362           0 :     return findQ(pid,3);
+     363             : }
+     364             : // does this particle contain a charm quark?
+     365           0 : bool hasCharm( const int & pid )
+     366             : {
+     367           0 :     if( extraBits(pid) > 0 ) { return false; }
+     368           0 :     if( fundamentalID(pid) > 0 ) { return false; }
+     369           0 :     return findQ(pid,4);
+     370             : }
+     371             : // does this particle contain a bottom quark?
+     372           0 : bool hasBottom( const int & pid )
+     373             : {
+     374           0 :     if( extraBits(pid) > 0 ) { return false; }
+     375           0 :     if( fundamentalID(pid) > 0 ) { return false; }
+     376           0 :     return findQ(pid,5);
+     377             : }
+     378             : // does this particle contain a top quark?
+     379           0 : bool hasTop( const int & pid )
+     380             : {
+     381           0 :     if( extraBits(pid) > 0 ) { return false; }
+     382           0 :     if( fundamentalID(pid) > 0 ) { return false; }
+     383           0 :     return findQ(pid,6);
+     384             : }
+     385             : 
+     386             : // ---  other information
+     387             : //
+     388             : // jSpin returns 2J+1, where J is the total spin
+     389           0 : int  jSpin( const int & pid )
+     390             : {
+     391           0 :     if( fundamentalID(pid) > 0 ) { 
+     392             :         // some of these are known
+     393           0 :         int fund = fundamentalID(pid);
+     394           0 :         if( fund > 0 && fund < 7 ) return 2;
+     395           0 :         if( fund == 9 ) return 3; 
+     396           0 :         if( fund > 10 && fund < 17 ) return 2;
+     397           0 :         if( fund > 20 && fund < 25 ) return 3;
+     398           0 :         return 0; 
+     399           0 :     } else if( extraBits(pid) > 0 ) { 
+     400             :         return 0; 
+     401             :     }
+     402           0 :     return abspid(pid)%10;
+     403             : }
+     404             : // sSpin returns 2S+1, where S is the spin
+     405           0 : int  sSpin( const int & pid )
+     406             : {
+     407           0 :     if( !isMeson(pid) ) { return 0; }
+     408           0 :     int inl = digit(nl,pid);
+     409             :     //int tent = digit(n,pid);
+     410           0 :     int js = digit(nj,pid);
+     411           0 :     if( digit(n,pid) == 9 ) { return 0; }       // tentative ID
+     412             :     //if( tent == 9 ) { return 0; }     // tentative assignment
+     413           0 :     if( inl == 0 && js >= 3 ) { 
+     414             :         return 1;
+     415           0 :     } else if( inl == 0  && js == 1 ) {
+     416             :         return 0;
+     417           0 :     } else if( inl == 1  && js >= 3 ) {
+     418             :         return 0;
+     419           0 :     } else if( inl == 2  && js >= 3 ) {
+     420             :         return 1;
+     421           0 :     } else if( inl == 1  && js == 1 ) {
+     422             :         return 1;
+     423           0 :     } else if( inl == 3  && js >= 3 ) {
+     424           0 :         return 1;
+     425             :     }
+     426             :     // default to zero
+     427             :     return 0;
+     428             : }
+     429             : // lSpin returns 2L+1, where L is the orbital angular momentum
+     430           0 : int  lSpin( const int & pid )
+     431             : {
+     432           0 :     if( !isMeson(pid) ) { return 0; }
+     433           0 :     int inl = digit(nl,pid);
+     434             :     //int tent = digit(n,pid);
+     435           0 :     int js = digit(nj,pid);
+     436           0 :     if( digit(n,pid) == 9 ) { return 0; }       // tentative ID
+     437           0 :     if( inl == 0 && js == 3 ) { 
+     438             :         return 0;
+     439           0 :     } else if( inl == 0 && js == 5 ) {
+     440             :         return 1;
+     441           0 :     } else if( inl == 0 && js == 7 ) {
+     442             :         return 2;
+     443           0 :     } else if( inl == 0 && js == 9 ) {
+     444             :         return 3;
+     445           0 :     } else if( inl == 0  && js == 1 ) {
+     446             :         return 0;
+     447           0 :     } else if( inl == 1  && js == 3 ) {
+     448             :         return 1;
+     449           0 :     } else if( inl == 1  && js == 5 ) {
+     450             :         return 2;
+     451           0 :     } else if( inl == 1  && js == 7 ) {
+     452             :         return 3;
+     453           0 :     } else if( inl == 1  && js == 9 ) {
+     454             :         return 4;
+     455           0 :     } else if( inl == 2  && js == 3 ) {
+     456             :         return 1;
+     457           0 :     } else if( inl == 2  && js == 5 ) {
+     458             :         return 2;
+     459           0 :     } else if( inl == 2  && js == 7 ) {
+     460             :         return 3;
+     461           0 :     } else if( inl == 2  && js == 9 ) {
+     462             :         return 4;
+     463           0 :     } else if( inl == 1  && js == 1 ) {
+     464             :         return 1;
+     465           0 :     } else if( inl == 3  && js == 3 ) {
+     466             :         return 2;
+     467           0 :     } else if( inl == 3  && js == 5 ) {
+     468             :         return 3;
+     469           0 :     } else if( inl == 3  && js == 7 ) {
+     470             :         return 4;
+     471           0 :     } else if( inl == 3  && js == 9 ) {
+     472           0 :         return 5;
+     473             :     }
+     474             :     // default to zero
+     475             :     return 0;
+     476             : }
+     477             : 
+     478             : // 3 times the charge
+     479    20168252 : int threeCharge( const int & pid )
+     480             : {
+     481             :     int charge=0;
+     482             :     int ida, sid;
+     483             :     unsigned short q1, q2, q3, ql;
+     484             :     static int ch100[] = { -1, 2,-1, 2,-1, 2,-1, 2, 0, 0,
+     485             :                        -3, 0,-3, 0,-3, 0,-3, 0, 0, 0,
+     486             :                         0, 0, 0, 3, 0, 0, 0, 0, 0, 0,
+     487             :                         0, 0, 0, 3, 0, 0, 3, 0, 0, 0,
+     488             :                         0, -1, 0, 0, 0, 0, 0, 0, 0, 0,
+     489             :                         0, 6, 3, 6, 0, 0, 0, 0, 0, 0,
+     490             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+     491             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+     492             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+     493             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
+     494    20168252 :     q1 = digit(nq1,pid);
+     495    20168249 :     q2 = digit(nq2,pid);
+     496    20168248 :     q3 = digit(nq3,pid);
+     497    20168250 :     ql = digit(nl,pid);
+     498    20168251 :     ida = abspid(pid);
+     499    20168250 :     sid = fundamentalID(pid);
+     500    20168244 :     if( ida == 0 ) {      // illegal
+     501             :         return 0;
+     502     3325563 :     } else if( isQBall(pid) ) {         // QBall
+     503           0 :        charge = 3*((abspid(pid)/10)%10000);
+     504     3325563 :     } else if( extraBits(pid) > 0 ) {                // ion
+     505             :         return 0;
+     506     3325562 :     } else if( isDyon(pid) ) {          // Dyon
+     507           0 :         charge = 3*( (abspid(pid)/10)%1000 );
+     508             :         // this is half right
+     509             :         // the charge sign will be changed below if pid < 0
+     510           0 :         if( ql == 2 ) {
+     511           0 :             charge = -charge; 
+     512             :         }
+     513     3325562 :     } else if( sid > 0 && sid <= 100 ) {  // use table
+     514     3325562 :         charge = ch100[sid-1];
+     515     3325562 :         if(ida==1000017 || ida==1000018) { charge = 0; }
+     516     3325562 :         if(ida==1000034 || ida==1000052) { charge = 0; }
+     517     3325562 :         if(ida==1000053 || ida==1000054) { charge = 0; }
+     518     3325562 :         if(ida==5100061 || ida==5100062) { charge = 6; }
+     519           0 :     } else if( digit(nj,pid) == 0 ) {           // KL, Ks, or undefined
+     520             :         return 0;
+     521           0 :     } else if( isMeson(pid) ) {                 // mesons
+     522           0 :             if( q2 == 3 || q2 == 5 ) {
+     523           0 :                 charge = ch100[q3-1] - ch100[q2-1];
+     524             :             } else {
+     525           0 :                 charge = ch100[q2-1] - ch100[q3-1];
+     526             :             }
+     527           0 :     } else if( isRhadron(pid) ) {               // Rhadron
+     528           0 :         if (( q1 == 0 ) || ( q1 == 9 )) {
+     529           0 :             if( q2 == 3 || q2 == 5 ) {
+     530           0 :                 charge = ch100[q3-1] - ch100[q2-1];
+     531             :             } else {
+     532           0 :                 charge = ch100[q2-1] - ch100[q3-1];
+     533             :             }
+     534           0 :         } else if( ql == 0 ) {
+     535           0 :             charge = ch100[q3-1] + ch100[q2-1] + ch100[q1-1];
+     536           0 :         } else if ( digit(nr,pid) == 0 ) {
+     537           0 :             charge = ch100[q3-1] + ch100[q2-1] + ch100[q1-1] + ch100[ql-1];
+     538             :         }
+     539           0 :     } else if( isDiQuark(pid) ) {                       // diquarks
+     540           0 :         charge = ch100[q2-1] + ch100[q1-1];
+     541           0 :     } else if( isBaryon(pid) ) {                        // baryons
+     542           0 :         charge = ch100[q3-1] + ch100[q2-1] + ch100[q1-1];
+     543             :     } else {            // unknown
+     544             :         return 0;
+     545             :     }
+     546     3325562 :     if( charge == 0 ) {
+     547     3310494 :         return 0;
+     548       15068 :     } else if( pid < 0 ) {
+     549        7103 :         charge = -charge; 
+     550             :     }
+     551             :     return charge;
+     552             : }
+     553             : 
+     554             : // the actual charge
+     555    20168251 : double charge( const int & pid )
+     556             : {
+     557    20168251 :    int tc = threeCharge(pid);
+     558    20168244 :    if( isQBall(pid) ) {
+     559           0 :        return double(tc)/30.;
+     560             :    } else {
+     561    20168248 :        return double(tc)/3.;
+     562             :    }
+     563             : }
+     564             : 
+     565             : } // HepPID
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html new file mode 100644 index 000000000..399175d29 --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleName.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - ParticleName.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01830.0 %
Date:2024-04-08 14:58:22Functions:0130.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID12_GLOBAL__N_116ParticleNameInitEv0
_ZN6HepPID12_GLOBAL__N_121writeParticleNameLineEiRSo0
_ZN6HepPID12_GLOBAL__N_123checkForSpecialParticleERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID12_GLOBAL__N_18dyonNameERKi0
_ZN6HepPID12_GLOBAL__N_19qballNameERKi0
_ZN6HepPID12particleNameB5cxx11ERKi0
_ZN6HepPID12particleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID15ParticleNameMapC2ESt3mapIiNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESt4lessIiESaISt4pairIKiS7_EEES1_IS7_iS8_IS7_ESaISA_IKS7_iEEE0
_ZN6HepPID15ParticleNameMapD2Ev0
_ZN6HepPID17listParticleNamesERSo0
_ZN6HepPID17validParticleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID17validParticleNameERKi0
_ZN6HepPID18getParticleNameMapEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html new file mode 100644 index 000000000..392fe15ed --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleName.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - ParticleName.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01830.0 %
Date:2024-04-08 14:58:22Functions:0130.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID12_GLOBAL__N_116ParticleNameInitEv0
_ZN6HepPID12_GLOBAL__N_121writeParticleNameLineEiRSo0
_ZN6HepPID12_GLOBAL__N_123checkForSpecialParticleERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID12_GLOBAL__N_18dyonNameERKi0
_ZN6HepPID12_GLOBAL__N_19qballNameERKi0
_ZN6HepPID12particleNameB5cxx11ERKi0
_ZN6HepPID12particleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID15ParticleNameMapC2ESt3mapIiNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESt4lessIiESaISt4pairIKiS7_EEES1_IS7_iS8_IS7_ESaISA_IKS7_iEEE0
_ZN6HepPID15ParticleNameMapD2Ev0
_ZN6HepPID17listParticleNamesERSo0
_ZN6HepPID17validParticleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID17validParticleNameERKi0
_ZN6HepPID18getParticleNameMapEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html new file mode 100644 index 000000000..c67d5715b --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html @@ -0,0 +1,2075 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleName.cc + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - ParticleName.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01830.0 %
Date:2024-04-08 14:58:22Functions:0130.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : // ----------------------------------------------------------------------
+       2             : //
+       3             : // ParticleName.cc
+       4             : // Author: Lynn Garren and Walter Brown
+       5             : //
+       6             : //  Create a map that gives a standard name for each pre-defined 
+       7             : //  particle ID number.   Also create a map for the reverse lookup of 
+       8             : //  the ID number from a string.  These maps are initialized if and only if 
+       9             : //  the public functions are called. Because the maps are static, 
+      10             : //  the initialization happens only once.
+      11             : //
+      12             : //  The user NEVER calls ParticleNameInit()
+      13             : //  We use a data table (struct Snames) so that compile time is not impacted.
+      14             : //
+      15             : //  public functions:
+      16             : //     PartcleIdMap const &  getPartcleIdMap()
+      17             : //     std::string              ParticleName( const int pid )
+      18             : //     void                     listParticleNames( std::ostream & os  )
+      19             : //
+      20             : // ----------------------------------------------------------------------
+      21             : 
+      22             : #include <string>
+      23             : #include <map>
+      24             : #include <iostream>
+      25             : #include <sstream>
+      26             : #include <iomanip>        // width
+      27             : #include <utility>        // make_pair
+      28             : 
+      29             : #include "HepPID/ParticleName.hh"
+      30             : #include "HepPID/ParticleIDMethods.hh"
+      31             : #include "HepPID/Version.hh"
+      32             : 
+      33             : namespace HepPID {
+      34             : 
+      35             : typedef  std::map< int, std::string >  PartcleIdMap;
+      36             : typedef  std::map< std::string, int >  ParticleLookupMap;
+      37             : 
+      38             : ///
+      39             : /// \class ParticleNameMap
+      40             : /// \author Lynn Garren
+      41             : ///
+      42             : /// Used internally to store the static maps
+      43             : ///
+      44             : class ParticleNameMap{
+      45             : 
+      46             : public:
+      47             : 
+      48             :    typedef PartcleIdMap::const_iterator      idIterator;
+      49             :    typedef ParticleLookupMap::const_iterator nameIterator;
+      50             :    
+      51           0 :    ParticleNameMap(PartcleIdMap m1,ParticleLookupMap m2)
+      52           0 :    : itsNameMap(m1), itsLookupMap(m2) {}
+      53           0 :    ~ParticleNameMap() {}
+      54             :    
+      55             :    PartcleIdMap       nameMap()    const { return itsNameMap; }
+      56             :    ParticleLookupMap lookupMap()  const { return itsLookupMap; }
+      57             :    idIterator   begin()               const { return itsNameMap.begin(); }
+      58             :    idIterator   end()                 const { return itsNameMap.end(); }
+      59             :    idIterator   find( const int & id) const { return itsNameMap.find(id); }
+      60             :    nameIterator beginLookupMap()      const { return itsLookupMap.begin(); }
+      61             :    nameIterator endLookupMap()        const { return itsLookupMap.end(); }
+      62             :    nameIterator findString( const std::string & s) const { return itsLookupMap.find(s); }
+      63             : 
+      64             : private:
+      65             :    
+      66             :    PartcleIdMap       itsNameMap;
+      67             :    ParticleLookupMap itsLookupMap;
+      68             :    
+      69             :    // copies are not allowed
+      70             :    ParticleNameMap( const ParticleNameMap & );
+      71             :    ParticleNameMap & operator = ( const ParticleNameMap & );
+      72             :    
+      73             : };
+      74             : 
+      75             : namespace {     // ParticleNameInit and ParticleNameMap are private
+      76             : 
+      77           0 : ParticleNameMap const &  ParticleNameInit()
+      78             : {
+      79             : 
+      80             :   PartcleIdMap  m;
+      81             :   ParticleLookupMap nameMap;
+      82             : 
+      83             :   static const struct {
+      84             :       int pid;
+      85             :       const char* pname;
+      86             :   } SNames[] = {
+      87             :       {          0, "" },
+      88             :       {          1, "d" },
+      89             :       {         -1, "d~" },
+      90             :       {          2, "u" },
+      91             :       {         -2, "u~" },
+      92             :       {          3, "s" },
+      93             :       {         -3, "s~" },
+      94             :       {          4, "c" },
+      95             :       {         -4, "c~" },
+      96             :       {          5, "b" },
+      97             :       {         -5, "b~" },
+      98             :       {          6, "t" },
+      99             :       {         -6, "t~" },
+     100             :       {          7, "b'" },
+     101             :       {         -7, "b'~" },
+     102             :       {          8, "t'" },
+     103             :       {         -8, "t'~" },
+     104             :       {         11, "e^-" },
+     105             :       {        -11, "e^+" },
+     106             :       {         12, "nu_e" },
+     107             :       {        -12, "nu_e~" },
+     108             :       {         13, "mu^-" },
+     109             :       {        -13, "mu^+" },
+     110             :       {         14, "nu_mu" },
+     111             :       {        -14, "nu_mu~" },
+     112             :       {         15, "tau^-" },
+     113             :       {        -15, "tau^+" },
+     114             :       {         16, "nu_tau" },
+     115             :       {        -16, "nu_tau~" },
+     116             :       {         17, "tau'^-" },
+     117             :       {        -17, "tau'^+" },
+     118             :       {         18, "nu_tau'" },
+     119             :       {        -18, "nu_tau'~" },
+     120             :       {         21, "g" },
+     121             :       {         22, "gamma" },
+     122             :       {      10022, "virtual-photon" },
+     123             :       {      20022, "Cerenkov-radiation" },
+     124             :       {         23, "Z^0" },
+     125             :       {         24, "W^+" },
+     126             :       {        -24, "W^-" },
+     127             :       {         25, "H_1^0" },
+     128             :       {         32, "Z_2^0" },
+     129             :       {         33, "Z_3^0" },
+     130             :       {         34, "W_2^+" },
+     131             :       {        -34, "W_2^-" },
+     132             :       {         35, "H_2^0" },
+     133             :       {         36, "H_3^0" },
+     134             :       {         37, "H^+" },
+     135             :       {        -37, "H^-" },
+     136             :       {         39, "G"  },
+     137             :       {         41, "R^0" },
+     138             :       {        -41, "R~^0" },
+     139             :       {         42, "LQ_c" },
+     140             :       {        -42, "LQ_c~" },
+     141             :       {         43, "Xu^0" },
+     142             :       {         44, "Xu^+" },
+     143             :       {        -44, "Xu^-" },
+     144             :       {         51, "H_L^0" },
+     145             :       {         52, "H_1^++" },
+     146             :       {        -52, "H_1^--" },
+     147             :       {         53, "H_2^+" },
+     148             :       {        -53, "H_2^-" },
+     149             :       {         54, "H_2^++" },
+     150             :       {        -54, "H_2^--" },
+     151             :       {         55, "H_4^0" },
+     152             :       {        -55, "H_4~^0" },
+     153             :       {         81, "generator-specific+81" },
+     154             :       {         82, "generator-specific+82" },
+     155             :       {         83, "generator-specific+83" },
+     156             :       {         84, "generator-specific+84" },
+     157             :       {         85, "generator-specific+85" },
+     158             :       {         86, "generator-specific+86" },
+     159             :       {         87, "generator-specific+87" },
+     160             :       {         88, "generator-specific+88" },
+     161             :       {         89, "generator-specific+89" },
+     162             :       {         90, "generator-specific+90" },
+     163             :       {         91, "generator-specific+91" },
+     164             :       {         92, "generator-specific+92" },
+     165             :       {         93, "generator-specific+93" },
+     166             :       {         94, "generator-specific+94" },
+     167             :       {         95, "generator-specific+95" },
+     168             :       {         96, "generator-specific+96" },
+     169             :       {         97, "generator-specific+97" },
+     170             :       {         98, "generator-specific+98" },
+     171             :       {         99, "generator-specific+99" },
+     172             :       {        -81, "generator-specific-81" },
+     173             :       {        -82, "generator-specific-82" },
+     174             :       {        -83, "generator-specific-83" },
+     175             :       {        -84, "generator-specific-84" },
+     176             :       {        -85, "generator-specific-85" },
+     177             :       {        -86, "generator-specific-86" },
+     178             :       {        -87, "generator-specific-87" },
+     179             :       {        -88, "generator-specific-88" },
+     180             :       {        -89, "generator-specific-89" },
+     181             :       {        -90, "generator-specific-90" },
+     182             :       {        -91, "generator-specific-91" },
+     183             :       {        -92, "generator-specific-92" },
+     184             :       {        -93, "generator-specific-93" },
+     185             :       {        -94, "generator-specific-94" },
+     186             :       {        -95, "generator-specific-95" },
+     187             :       {        -96, "generator-specific-96" },
+     188             :       {        -97, "generator-specific-97" },
+     189             :       {        -98, "generator-specific-98" },
+     190             :       {        -99, "generator-specific-99" },
+     191             :       {        100, "generator-specific+100" },
+     192             :       {       -100, "generator-specific-100" },
+     193             :       {        101, "geantino" },
+     194             :       {        102, "charged-geantino" },
+     195             :       {        110, "reggeon" },
+     196             :       {        130, "K_L^0" },
+     197             :       {        310, "K_S^0" },
+     198             :       {        990, "pomeron" },
+     199             :       {       9990, "odderon" },
+     200             :       {    1000001, "susy-d_L" },
+     201             :       {   -1000001, "susy-d_L~" },
+     202             :       {    1000002, "susy-u_L" },
+     203             :       {   -1000002, "susy-u_L~" },
+     204             :       {    1000003, "susy-s_L" },
+     205             :       {   -1000003, "susy-s_L~" },
+     206             :       {    1000004, "susy-c_L" },
+     207             :       {   -1000004, "susy-c_L~" },
+     208             :       {    1000005, "susy-b_1" },
+     209             :       {   -1000005, "susy-b_1~" },
+     210             :       {    1000006, "susy-t_1" },
+     211             :       {   -1000006, "susy-t_1~" },
+     212             :       {    1000011, "susy-e_L^-" },
+     213             :       {   -1000011, "susy-e_L^+" },
+     214             :       {    1000012, "susy-nu_eL" },
+     215             :       {   -1000012, "susy-nu_eL~" },
+     216             :       {    1000013, "susy-mu_L^-" },
+     217             :       {   -1000013, "susy-mu_L^+" },
+     218             :       {    1000014, "susy-nu_muL" },
+     219             :       {   -1000014, "susy-nu_muL~" },
+     220             :       {    1000015, "susy-tau_L^-" },
+     221             :       {   -1000015, "susy-tau_L^+" },
+     222             :       {    1000016, "susy-nu_tauL" },
+     223             :       {   -1000016, "susy-nu_tauL~" },
+     224             :       {    1000021, "gluino" },
+     225             :       {    1000022, "susy-chi_1^0" },
+     226             :       {    1000023, "susy-chi_2^0" },
+     227             :       {    1000024, "susy-chi_1^+" },
+     228             :       {   -1000024, "susy-chi_1^-" },
+     229             :       {    1000025, "susy-chi_3^0" },
+     230             :       {    1000035, "susy-chi_4^0" },
+     231             :       {    1000037, "susy-chi_2^+" },
+     232             :       {   -1000037, "susy-chi_2^-" },
+     233             :       {    1000039, "gravitino" },
+     234             :       {    2000001, "susy-d_R" },
+     235             :       {   -2000001, "susy-d_R~" },
+     236             :       {    2000002, "susy-u_R" },
+     237             :       {   -2000002, "susy-u_R~" },
+     238             :       {    2000003, "susy-s_R" },
+     239             :       {   -2000003, "susy-s_R~" },
+     240             :       {    2000004, "susy-c_R" },
+     241             :       {   -2000004, "susy-c_R~" },
+     242             :       {    2000005, "susy-b_R" },
+     243             :       {   -2000005, "susy-b_R~" },
+     244             :       {    2000006, "susy-t_R" },
+     245             :       {   -2000006, "susy-t_R~" },
+     246             :       {    2000011, "susy-e_R^-" },
+     247             :       {   -2000011, "susy-e_R^+" },
+     248             :       {    2000012, "susy-nu_eR" },
+     249             :       {   -2000012, "susy-nu_eR~" },
+     250             :       {    2000013, "susy-mu_R^-" },
+     251             :       {   -2000013, "susy-mu_R^+" },
+     252             :       {    2000014, "susy-nu_muR" },
+     253             :       {   -2000014, "susy-nu_muR~" },
+     254             :       {    2000015, "susy-tau_R^-" },
+     255             :       {   -2000015, "susy-tau_R^+" },
+     256             :       {    2000016, "susy-nu_tauR" },
+     257             :       {   -2000016, "susy-nu_tauR~" },
+     258             :       {    3100021, "V8_tech" },
+     259             :       {   -3100021, "V8_tech~" },
+     260             :       {    3000111, "pi_tech^0" },
+     261             :       {    3000115, "a_tech^0" },
+     262             :       {    3060111, "pi_tech_22_1" },
+     263             :       {    3160111, "pi_tech_22_8" },
+     264             :       {    3000113, "rho_tech^0" },
+     265             :       {    3130113, "rho_tech_11" },
+     266             :       {    3140113, "rho_tech_12" },
+     267             :       {    3150113, "rho_tech_21" },
+     268             :       {    3160113, "rho_tech_22" },
+     269             :       {    3000211, "pi_tech^+" },
+     270             :       {   -3000211, "pi_tech^-" },
+     271             :       {    3000213, "rho_tech^+" },
+     272             :       {   -3000213, "rho_tech^-" },
+     273             :       {    3000215, "a_tech^+" },
+     274             :       {   -3000215, "a_tech^-" },
+     275             :       {    3000221, "pi'_tech" },
+     276             :       {    3100221, "eta_tech" },
+     277             :       {    3000223, "omega_tech" },
+     278             :       {    4000001, "d*" },
+     279             :       {   -4000001, "d*~" },
+     280             :       {    4000002, "u*" },
+     281             :       {   -4000002, "u*~" },
+     282             :       {    4000011, "e*^-" },
+     283             :       {   -4000011, "e*^+" },
+     284             :       {    4000012, "nu*_e" },
+     285             :       {   -4000012, "nu*_e~" },
+     286             :       {    4000039, "G*" },
+     287             :       {   -4000039, "G*~" },
+     288             :       {    5000040, "black_hole" },
+     289             :       {    5100001, "d_L^(1)" },
+     290             :       {   -5100001, "d~_L^(1)" },
+     291             :       {    5100002, "u_L^(1)" },
+     292             :       {   -5100002, "u~_L^(1)" },
+     293             :       {    5100003, "s_L^(1)" },
+     294             :       {   -5100003, "s~_L^(1)" },
+     295             :       {    5100004, "c_L^(1)" },
+     296             :       {   -5100004, "c~_L^(1)" },
+     297             :       {    5100005, "b_L^(1)" },
+     298             :       {   -5100005, "b~_L^(1)" },
+     299             :       {    5100006, "t_L^(1)" },
+     300             :       {   -5100006, "t~_L^(1)" },
+     301             :       {    5100011, "e_L^(1)-" },
+     302             :       {   -5100011, "e_L^(1)+" },
+     303             :       {    5100012, "nu_eL^(1)" },
+     304             :       {   -5100012, "nu_eL~^(1)" },
+     305             :       {    5100013, "mu_L^(1)-" },
+     306             :       {   -5100013, "mu_L^(1)+" },
+     307             :       {    5100014, "nu_muL^(1)" },
+     308             :       {   -5100014, "nu_muL~^(1)" },
+     309             :       {    5100015, "tau_L^(1)-" },
+     310             :       {   -5100015, "tau_L^(1)+" },
+     311             :       {    5100016, "nu_tauL^(1)" },
+     312             :       {   -5100016, "nu_tauL~^(1)" },
+     313             :       {    6100001, "d_R^(1)" },
+     314             :       {   -6100001, "d~_R^(1)" },
+     315             :       {    6100002, "u_R^(1)" },
+     316             :       {   -6100002, "u~_R^(1)" },
+     317             :       {    6100003, "s_R^(1)" },
+     318             :       {   -6100003, "s~_R^(1)" },
+     319             :       {    6100004, "c_R^(1)" },
+     320             :       {   -6100004, "c~_R^(1)" },
+     321             :       {    6100005, "b_R^(1)" },
+     322             :       {   -6100005, "b~_R^(1)" },
+     323             :       {    6100006, "t_R^(1)" },
+     324             :       {   -6100006, "t~_R^(1)" },
+     325             :       {    6100011, "e_R^(1)-" },
+     326             :       {   -6100011, "e_R^(1)+" },
+     327             :       {    6100012, "nu_eR^(1)" },
+     328             :       {   -6100012, "nu_eR~^(1)" },
+     329             :       {    6100013, "mu_R^(1)-" },
+     330             :       {   -6100013, "mu_R^(1)+" },
+     331             :       {    6100014, "nu_muR^(1)" },
+     332             :       {   -6100014, "nu_muR~^(1)" },
+     333             :       {    6100015, "tau_R^(1)-" },
+     334             :       {   -6100015, "tau_R^(1)+" },
+     335             :       {    6100016, "nu_tauR^(1)" },
+     336             :       {   -6100016, "nu_tauR~^(1)" },
+     337             :       {    5100021, "g^(1)" },
+     338             :       {    5100022, "gamma^(1)" },
+     339             :       {    5100023, "Z^(1)0" },
+     340             :       {    5100024, "W^(1)+" },
+     341             :       {   -5100024, "W^(1)-" },
+     342             :       {    5100025, "h^(1)0" },
+     343             :       {    5100039, "G^(1)" },
+     344             :       {    9900012, "nu_Re" },
+     345             :       {   -9900012, "nu_Re~" },
+     346             :       {    9900014, "nu_Rmu" },
+     347             :       {   -9900014, "nu_Rmu~" },
+     348             :       {    9900016, "nu_Rtau" },
+     349             :       {   -9900016, "nu_Rtau~" },
+     350             :       {    9900023, "Z_R^0" },
+     351             :       {   -9900023, "Z_R~^0" },
+     352             :       {    9900024, "W_R^+" },
+     353             :       {   -9900024, "W_R^-" },
+     354             :       {    9900041, "H_L^++" },
+     355             :       {   -9900041, "H_L^--" },
+     356             :       {    9900042, "H_R^++" },
+     357             :       {   -9900042, "H_R^--" },
+     358             :       {    9910113, "rho_diffr^0" },
+     359             :       {    9910211, "pi_diffr^+" },
+     360             :       {   -9910211, "pi_diffr^-" },
+     361             :       {    9910223, "omega_diffr" },
+     362             :       {    9910333, "phi_diffr" },
+     363             :       {    9910443, "psi_diffr" },
+     364             :       {    9912112, "n_diffr^0" },
+     365             :       {   -9912112, "n_diffr~^0" },
+     366             :       {    9912212, "p_diffr^+" },
+     367             :       {   -9912212, "p_diffr~^-" },
+     368             :       {    9920022, "remnant photon" },
+     369             :       {    9922212, "remnant nucleon" },
+     370             :       {   -9922212, "remnant nucleon~" },
+     371             :       {    9900441, "cc~[1S08]" },     
+     372             :       {    9910441, "cc~[3P08]" },     
+     373             :       {    9900443, "cc~[3S18]" },     
+     374             :       {    9900551, "bb~[1S08]" },     
+     375             :       {    9910551, "bb~[3P08]" },     
+     376             :       {    9900553, "bb~[3S18]" },    
+     377             :       {       1103, "dd_1" },
+     378             :       {      -1103, "dd_1~" },
+     379             :       {       2101, "ud_0" },
+     380             :       {      -2101, "ud_0~" },
+     381             :       {       2103, "ud_1" },
+     382             :       {      -2103, "ud_1~" },
+     383             :       {       2203, "uu_1" },
+     384             :       {      -2203, "uu_1~" },
+     385             :       {       3101, "sd_0" },
+     386             :       {      -3101, "sd_0~" },
+     387             :       {       3103, "sd_1" },
+     388             :       {      -3103, "sd_1~" },
+     389             :       {       3201, "su_0" },
+     390             :       {      -3201, "su_0~" },
+     391             :       {       3203, "su_1" },
+     392             :       {      -3203, "su_1~" },
+     393             :       {       3303, "ss_1" },
+     394             :       {      -3303, "ss_1~" },
+     395             :       {       4101, "cd_0" },
+     396             :       {      -4101, "cd_0~" },
+     397             :       {       4103, "cd_1" },
+     398             :       {      -4103, "cd_1~" },
+     399             :       {       4201, "cu_0" },
+     400             :       {      -4201, "cu_0~" },
+     401             :       {       4203, "cu_1" },
+     402             :       {      -4203, "cu_1~" },
+     403             :       {       4301, "cs_0" },
+     404             :       {      -4301, "cs_0~" },
+     405             :       {       4303, "cs_1" },
+     406             :       {      -4303, "cs_1~" },
+     407             :       {       4403, "cc_1" },
+     408             :       {      -4403, "cc_1~" },
+     409             :       {       5101, "bd_0" },
+     410             :       {      -5101, "bd_0~" },
+     411             :       {       5103, "bd_1" },
+     412             :       {      -5103, "bd_1~" },
+     413             :       {       5201, "bu_0" },
+     414             :       {      -5201, "bu_0~" },
+     415             :       {       5203, "bu_1" },
+     416             :       {      -5203, "bu_1~" },
+     417             :       {       5301, "bs_0" },
+     418             :       {      -5301, "bs_0~" },
+     419             :       {       5303, "bs_1" },
+     420             :       {      -5303, "bs_1~" },
+     421             :       {       5401, "bc_0" },
+     422             :       {      -5401, "bc_0~" },
+     423             :       {       5403, "bc_1" },
+     424             :       {      -5403, "bc_1~" },
+     425             :       {       5503, "bb_1" },
+     426             :       {      -5503, "bb_1~" },
+     427             :       {       6101, "td_0" },
+     428             :       {      -6101, "td_0~" },
+     429             :       {       6103, "td_1" },
+     430             :       {      -6103, "td_1~" },
+     431             :       {       6201, "tu_0" },
+     432             :       {      -6201, "tu_0~" },
+     433             :       {       6203, "tu_1" },
+     434             :       {      -6203, "tu_1~" },
+     435             :       {       6301, "ts_0" },
+     436             :       {      -6301, "ts_0~" },
+     437             :       {       6303, "ts_1" },
+     438             :       {      -6303, "ts_1~" },
+     439             :       {       6401, "tc_0" },
+     440             :       {      -6401, "tc_0~" },
+     441             :       {       6403, "tc_1" },
+     442             :       {      -6403, "tc_1~" },
+     443             :       {       6501, "tb_0" },
+     444             :       {      -6501, "tb_0~" },
+     445             :       {       6503, "tb_1" },
+     446             :       {      -6503, "tb_1~" },
+     447             :       {       6603, "tt_1" },
+     448             :       {      -6603, "tt_1~" },
+     449             :       {       7101, "b'd_0" },
+     450             :       {      -7101, "b'd_0~" },
+     451             :       {       7103, "b'd_1" },
+     452             :       {      -7103, "b'd_1~" },
+     453             :       {       7201, "b'u_0" },
+     454             :       {      -7201, "b'u_0~" },
+     455             :       {       7203, "b'u_1" },
+     456             :       {      -7203, "b'u_1~" },
+     457             :       {       7301, "b's_0" },
+     458             :       {      -7301, "b's_0~" },
+     459             :       {       7303, "b's_1" },
+     460             :       {      -7303, "b's_1~" },
+     461             :       {       7401, "b'c_0" },
+     462             :       {      -7401, "b'c_0~" },
+     463             :       {       7403, "b'c_1" },
+     464             :       {      -7403, "b'c_1~" },
+     465             :       {       7501, "b'b_0" },
+     466             :       {      -7501, "b'b_0~" },
+     467             :       {       7503, "b'b_1" },
+     468             :       {      -7503, "b'b_1~" },
+     469             :       {       7601, "b't_0" },
+     470             :       {      -7601, "b't_0~" },
+     471             :       {       7603, "b't_1" },
+     472             :       {      -7603, "b't_1~" },
+     473             :       {       7703, "b'b'_1" },
+     474             :       {      -7703, "b'b'_1~" },
+     475             :       {       8101, "t'd_0" },
+     476             :       {      -8101, "t'd_0~" },
+     477             :       {       8103, "t'd_1" },
+     478             :       {      -8103, "t'd_1~" },
+     479             :       {       8201, "t'u_0" },
+     480             :       {      -8201, "t'u_0~" },
+     481             :       {       8203, "t'u_1" },
+     482             :       {      -8203, "t'u_1~" },
+     483             :       {       8301, "t's_0" },
+     484             :       {      -8301, "t's_0~" },
+     485             :       {       8303, "t's_1" },
+     486             :       {      -8303, "t's_1~" },
+     487             :       {       8401, "t'c_0" },
+     488             :       {      -8401, "t'c_0~" },
+     489             :       {       8403, "t'c_1" },
+     490             :       {      -8403, "t'c_1~" },
+     491             :       {       8501, "t'b_0" },
+     492             :       {      -8501, "t'b_0~" },
+     493             :       {       8503, "t'b_1" },
+     494             :       {      -8503, "t'b_1~" },
+     495             :       {       8601, "t't_0" },
+     496             :       {      -8601, "t't_0~" },
+     497             :       {       8603, "t't_1" },
+     498             :       {      -8603, "t't_1~" },
+     499             :       {       8701, "t'b'_0" },
+     500             :       {      -8701, "t'b'_0~" },
+     501             :       {       8703, "t'b'_1" },
+     502             :       {      -8703, "t'b'_1~" },
+     503             :       {       8803, "t't'_1" },
+     504             :       {      -8803, "t't'_1~" },
+     505             :       {        111, "pi^0" },
+     506             :       {    9000111, "a_0(980)^0" },
+     507             :       {      10111, "a_0(1450)^0" },
+     508             :       {     100111, "pi(1300)^0" },
+     509             :       {    9010111, "pi(1800)^0" },
+     510             :       {        113, "rho(770)^0" },
+     511             :       {      10113, "b_1(1235)^0" },
+     512             :       {      20113, "a_1(1260)^0" },
+     513             :       {    9000113, "pi_1(1400)^0" },
+     514             :       {     100113, "rho(1450)^0" },
+     515             :       {    9010113, "pi_1(1600)^0" },
+     516             :       {    9020113, "a_1(1640)^0" },
+     517             :       {      30113, "rho(1700)^0" },
+     518             :       {    9030113, "rho(1900)^0" },
+     519             :       {    9040113, "rho(2150)^0" },
+     520             :       {        115, "a_2(1320)^0" },
+     521             :       {      10115, "pi_2(1670)^0" },
+     522             :       {    9000115, "a_2(1700)^0" },
+     523             :       {    9010115, "pi_2(2100)^0" },
+     524             :       {        117, "rho_3(1690)^0" },
+     525             :       {    9000117, "rho_3(1990)^0" },
+     526             :       {    9010117, "rho_3(2250)^0" },
+     527             :       {        119, "a_4(2040)^0" },
+     528             :       {        211, "pi^+" },
+     529             :       {       -211, "pi^-" },
+     530             :       {    9000211, "a_0(980)^+" },
+     531             :       {   -9000211, "a_0(980)^-" },
+     532             :       {      10211, "a_0(1450)^+" },
+     533             :       {     -10211, "a_0(1450)^-" },
+     534             :       {     100211, "pi(1300)^+" },
+     535             :       {    -100211, "pi(1300)^-" },
+     536             :       {    9010211, "pi(1800)^+" },
+     537             :       {   -9010211, "pi(1800)^-" },
+     538             :       {        213, "rho(770)^+" },
+     539             :       {       -213, "rho(770)^-" },
+     540             :       {      10213, "b_1(1235)^+" },
+     541             :       {     -10213, "b_1(1235)^-" },
+     542             :       {      20213, "a_1(1260)^+" },
+     543             :       {     -20213, "a_1(1260)^-" },
+     544             :       {    9000213, "pi_1(1400)^+" },
+     545             :       {   -9000213, "pi_1(1400)^-" },
+     546             :       {     100213, "rho(1450)^+" },
+     547             :       {    -100213, "rho(1450)^-" },
+     548             :       {    9010213, "pi_1(1600)^+" },
+     549             :       {   -9010213, "pi_1(1600)^-" },
+     550             :       {    9020213, "a_1(1640)^+" },
+     551             :       {   -9020213, "a_1(1640)^-" },
+     552             :       {      30213, "rho(1700)^+" },
+     553             :       {     -30213, "rho(1700)^-" },
+     554             :       {    9030213, "rho(1900)^+" },
+     555             :       {   -9030213, "rho(1900)^-" },
+     556             :       {    9040213, "rho(2150)^+" },
+     557             :       {   -9040213, "rho(2150)^-" },
+     558             :       {        215, "a_2(1320)^+" },
+     559             :       {       -215, "a_2(1320)^-" },
+     560             :       {      10215, "pi_2(1670)^+" },
+     561             :       {     -10215, "pi_2(1670)^-" },
+     562             :       {    9000215, "a_2(1700)^+" },
+     563             :       {   -9000215, "a_2(1700)^-" },
+     564             :       {    9010215, "pi_2(2100)^+" },
+     565             :       {   -9010215, "pi_2(2100)^-" },
+     566             :       {        217, "rho_3(1690)^+" },
+     567             :       {       -217, "rho_3(1690)^-" },
+     568             :       {    9000217, "rho_3(1990)^+" },
+     569             :       {   -9000217, "rho_3(1990)^-" },
+     570             :       {    9010217, "rho_3(2250)^+" },
+     571             :       {   -9010217, "rho_3(2250)^-" },
+     572             :       {        219, "a_4(2040)^+" },
+     573             :       {       -219, "a_4(2040)^-" },
+     574             :       {        221, "eta" },
+     575             :       {    9000221, "f_0(600)" },
+     576             :       {      10221, "f_0(1370)" },
+     577             :       {    9010221, "f_0(980)" },
+     578             :       {    9020221, "eta(1405)" },
+     579             :       {    9030221, "f_0(1500)" },
+     580             :       {    9040221, "eta(1760)" },
+     581             :       {    9050221, "f_0(2020)" },
+     582             :       {    9060221, "f_0(2100)" },
+     583             :       {    9070221, "f_0(2200)" },
+     584             :       {    9080221, "eta(2225)" },
+     585             :       {    9090221, "sigma_0" },
+     586             :       {     100221, "eta(1295)" },
+     587             :       {        331, "eta'(958)" },
+     588             :       {      10331, "f_0(1710)" },
+     589             :       {     100331, "eta(1475)" },
+     590             :       {        223, "omega(782)" },
+     591             :       {    9000223, "f_1(1510)" },
+     592             :       {    9010223, "h_1(1595)" },
+     593             :       {      10223, "h_1(1170)" },
+     594             :       {      20223, "f_1(1285)" },
+     595             :       {      30223, "omega(1650)" },
+     596             :       {     100223, "omega(1420)" },
+     597             :       {        333, "phi(1020)" },
+     598             :       {      10333, "h_1(1380)" },
+     599             :       {      20333, "f_1(1420)" },
+     600             :       {     100333, "phi(1680)" },
+     601             :       {        225, "f_2(1270)" },
+     602             :       {    9000225, "f_2(1430)" },
+     603             :       {      10225, "eta_2(1645)" },
+     604             :       {    9010225, "f_2(1565)" },
+     605             :       {    9020225, "f_2(1640)" },
+     606             :       {    9030225, "f_2(1810)" },
+     607             :       {    9040225, "f_2(1910)" },
+     608             :       {    9050225, "f_2(1950)" },
+     609             :       {    9060225, "f_2(2010)" },
+     610             :       {    9070225, "f_2(2150)" },
+     611             :       {    9080225, "f_2(2300)" },
+     612             :       {    9090225, "f_2(2340)" },
+     613             :       {        335, "f'_2(1525)" },
+     614             :       {      10335, "eta_2(1870)" },
+     615             :       {        227, "omega_3(1670)" },
+     616             :       {        337, "phi_3(1850)" },
+     617             :       {        229, "f_4(2050)" },
+     618             :       {    9000229, "f_J(2220)" },
+     619             :       {    9010229, "f_4(2300)" },
+     620             :       {        311, "K^0" },
+     621             :       {       -311, "K~^0" },
+     622             :       {    9000311, "K*_0(800)^0" },
+     623             :       {   -9000311, "K*_0(800)~^0" },
+     624             :       {      10311, "K*_0(1430)^0" },
+     625             :       {     -10311, "K*_0(1430)~^0" },
+     626             :       {     100311, "K(1460)^0" },
+     627             :       {    -100311, "K(1460)~^0" },
+     628             :       {    9010311, "K(1830)^0" },
+     629             :       {   -9010311, "K(1830)~^0" },
+     630             :       {    9020311, "K*_0(1950)^0" },
+     631             :       {   -9020311, "K*_0(1950)~^0" },
+     632             :       {        321, "K^+" },
+     633             :       {       -321, "K^-" },
+     634             :       {    9000321, "K*_0(800)^+" },
+     635             :       {   -9000321, "K*_0(800)^-" },
+     636             :       {      10321, "K*_0(1430)^+" },
+     637             :       {     -10321, "K*_0(1430)^-" },
+     638             :       {     100321, "K(1460)^+" },
+     639             :       {    -100321, "K(1460)^-" },
+     640             :       {    9010321, "K(1830)^+" },
+     641             :       {   -9010321, "K(1830)^-" },
+     642             :       {    9020321, "K*_0(1950)^+" },
+     643             :       {   -9020321, "K*_0(1950)^-" },
+     644             :       {        313, "K*(892)^0" },
+     645             :       {       -313, "K*(892)~^0" },
+     646             :       {      10313, "K_1(1270)^0" },
+     647             :       {     -10313, "K_1(1270)~^0" },
+     648             :       {      20313, "K_1(1400)^0" },
+     649             :       {     -20313, "K_1(1400)~^0" },
+     650             :       {      30313, "K*(1680)^0" },
+     651             :       {     -30313, "K*(1680)~^0" },
+     652             :       {     100313, "K*(1410)^0" },
+     653             :       {    -100313, "K*(1410)~^0" },
+     654             :       {    9000313, "K_1(1650)^0" },
+     655             :       {   -9000313, "K_1(1650)~^0" },
+     656             :       {        323, "K*(892)^+" },
+     657             :       {       -323, "K*(892)^-" },
+     658             :       {      10323, "K_1(1270)^+" },
+     659             :       {     -10323, "K_1(1270)^-" },
+     660             :       {      20323, "K_1(1400)^+" },
+     661             :       {     -20323, "K_1(1400)^-" },
+     662             :       {      30323, "K*(1680)^+" },
+     663             :       {     -30323, "K*(1680)^-" },
+     664             :       {     100323, "K*(1410)^+" },
+     665             :       {    -100323, "K*(1410)^-" },
+     666             :       {    9000323, "K_1(1650)^+" },
+     667             :       {   -9000323, "K_1(1650)^-" },
+     668             :       {        315, "K*_2(1430)^0" },
+     669             :       {       -315, "K*_2(1430)~^0" },
+     670             :       {    9000315, "K_2(1580)^0" },
+     671             :       {   -9000315, "K_2(1580)~^0" },
+     672             :       {      10315, "K_2(1770)^0" },
+     673             :       {     -10315, "K_2(1770)~^0" },
+     674             :       {    9010315, "K*_2(1980)^0" },
+     675             :       {   -9010315, "K*_2(1980)~^0" },
+     676             :       {    9020315, "K_2(2250)^0" },
+     677             :       {   -9020315, "K_2(2250)~^0" },
+     678             :       {      20315, "K_2(1820)^0" },
+     679             :       {     -20315, "K_2(1820)~^0" },
+     680             :       {        325, "K*_2(1430)^+" },
+     681             :       {       -325, "K*_2(1430)^-" },
+     682             :       {    9000325, "K_2(1580)^+" },
+     683             :       {   -9000325, "K_2(1580)^-" },
+     684             :       {      10325, "K_2(1770)^+" },
+     685             :       {     -10325, "K_2(1770)^-" },
+     686             :       {    9010325, "K*_2(1980)^+" },
+     687             :       {   -9010325, "K*_2(1980)^-" },
+     688             :       {    9020325, "K_2(2250)^+" },
+     689             :       {   -9020325, "K_2(2250)^-" },
+     690             :       {      20325, "K_2(1820)^+" },
+     691             :       {     -20325, "K_2(1820)^-" },
+     692             :       {     100325, "K_2(1980)^+" },
+     693             :       {    -100325, "K_2(1980)^-" },
+     694             :       {        317, "K*_3(1780)^0" },
+     695             :       {       -317, "K*_3(1780)~^0" },
+     696             :       {    9010317, "K_3(2320)^0" },
+     697             :       {   -9010317, "K_3(2320)~^0" },
+     698             :       {        327, "K*_3(1780)^+" },
+     699             :       {       -327, "K*_3(1780)^-" },
+     700             :       {    9010327, "K_3(2320)^+" },
+     701             :       {   -9010327, "K_3(2320)^-" },
+     702             :       {        319, "K*_4(2045)^0" },
+     703             :       {       -319, "K*_4(2045)~^0" },
+     704             :       {    9000319, "K_4(2500)^0" },
+     705             :       {   -9000319, "K_4(2500)~^0" },
+     706             :       {        329, "K*_4(2045)^+" },
+     707             :       {       -329, "K*_4(2045)^-" },
+     708             :       {    9000329, "K_4(2500)^+" },
+     709             :       {   -9000329, "K_4(2500)^-" },
+     710             :       {        411, "D^+" },
+     711             :       {       -411, "D^-" },
+     712             :       {      10411, "D*_0(2400)^+" },
+     713             :       {     -10411, "D*_0(2400)^-" },
+     714             :       {     100411, "D(2S)^+" },
+     715             :       {    -100411, "D(2S)^-" },
+     716             :       {        413, "D*(2010)^+" },
+     717             :       {       -413, "D*(2010)^-" },
+     718             :       {      10413, "D_1(2420)^+" },
+     719             :       {     -10413, "D_1(2420)^-" },
+     720             :       {      20413, "D_1(H)^+" },
+     721             :       {     -20413, "D_1(H)^-" },
+     722             :       {     100413, "D*(2S)^+" },
+     723             :       {    -100413, "D*(2S)^-" },
+     724             :       {        415, "D*_2(2460)^+" },
+     725             :       {       -415, "D*_2(2460)^-" },
+     726             :       {        421, "D^0" },
+     727             :       {       -421, "D~^0" },
+     728             :       {      10421, "D*_0(2400)^0" },
+     729             :       {     -10421, "D*_0(2400)~^0" },
+     730             :       {     100421, "D(2S)^0" },
+     731             :       {    -100421, "D(2S)~^0" },
+     732             :       {        423, "D*(2007)^0" },
+     733             :       {       -423, "D*(2007)~^0" },
+     734             :       {      10423, "D_1(2420)^0" },
+     735             :       {     -10423, "D_1(2420)~^0" },
+     736             :       {      20423, "D_1(2430)^0" },
+     737             :       {     -20423, "D_1(2430)~^0" },
+     738             :       {     100423, "D*(2S)^0" },
+     739             :       {    -100423, "D*(2S)~^0" },
+     740             :       {        425, "D*_2(2460)^0" },
+     741             :       {       -425, "D*_2(2460)~^0" },
+     742             :       {        431, "D_s^+" },
+     743             :       {       -431, "D_s^-" },
+     744             :       {      10431, "D*_s0(2317)^+" },
+     745             :       {     -10431, "D*_s0(2317)^-" },
+     746             :       {        433, "D*_s^+" },
+     747             :       {       -433, "D*_s^-" },
+     748             :       {      10433, "D_s1(2536)^+" },
+     749             :       {     -10433, "D_s1(2536)^-" },
+     750             :       {      20433, "D_s1(2460)^+" },
+     751             :       {     -20433, "D_s1(2460)^-" },
+     752             :       {        435, "D*_s2(2573)^+" },
+     753             :       {       -435, "D*_s2(2573)^-" },
+     754             :       {        441, "eta_c(1S)" },
+     755             :       {      10441, "chi_c0(1P)" },
+     756             :       {     100441, "eta_c(2S)" },
+     757             :       {        443, "J/psi(1S)" },
+     758             :       {    9000443, "psi(4040)" },
+     759             :       {      10443, "hc(1P)" },
+     760             :       {    9010443, "psi(4160)" },
+     761             :       {      20443, "chi_c1(1P)" },
+     762             :       {    9020443, "psi(4415)" },
+     763             :       {      30443, "psi(3770)" },
+     764             :       {     100443, "psi(2S)" },
+     765             :       {        445, "chi_c2(1P)" },
+     766             :       {     100445, "chi_c2(2P)" },
+     767             :       {        511, "B^0" },
+     768             :       {       -511, "B~^0" },
+     769             :       {      10511, "B*_0^0" },
+     770             :       {     -10511, "B*_0~^0" },
+     771             :       {        513, "B*^0" },
+     772             :       {       -513, "B*~^0" },
+     773             :       {      10513, "B_1(L)^0" },
+     774             :       {     -10513, "B_1(L)~^0" },
+     775             :       {      20513, "B_1(H)^0" },
+     776             :       {     -20513, "B_1(H)~^0" },
+     777             :       {        515, "B*_2^0" },
+     778             :       {       -515, "B*_2~^0" },
+     779             :       {        521, "B^+" },
+     780             :       {       -521, "B^-" },
+     781             :       {      10521, "B*_0^+" },
+     782             :       {     -10521, "B*_0^-" },
+     783             :       {        523, "B*^+" },
+     784             :       {       -523, "B*^-" },
+     785             :       {      10523, "B_1(L)^+" },
+     786             :       {     -10523, "B_1(L)^-" },
+     787             :       {      20523, "B_1(H)^+" },
+     788             :       {     -20523, "B_1(H)^-" },
+     789             :       {        525, "B*_2^+" },
+     790             :       {       -525, "B*_2^-" },
+     791             :       {        531, "B_s^0" },
+     792             :       {       -531, "B_s~^0" },
+     793             :       {      10531, "B*_s0^0" },
+     794             :       {     -10531, "B*_s0~^0" },
+     795             :       {        533, "B*_s^0" },
+     796             :       {       -533, "B*_s~^0" },
+     797             :       {      10533, "B_s1(L)^0" },
+     798             :       {     -10533, "B_s1(L)~^0" },
+     799             :       {      20533, "B_s1(H)^0" },
+     800             :       {     -20533, "B_s1(H)~^0" },
+     801             :       {        535, "B*_s2^0" },
+     802             :       {       -535, "B*_s2~^0" },
+     803             :       {        541, "B_c^+" },
+     804             :       {       -541, "B_c^-" },
+     805             :       {      10541, "B*_c0^+" },
+     806             :       {     -10541, "B*_c0^-" },
+     807             :       {        543, "B*_c^+" },
+     808             :       {       -543, "B*_c^-" },
+     809             :       {      10543, "B_c1(L)^+" },
+     810             :       {     -10543, "B_c1(L)^-" },
+     811             :       {      20543, "B_c1(H)^+" },
+     812             :       {     -20543, "B_c1(H)^-" },
+     813             :       {        545, "B*_c2^+" },
+     814             :       {       -545, "B*_c2^-" },
+     815             :       {        551, "eta_b(1S)" },
+     816             :       {      10551, "chi_b0(1P)" },
+     817             :       {     100551, "eta_b(2S)" },
+     818             :       {     110551, "chi_b0(2P)" },
+     819             :       {     200551, "eta_b(3S)" },
+     820             :       {     210551, "chi_b0(3P)" },
+     821             :       {        553, "Upsilon(1S)" },
+     822             :       {    9000553, "Upsilon(10860)" },
+     823             :       {      10553, "h_b(1P)" },
+     824             :       {    9010553, "Upsilon(11020)" },
+     825             :       {      20553, "chi_b1(1P)" },
+     826             :       {    9020553, "Upsilon(7S)" },
+     827             :       {      30553, "Upsilon_1(1D)" },
+     828             :       {     100553, "Upsilon(2S)" },
+     829             :       {     110553, "h_b(2P)" },
+     830             :       {     120553, "chi_b1(2P)" },
+     831             :       {     130553, "Upsilon_1(2D)" },
+     832             :       {     200553, "Upsilon(3S)" },
+     833             :       {     210553, "h_b(3P)" },
+     834             :       {     220553, "chi_b1(3P)" },
+     835             :       {     300553, "Upsilon(4S)" },
+     836             :       {        555, "chi_b2(1P)" },
+     837             :       {      10555, "eta_b2(1D)" },
+     838             :       {      20555, "Upsilon_2(1D)" },
+     839             :       {     100555, "chi_b2(2P)" },
+     840             :       {     110555, "eta_b2(2D)" },
+     841             :       {     120555, "Upsilon_2(2D)" },
+     842             :       {     200555, "chi_b2(3P)" },
+     843             :       {        557, "Upsilon_3(1D)" },
+     844             :       {     100557, "Upsilon_3(2D)" },
+     845             :       {        611, "T^+" },
+     846             :       {       -611, "T^-" },
+     847             :       {        613, "T*^+" },
+     848             :       {       -613, "T*^-" },
+     849             :       {        621, "T^0" },
+     850             :       {       -621, "T~^0" },
+     851             :       {        623, "T*^0" },
+     852             :       {       -623, "T*~^0" },
+     853             :       {        631, "T_s^+" },
+     854             :       {       -631, "T_s^-" },
+     855             :       {        633, "T*_s^+" },
+     856             :       {       -633, "T*_s^-" },
+     857             :       {        641, "T_c^0" },
+     858             :       {       -641, "T_c~^0" },
+     859             :       {        643, "T*_c^0" },
+     860             :       {       -643, "T*_c~^0" },
+     861             :       {        651, "T_b^+" },
+     862             :       {       -651, "T_b^-" },
+     863             :       {        653, "T*_b^+" },
+     864             :       {       -653, "T*_b^-" },
+     865             :       {        661, "eta_t" },
+     866             :       {        663, "theta" },
+     867             :       {        711, "L^0" },
+     868             :       {       -711, "L~^0" },
+     869             :       {        713, "L*^0" },
+     870             :       {       -713, "L*~^0" },
+     871             :       {        721, "L^-" },
+     872             :       {       -721, "L^+" },
+     873             :       {        723, "L*^-" },
+     874             :       {       -723, "L*^+" },
+     875             :       {        731, "L_s^0" },
+     876             :       {       -731, "L_s~^0" },
+     877             :       {        733, "L*_s^0" },
+     878             :       {       -733, "L*_s~^0" },
+     879             :       {        741, "L_c^-" },
+     880             :       {       -741, "L_c^+" },
+     881             :       {        743, "L*_c^-" },
+     882             :       {       -743, "L*_c^+" },
+     883             :       {        751, "L_b^0" },
+     884             :       {       -751, "L_b~^0" },
+     885             :       {        753, "L*_b^0" },
+     886             :       {       -753, "L*_b~^0" },
+     887             :       {        761, "L_t^-" },
+     888             :       {       -761, "L_t^+" },
+     889             :       {        763, "L*_t^-" },
+     890             :       {       -763, "L*_t^+" },
+     891             :       {        771, "eta_l" },
+     892             :       {        773, "theta_l" },
+     893             :       {        811, "X^+" },
+     894             :       {       -811, "X^-" },
+     895             :       {        813, "X*^+" },
+     896             :       {       -813, "X*^-" },
+     897             :       {        821, "X^0" },
+     898             :       {       -821, "X~^0" },
+     899             :       {        823, "X*^0" },
+     900             :       {       -823, "X*~^0" },
+     901             :       {        831, "X_s^+" },
+     902             :       {       -831, "X_s^-" },
+     903             :       {        833, "X*_s^+" },
+     904             :       {       -833, "X*_s^-" },
+     905             :       {        841, "X_c^0" },
+     906             :       {       -841, "X_c~^0" },
+     907             :       {        843, "X*_c^0" },
+     908             :       {       -843, "X*_c~^0" },
+     909             :       {        851, "X_b^+" },
+     910             :       {       -851, "X_b^-" },
+     911             :       {        853, "X*_b^+" },
+     912             :       {       -853, "X*_b^-" },
+     913             :       {        861, "X_t^0" },
+     914             :       {       -861, "X_t~^0" },
+     915             :       {        863, "X*_t^0" },
+     916             :       {       -863, "X*_t~^0" },
+     917             :       {        871, "X_l^+" },
+     918             :       {       -871, "X_l^-" },
+     919             :       {        873, "X*_l^+" },
+     920             :       {       -873, "X*_l^-" },
+     921             :       {        881, "eta_h" },
+     922             :       {        883, "theta_H" },
+     923             :       {      30343, "Xsd" },
+     924             :       {     -30343, "anti-Xsd" },
+     925             :       {      30353, "Xsu" },
+     926             :       {     -30353, "anti-Xsu" },
+     927             :       {      30363, "Xss" },
+     928             :       {     -30363, "anti-Xss" },
+     929             :       {      30373, "Xdd" },
+     930             :       {     -30373, "anti-Xdd" },
+     931             :       {      30383, "Xdu" },
+     932             :       {     -30383, "anti-Xdu" },
+     933             :       {       2112, "n^0" },
+     934             :       {      -2112, "n~^0" },
+     935             :       {       2212, "p^+" },
+     936             :       {      -2212, "p~^-" },
+     937             :     {        12212,        "N(1440)^+"},
+     938             :     {        12112,        "N(1440)^0"},
+     939             :     {        22212,        "N(1535)^+"},
+     940             :     {        22112,        "N(1535)^0"},
+     941             :     {        32212,        "N(1650)^+"},
+     942             :     {        32112,        "N(1650)^0"},
+     943             :     {        42212,        "N(1710)^+"},
+     944             :     {        42112,        "N(1710)^0"},
+     945             :     {         1214,         "N(1520)^0"},
+     946             :     {         2124,         "N(1520)^+"},
+     947             :     {        21214,        "N(1700)^0"},
+     948             :     {        22124,        "N(1700)^+"},
+     949             :     {        31214,        "N(1720)^0"},
+     950             :     {        32124,        "N(1720)^+"},
+     951             :     {         2116,         "N(1675)^0"},
+     952             :     {         2216,         "N(1675)^+"},
+     953             :     {        12116,        "N(1680)^0"},
+     954             :     {        12216,        "N(1680)^+"},
+     955             :     {         1218,         "N(2190)^0"},
+     956             :     {         2128,        "N(2190)^+" },
+     957             :       {       1114, "Delta^-" },
+     958             :       {      -1114, "Delta~^+" },
+     959             :       {       2114, "Delta^0" },
+     960             :       {      -2114, "Delta~^0" },
+     961             :       {       2214, "Delta^+" },
+     962             :       {      -2214, "Delta~^-" },
+     963             :       {       2224, "Delta^++" },
+     964             :       {      -2224, "Delta~^--" },
+     965             :     {        31114,   "Delta(1600)^-"      },
+     966             :     {        32114,   "Delta(1600)^0"      },
+     967             :     {        32214,    "Delta(1600)^+"     },
+     968             :     {        32224,     "Delta(1600)^++"    },
+     969             :     {         1112,    "Delta(1620)^-"     },
+     970             :     {         1212,    "Delta(1620)^0"     },
+     971             :     {         2122,    "Delta(1620)^+"     },
+     972             :     {         2222,     "Delta(1620)^++"    },
+     973             :     {        11114,     "Delta(1700)^-"    },
+     974             :     {        12114,     "Delta(1700)^0"    },
+     975             :     {        12214,     "Delta(1700)^+"    },
+     976             :     {        12224,      "Delta(1700)^++"   },
+     977             :     {         1116,     "Delta(1905)^-"    },
+     978             :     {         1216,     "Delta(1905)^0"    },
+     979             :     {         2126,     "Delta(1905)^+"    },
+     980             :     {         2226,      "Delta(1905)^++"   },
+     981             :     {        21112,    "Delta(1910)^-"    },
+     982             :     {        21212,     "Delta(1910)^0"   },
+     983             :     {        22122,     "Delta(1910)^+"   },
+     984             :     {        22222,     "Delta(1910)^++"   },
+     985             :     {        21114,    "Delta(1920)^-"    },
+     986             :     {        22114,     "Delta(1920)^0"   },
+     987             :     {        22214,     "Delta(1920)^+"   },
+     988             :     {        22224,    "Delta(1920)^++"    },
+     989             :     {        11116,    "Delta(1930)^-"    },
+     990             :     {        11216,     "Delta(1930)^0"   },
+     991             :     {        12126,     "Delta(1930)^+"   },
+     992             :     {        12226,     "Delta(1930)^++"   },
+     993             :     {         1118,     "Delta(1950)^-"    },
+     994             :     {         2118,      "Delta(1950)^0"   },
+     995             :     {         2218,      "Delta(1950)^+"   },
+     996             :     {         2228,     "Delta(1950)^++"    },
+     997             :       {       3122, "Lambda^0" },
+     998             :       {      -3122, "Lambda~^0" },
+     999             :       {      13122, "Lambda(1405)^0" },
+    1000             :       {     -13122, "Lambda~(1405)^0" },
+    1001             :       {      23122, "Lambda(1600)^0" },
+    1002             :       {     -23122, "Lambda~(1600)^0" },
+    1003             :       {      33122, "Lambda(1670)^0" },
+    1004             :       {     -33122, "Lambda~(1670)^0" },
+    1005             :       {      43122, "Lambda(1800)^0" },
+    1006             :       {     -43122, "Lambda~(1800)^0" },
+    1007             :       {      53122, "Lambda(1810)^0" },
+    1008             :       {     -53122, "Lambda~(1810)^0" },
+    1009             :       {       3124, "Lambda(1520)^0" },
+    1010             :       {      -3124, "Lambda~(1520)^0" },
+    1011             :       {      13124, "Lambda(1690)^0" },
+    1012             :       {     -13124, "Lambda~(1690)^0" },
+    1013             :       {      23124, "Lambda(1890)^0" },
+    1014             :       {     -23124, "Lambda~(1890)^0" },
+    1015             :       {       3126, "Lambda(1820)^0" },
+    1016             :       {      -3126, "Lambda~(1820)^0" },
+    1017             :       {      13126, "Lambda(1830)^0" },
+    1018             :       {     -13126, "Lambda~(1830)^0" },
+    1019             :       {      23126, "Lambda(2110)^0" },
+    1020             :       {     -23126, "Lambda~(2110)^0" },
+    1021             :       {       3128, "Lambda(2100)^0" },
+    1022             :       {      -3128, "Lambda~(2100)^0" },
+    1023             :       {       3112, "Sigma^-" },
+    1024             :       {      -3112, "Sigma~^+" },
+    1025             :       {       3212, "Sigma^0" },
+    1026             :       {      -3212, "Sigma~^0" },
+    1027             :       {       3222, "Sigma^+" },
+    1028             :       {      -3222, "Sigma~^-" },
+    1029             :       {      13222, "Sigma(1660)^+" },
+    1030             :       {     -13222, "Sigma~(1660)^+" },
+    1031             :       {      13212, "Sigma(1660)^0" },
+    1032             :       {     -13212, "Sigma~(1660)^0" },
+    1033             :       {      13112, "Sigma(1660)^-" },
+    1034             :       {     -13112, "Sigma~(1660)^-" },
+    1035             :       {      23112, "Sigma(1750)^-" },
+    1036             :       {     -23112, "Sigma~(1750)^-" },
+    1037             :       {      23212, "Sigma(1750)^0" },
+    1038             :       {     -23212, "Sigma~(1750)^0" },
+    1039             :       {      23222, "Sigma(1750)^+" },
+    1040             :       {     -23222, "Sigma~(1750)^+" },
+    1041             :       {       3114, "Sigma*^-" },
+    1042             :       {      -3114, "Sigma*~^+" },
+    1043             :       {       3214, "Sigma*^0" },
+    1044             :       {      -3214, "Sigma*~^0" },
+    1045             :       {       3224, "Sigma*^+" },
+    1046             :       {      -3224, "Sigma*~^-" },
+    1047             :       {      13224, "Sigma(1670)^+" },
+    1048             :       {     -13224, "Sigma~(1670)^+" },
+    1049             :       {      13214, "Sigma(1670)^0" },
+    1050             :       {     -13214, "Sigma~(1670)^0" },
+    1051             :       {      13114, "Sigma(1670)^-" },
+    1052             :       {     -13114, "Sigma~(1670)^-" },
+    1053             :       {      23224, "Sigma(1940)^+" },
+    1054             :       {     -23224, "Sigma~(1940)^+" },
+    1055             :       {      23214, "Sigma(1940)^0" },
+    1056             :       {     -23214, "Sigma~(1940)^0" },
+    1057             :       {      23114, "Sigma(1940)^-" },
+    1058             :       {     -23114, "Sigma~(1940)^-" },
+    1059             :       {       3226, "Sigma(1775)^+" },
+    1060             :       {      -3226, "Sigma~(1775)^+" },
+    1061             :       {       3216, "Sigma(1775)^0" },
+    1062             :       {      -3216, "Sigma~(1775)^0" },
+    1063             :       {       3116, "Sigma(1775)^-" },
+    1064             :       {      -3116, "Sigma~(1775)^-" },
+    1065             :       {      13226, "Sigma(1915)^+" },
+    1066             :       {     -13226, "Sigma~(1915)^+" },
+    1067             :       {      13216, "Sigma(1915)^0" },
+    1068             :       {     -13216, "Sigma~(1915)^0" },
+    1069             :       {      13116, "Sigma(1915)^-" },
+    1070             :       {     -13116, "Sigma~(1915)^-" },
+    1071             :       {       3228, "Sigma(2030)^+" },
+    1072             :       {      -3228, "Sigma~(2030)^+" },
+    1073             :       {       3218, "Sigma(2030)^0" },
+    1074             :       {      -3218, "Sigma~(2030)^0" },
+    1075             :       {       3118, "Sigma(2030)^-" },
+    1076             :       {      -3118, "Sigma~(2030)^-" },
+    1077             :       {       3312, "Xi^-" },
+    1078             :       {      -3312, "Xi~^+" },
+    1079             :       {       3322, "Xi^0" },
+    1080             :       {      -3322, "Xi~^0" },
+    1081             :       {       3314, "Xi*^-" },
+    1082             :       {      -3314, "Xi*~^+" },
+    1083             :       {       3324, "Xi*^0" },
+    1084             :       {      -3324, "Xi*~^0" },
+    1085             :       {      13314, "Xi(1820)^-" },
+    1086             :       {     -13314, "Xi(1820)~^+" },
+    1087             :       {      13324, "Xi(1820)^0" },
+    1088             :       {     -13324, "Xi(1820)~^0" },
+    1089             :       {       3334, "Omega^-" },
+    1090             :       {      -3334, "Omega~^+" },
+    1091             :       {       4112, "Sigma_c^0" },
+    1092             :       {      -4112, "Sigma_c~^0" },
+    1093             :       {       4114, "Sigma*_c^0" },
+    1094             :       {      -4114, "Sigma*_c~^0" },
+    1095             :       {       4122, "Lambda_c^+" },
+    1096             :       {      -4122, "Lambda_c~^-" },
+    1097             :       {      14122, "Lambda_c(2593)^+" },
+    1098             :       {     -14122, "Lambda_c~(2593)^-" },
+    1099             :       {      14124, "Lambda_c(2625)^+" },
+    1100             :       {     -14124, "Lambda_c~(2625)^-" },
+    1101             :       {       4132, "Xi_c^0" },
+    1102             :       {      -4132, "Xi_c~^0" },
+    1103             :       {       4212, "Sigma_c^+" },
+    1104             :       {      -4212, "Sigma_c~^-" },
+    1105             :       {       4214, "Sigma*_c^+" },
+    1106             :       {      -4214, "Sigma*_c~^-" },
+    1107             :       {       4222, "Sigma_c^++" },
+    1108             :       {      -4222, "Sigma_c~^--" },
+    1109             :       {       4224, "Sigma*_c^++" },
+    1110             :       {      -4224, "Sigma*_c~^--" },
+    1111             :       {       4232, "Xi_c^+" },
+    1112             :       {      -4232, "Xi_c~^-" },
+    1113             :       {       4312, "Xi'_c^0" },
+    1114             :       {      -4312, "Xi'_c~^0" },
+    1115             :       {       4314, "Xi*_c^0" },
+    1116             :       {      -4314, "Xi*_c~^0" },
+    1117             :       {       4322, "Xi'_c^+" },
+    1118             :       {      -4322, "Xi'_c~^-" },
+    1119             :       {       4324, "Xi*_c^+" },
+    1120             :       {      -4324, "Xi*_c~^-" },
+    1121             :       {       4332, "Omega_c^0" },
+    1122             :       {      -4332, "Omega_c~^0" },
+    1123             :       {       4334, "Omega*_c^0" },
+    1124             :       {      -4334, "Omega*_c~^0" },
+    1125             :       {       4412, "Xi_cc^+" },
+    1126             :       {      -4412, "Xi_cc~^-" },
+    1127             :       {       4414, "Xi*_cc^+" },
+    1128             :       {      -4414, "Xi*_cc~^-" },
+    1129             :       {       4422, "Xi_cc^++" },
+    1130             :       {      -4422, "Xi_cc~^--" },
+    1131             :       {       4424, "Xi*_cc^++" },
+    1132             :       {      -4424, "Xi*_cc~^--" },
+    1133             :       {       4432, "Omega_cc^+" },
+    1134             :       {      -4432, "Omega_cc~^-" },
+    1135             :       {       4434, "Omega*_cc^+" },
+    1136             :       {      -4434, "Omega*_cc~^-" },
+    1137             :       {       4444, "Omega*_ccc^++" },
+    1138             :       {      -4444, "Omega*_ccc~^--" },
+    1139             :       {       5112, "Sigma_b^-" },
+    1140             :       {      -5112, "Sigma_b~^+" },
+    1141             :       {       5114, "Sigma*_b^-" },
+    1142             :       {      -5114, "Sigma*_b~^+" },
+    1143             :       {       5122, "Lambda_b^0" },
+    1144             :       {      -5122, "Lambda_b~^0" },
+    1145             :       {       5132, "Xi_b^-" },
+    1146             :       {      -5132, "Xi_b~^+" },
+    1147             :       {       5142, "Xi_bc^0" },
+    1148             :       {      -5142, "Xi_bc~^0" },
+    1149             :       {       5212, "Sigma_b^0" },
+    1150             :       {      -5212, "Sigma_b~^0" },
+    1151             :       {       5214, "Sigma*_b^0" },
+    1152             :       {      -5214, "Sigma*_b~^0" },
+    1153             :       {       5222, "Sigma_b^+" },
+    1154             :       {      -5222, "Sigma_b~^-" },
+    1155             :       {       5224, "Sigma*_b^+" },
+    1156             :       {      -5224, "Sigma*_b~^-" },
+    1157             :       {       5232, "Xi_b^0" },
+    1158             :       {      -5232, "Xi_b~^0" },
+    1159             :       {       5242, "Xi_bc^+" },
+    1160             :       {      -5242, "Xi_bc~^-" },
+    1161             :       {       5312, "Xi'_b^-" },
+    1162             :       {      -5312, "Xi'_b~^+" },
+    1163             :       {       5314, "Xi*_b^-" },
+    1164             :       {      -5314, "Xi*_b~^+" },
+    1165             :       {       5322, "Xi'_b^0" },
+    1166             :       {      -5322, "Xi'_b~^0" },
+    1167             :       {       5324, "Xi*_b^0" },
+    1168             :       {      -5324, "Xi*_b~^0" },
+    1169             :       {       5332, "Omega_b^-" },
+    1170             :       {      -5332, "Omega_b~^+" },
+    1171             :       {       5334, "Omega*_b^-" },
+    1172             :       {      -5334, "Omega*_b~^+" },
+    1173             :       {       5342, "Omega_bc^0" },
+    1174             :       {      -5342, "Omega_bc~^0" },
+    1175             :       {       5412, "Xi'_bc^0" },
+    1176             :       {      -5412, "Xi'_bc~^0" },
+    1177             :       {       5414, "Xi*_bc^0" },
+    1178             :       {      -5414, "Xi*_bc~^0" },
+    1179             :       {       5422, "Xi'_bc^+" },
+    1180             :       {      -5422, "Xi'_bc~^-" },
+    1181             :       {       5424, "Xi*_bc^+" },
+    1182             :       {      -5424, "Xi*_bc~^-" },
+    1183             :       {       5432, "Omega'_bc^0" },
+    1184             :       {      -5432, "Omega'_bc~^0" },
+    1185             :       {       5434, "Omega*_bc^0" },
+    1186             :       {      -5434, "Omega*_bc~^0" },
+    1187             :       {       5442, "Omega_bcc^+" },
+    1188             :       {      -5442, "Omega_bcc~^-" },
+    1189             :       {       5444, "Omega*_bcc^+" },
+    1190             :       {      -5444, "Omega*_bcc~^-" },
+    1191             :       {       5512, "Xi_bb^-" },
+    1192             :       {      -5512, "Xi_bb~^+" },
+    1193             :       {       5514, "Xi*_bb^-" },
+    1194             :       {      -5514, "Xi*_bb~^+" },
+    1195             :       {       5522, "Xi_bb^0" },
+    1196             :       {      -5522, "Xi_bb~^0" },
+    1197             :       {       5524, "Xi*_bb^0" },
+    1198             :       {      -5524, "Xi*_bb~^0" },
+    1199             :       {       5532, "Omega_bb^-" },
+    1200             :       {      -5532, "Omega_bb~^+" },
+    1201             :       {       5534, "Omega*_bb^-" },
+    1202             :       {      -5534, "Omega*_bb~^+" },
+    1203             :       {       5542, "Omega_bbc^0" },
+    1204             :       {      -5542, "Omega_bbc~^0" },
+    1205             :       {       5544, "Omega*_bbc^0" },
+    1206             :       {      -5544, "Omega*_bbc~^0" },
+    1207             :       {       5554, "Omega*_bbb^-" },
+    1208             :       {      -5554, "Omega*_bbb~^+" },
+    1209             :       {       6112, "Sigma_t^0" },
+    1210             :       {      -6112, "Sigma_t~^0" },
+    1211             :       {       6114, "Sigma*_t^0" },
+    1212             :       {      -6114, "Sigma*_t~^0" },
+    1213             :       {       6122, "Lambda_t^+" },
+    1214             :       {      -6122, "Lambda_t~^-" },
+    1215             :       {       6132, "Xi_t^0" },
+    1216             :       {      -6132, "Xi_t~^0" },
+    1217             :       {       6142, "Xi_tc^+" },
+    1218             :       {      -6142, "Xi_tc~^-" },
+    1219             :       {       6152, "Xi_tb^0" },
+    1220             :       {      -6152, "Xi_tb~^0" },
+    1221             :       {       6212, "Sigma_t^+" },
+    1222             :       {      -6212, "Sigma_t~^-" },
+    1223             :       {       6214, "Sigma*_t^+" },
+    1224             :       {      -6214, "Sigma*_t~^-" },
+    1225             :       {       6222, "Sigma_t^++" },
+    1226             :       {      -6222, "Sigma_t~^--" },
+    1227             :       {       6224, "Sigma*_t^++" },
+    1228             :       {      -6224, "Sigma*_t~^--" },
+    1229             :       {       6232, "Xi_t^+" },
+    1230             :       {      -6232, "Xi_t~^-" },
+    1231             :       {       6242, "Xi_tc^++" },
+    1232             :       {      -6242, "Xi_tc~^--" },
+    1233             :       {       6252, "Xi_tb^+" },
+    1234             :       {      -6252, "Xi_tb~^-" },
+    1235             :       {       6312, "Xi'_t^0" },
+    1236             :       {      -6312, "Xi'_t~^0" },
+    1237             :       {       6314, "Xi*_t^0" },
+    1238             :       {      -6314, "Xi*_t~^0" },
+    1239             :       {       6322, "Xi'_t^+" },
+    1240             :       {      -6322, "Xi'_t~^-" },
+    1241             :       {       6324, "Xi*_t^+" },
+    1242             :       {      -6324, "Xi*_t~^-" },
+    1243             :       {       6332, "Omega_t^0" },
+    1244             :       {      -6332, "Omega_t~^0" },
+    1245             :       {       6334, "Omega*_t^0" },
+    1246             :       {      -6334, "Omega*_t~^0" },
+    1247             :       {       6342, "Omega_tc^+" },
+    1248             :       {      -6342, "Omega_tc~^-" },
+    1249             :       {       6352, "Omega_tb^0" },
+    1250             :       {      -6352, "Omega_tb~^0" },
+    1251             :       {       6412, "Xi'_tc^+" },
+    1252             :       {      -6412, "Xi'_tc~^-" },
+    1253             :       {       6414, "Xi*_tc^+" },
+    1254             :       {      -6414, "Xi*_tc~^-" },
+    1255             :       {       6422, "Xi'_tc^++" },
+    1256             :       {      -6422, "Xi'_tc~^--" },
+    1257             :       {       6424, "Xi*_tc^++" },
+    1258             :       {      -6424, "Xi*_tc~^--" },
+    1259             :       {       6432, "Omega'_tc^+" },
+    1260             :       {      -6432, "Omega'_tc~^-" },
+    1261             :       {       6434, "Omega*_tc^+" },
+    1262             :       {      -6434, "Omega*_tc~^-" },
+    1263             :       {       6442, "Omega_tcc^++" },
+    1264             :       {      -6442, "Omega_tcc~^--" },
+    1265             :       {       6444, "Omega*_tcc^++" },
+    1266             :       {      -6444, "Omega*_tcc~^--" },
+    1267             :       {       6452, "Omega_tbc^+" },
+    1268             :       {      -6452, "Omega_tbc~^-" },
+    1269             :       {       6512, "Xi'_tb^0" },
+    1270             :       {      -6512, "Xi'_tb~^0" },
+    1271             :       {       6514, "Xi*_tb^0" },
+    1272             :       {      -6514, "Xi*_tb~^0" },
+    1273             :       {       6522, "Xi'_tb^+" },
+    1274             :       {      -6522, "Xi'_tb~^-" },
+    1275             :       {       6524, "Xi*_tb^+" },
+    1276             :       {      -6524, "Xi*_tb~^-" },
+    1277             :       {       6532, "Omega'_tb^0" },
+    1278             :       {      -6532, "Omega'_tb~^0" },
+    1279             :       {       6534, "Omega*_tb^0" },
+    1280             :       {      -6534, "Omega*_tb~^0" },
+    1281             :       {       6542, "Omega'_tbc^+" },
+    1282             :       {      -6542, "Omega'_tbc~^-" },
+    1283             :       {       6544, "Omega*_tbc^+" },
+    1284             :       {      -6544, "Omega*_tbc~^-" },
+    1285             :       {       6552, "Omega_tbb^0" },
+    1286             :       {      -6552, "Omega_tbb~^0" },
+    1287             :       {       6554, "Omega*_tbb^0" },
+    1288             :       {      -6554, "Omega*_tbb~^0" },
+    1289             :       {       6612, "Xi_tt^+" },
+    1290             :       {      -6612, "Xi_tt~^-" },
+    1291             :       {       6614, "Xi*_tt^+" },
+    1292             :       {      -6614, "Xi*_tt~^-" },
+    1293             :       {       6622, "Xi_tt^++" },
+    1294             :       {      -6622, "Xi_tt~^--" },
+    1295             :       {       6624, "Xi*_tt^++" },
+    1296             :       {      -6624, "Xi*_tt~^--" },
+    1297             :       {       6632, "Omega_tt^+" },
+    1298             :       {      -6632, "Omega_tt~^-" },
+    1299             :       {       6634, "Omega*_tt^+" },
+    1300             :       {      -6634, "Omega*_tt~^-" },
+    1301             :       {       6642, "Omega_ttc^++" },
+    1302             :       {      -6642, "Omega_ttc~^--" },
+    1303             :       {       6644, "Omega*_ttc^++" },
+    1304             :       {      -6644, "Omega*_ttc~^--" },
+    1305             :       {       6652, "Omega_ttb^+" },
+    1306             :       {      -6652, "Omega_ttb~^-" },
+    1307             :       {       6654, "Omega*_ttb^+" },
+    1308             :       {      -6654, "Omega*_ttb~^-" },
+    1309             :       {       6664, "Omega*_ttt^++" },
+    1310             :       {      -6664, "Omega*_ttt~^--" },
+    1311             :       {       7112, "Sigma_b'^-" },
+    1312             :       {      -7112, "Sigma_b'~^+" },
+    1313             :       {       7114, "Sigma*_b'^-" },
+    1314             :       {      -7114, "Sigma*_b'~^+" },
+    1315             :       {       7122, "Lambda_b'^0" },
+    1316             :       {      -7122, "Lambda_b'~^0" },
+    1317             :       {       7132, "Xi_b'^-" },
+    1318             :       {      -7132, "Xi_b'~^+" },
+    1319             :       {       7142, "Xi_b'c^0" },
+    1320             :       {      -7142, "Xi_b'c~^0" },
+    1321             :       {       7152, "Xi_b'b^-" },
+    1322             :       {      -7152, "Xi_b'b~^+" },
+    1323             :       {       7162, "Xi_b't^0" },
+    1324             :       {      -7162, "Xi_b't~^0" },
+    1325             :       {       7212, "Sigma_b'^0" },
+    1326             :       {      -7212, "Sigma_b'~^0" },
+    1327             :       {       7214, "Sigma*_b'^0" },
+    1328             :       {      -7214, "Sigma*_b'~^0" },
+    1329             :       {       7222, "Sigma_b'^+" },
+    1330             :       {      -7222, "Sigma_b'~^-" },
+    1331             :       {       7224, "Sigma*_b'^+" },
+    1332             :       {      -7224, "Sigma*_b'~^-" },
+    1333             :       {       7232, "Xi_b'^0" },
+    1334             :       {      -7232, "Xi_b'~^0" },
+    1335             :       {       7242, "Xi_b'c^+" },
+    1336             :       {      -7242, "Xi_b'c~^-" },
+    1337             :       {       7252, "Xi_b'b^0" },
+    1338             :       {      -7252, "Xi_b'b~^0" },
+    1339             :       {       7262, "Xi_b't^+" },
+    1340             :       {      -7262, "Xi_b't~^-" },
+    1341             :       {       7312, "Xi'_b'^-" },
+    1342             :       {      -7312, "Xi'_b'~^+" },
+    1343             :       {       7314, "Xi*_b'^-" },
+    1344             :       {      -7314, "Xi*_b'~^+" },
+    1345             :       {       7322, "Xi'_b'^0" },
+    1346             :       {      -7322, "Xi'_b'~^0" },
+    1347             :       {       7324, "Xi*_b'^0" },
+    1348             :       {      -7324, "Xi*_b'~^0" },
+    1349             :       {       7332, "Omega'_b'^-" },
+    1350             :       {      -7332, "Omega'_b'~^+" },
+    1351             :       {       7334, "Omega*_b'^-" },
+    1352             :       {      -7334, "Omega*_b'~^+" },
+    1353             :       {       7342, "Omega_b'c^0" },
+    1354             :       {      -7342, "Omega_b'c~^0" },
+    1355             :       {       7352, "Omega_b'b^-" },
+    1356             :       {      -7352, "Omega_b'b~^+" },
+    1357             :       {       7362, "Omega_b't^0" },
+    1358             :       {      -7362, "Omega_b't~^0" },
+    1359             :       {       7412, "Xi'_b'c^0" },
+    1360             :       {      -7412, "Xi'_b'c~^0" },
+    1361             :       {       7414, "Xi*_b'c^0" },
+    1362             :       {      -7414, "Xi*_b'c~^0" },
+    1363             :       {       7422, "Xi'_b'c^+" },
+    1364             :       {      -7422, "Xi'_b'c~^-" },
+    1365             :       {       7424, "Xi*_b'c^+" },
+    1366             :       {      -7424, "Xi*_b'c~^-" },
+    1367             :       {       7432, "Omega'_b'c^0" },
+    1368             :       {      -7432, "Omega'_b'c~^0" },
+    1369             :       {       7434, "Omega*_b'c^0" },
+    1370             :       {      -7434, "Omega*_b'c~^0" },
+    1371             :       {       7442, "Omega'_b'cc^+" },
+    1372             :       {      -7442, "Omega'_b'cc~^-" },
+    1373             :       {       7444, "Omega*_b'cc^+" },
+    1374             :       {      -7444, "Omega*_b'cc~^-" },
+    1375             :       {       7452, "Omega_b'bc^0" },
+    1376             :       {      -7452, "Omega_b'bc~^0" },
+    1377             :       {       7462, "Omega_b'tc^+" },
+    1378             :       {      -7462, "Omega_b'tc~^-" },
+    1379             :       {       7512, "Xi'_b'b^-" },
+    1380             :       {      -7512, "Xi'_b'b~^+" },
+    1381             :       {       7514, "Xi*_b'b^-" },
+    1382             :       {      -7514, "Xi*_b'b~^+" },
+    1383             :       {       7522, "Xi'_b'b^0" },
+    1384             :       {      -7522, "Xi'_b'b~^0" },
+    1385             :       {       7524, "Xi*_b'b^0" },
+    1386             :       {      -7524, "Xi*_b'b~^0" },
+    1387             :       {       7532, "Omega'_b'b^-" },
+    1388             :       {      -7532, "Omega'_b'b~^+" },
+    1389             :       {       7534, "Omega*_b'b^-" },
+    1390             :       {      -7534, "Omega*_b'b~^+" },
+    1391             :       {       7542, "Omega'_b'bc^0" },
+    1392             :       {      -7542, "Omega'_b'bc~^0" },
+    1393             :       {       7544, "Omega*_b'bc^0" },
+    1394             :       {      -7544, "Omega*_b'bc~^0" },
+    1395             :       {       7552, "Omega'_b'bb^-" },
+    1396             :       {      -7552, "Omega'_b'bb~^+" },
+    1397             :       {       7554, "Omega*_b'bb^-" },
+    1398             :       {      -7554, "Omega*_b'bb~^+" },
+    1399             :       {       7562, "Omega_b'tb^0" },
+    1400             :       {      -7562, "Omega_b'tb~^0" },
+    1401             :       {       7612, "Xi'_b't^0" },
+    1402             :       {      -7612, "Xi'_b't~^0" },
+    1403             :       {       7614, "Xi*_b't^0" },
+    1404             :       {      -7614, "Xi*_b't~^0" },
+    1405             :       {       7622, "Xi'_b't^+" },
+    1406             :       {      -7622, "Xi'_b't~^-" },
+    1407             :       {       7624, "Xi*_b't^+" },
+    1408             :       {      -7624, "Xi*_b't~^-" },
+    1409             :       {       7632, "Omega'_b't^0" },
+    1410             :       {      -7632, "Omega'_b't~^0" },
+    1411             :       {       7634, "Omega*_b't^0" },
+    1412             :       {      -7634, "Omega*_b't~^0" },
+    1413             :       {       7642, "Omega'_b'tc^+" },
+    1414             :       {      -7642, "Omega'_b'tc~^-" },
+    1415             :       {       7644, "Omega*_b'tc^+" },
+    1416             :       {      -7644, "Omega*_b'tc~^-" },
+    1417             :       {       7652, "Omega'_b'tb^0" },
+    1418             :       {      -7652, "Omega'_b'tb~^0" },
+    1419             :       {       7654, "Omega*_b'tb^0" },
+    1420             :       {      -7654, "Omega*_b'tb~^0" },
+    1421             :       {       7662, "Omega'_b'tt^+" },
+    1422             :       {      -7662, "Omega'_b'tt~^-" },
+    1423             :       {       7664, "Omega*_b'tt^+" },
+    1424             :       {      -7664, "Omega*_b'tt~^-" },
+    1425             :       {       7712, "Xi'_b'b'^-" },
+    1426             :       {      -7712, "Xi'_b'b'~^+" },
+    1427             :       {       7714, "Xi*_b'b'^-" },
+    1428             :       {      -7714, "Xi*_b'b'~^+" },
+    1429             :       {       7722, "Xi'_b'b'^0" },
+    1430             :       {      -7722, "Xi'_b'b'~^0" },
+    1431             :       {       7724, "Xi*_b'b'^0" },
+    1432             :       {      -7724, "Xi*_b'b'~^0" },
+    1433             :       {       7732, "Omega'_b'b'^-" },
+    1434             :       {      -7732, "Omega'_b'b'~^+" },
+    1435             :       {       7734, "Omega*_b'b'^-" },
+    1436             :       {      -7734, "Omega*_b'b'~^+" },
+    1437             :       {       7742, "Omega'_b'b'c^0" },
+    1438             :       {      -7742, "Omega'_b'b'c~^0" },
+    1439             :       {       7744, "Omega*_b'b'c^0" },
+    1440             :       {      -7744, "Omega*_b'b'c~^0" },
+    1441             :       {       7752, "Omega'_b'b'b^-" },
+    1442             :       {      -7752, "Omega'_b'b'b~^+" },
+    1443             :       {       7754, "Omega*_b'b'b^-" },
+    1444             :       {      -7754, "Omega*_b'b'b~^+" },
+    1445             :       {       7762, "Omega'_b'b't^0" },
+    1446             :       {      -7762, "Omega'_b'b't~^0" },
+    1447             :       {       7764, "Omega*_b'b't^0" },
+    1448             :       {      -7764, "Omega*_b'b't~^0" },
+    1449             :       {       7774, "Omega*_b'b'b'^-" },
+    1450             :       {      -7774, "Omega*_b'b'b'~^+" },
+    1451             :       {       8112, "Sigma_t'^0" },
+    1452             :       {      -8112, "Sigma_t'~^0" },
+    1453             :       {       8114, "Sigma*_t'^0" },
+    1454             :       {      -8114, "Sigma*_t'~^0" },
+    1455             :       {       8122, "Lambda_t'^+" },
+    1456             :       {      -8122, "Lambda_t'~^-" },
+    1457             :       {       8132, "Xi_t'^0" },
+    1458             :       {      -8132, "Xi_t'~^0" },
+    1459             :       {       8142, "Xi_t'c^+" },
+    1460             :       {      -8142, "Xi_t'c~^-" },
+    1461             :       {       8152, "Xi_t'b^0" },
+    1462             :       {      -8152, "Xi_t'b~^0" },
+    1463             :       {       8162, "Xi_t't^+" },
+    1464             :       {      -8162, "Xi_t't~^-" },
+    1465             :       {       8172, "Xi_t'b'^0" },
+    1466             :       {      -8172, "Xi_t'b'~^0" },
+    1467             :       {       8212, "Sigma_t'^+" },
+    1468             :       {      -8212, "Sigma_t'~^-" },
+    1469             :       {       8214, "Sigma*_t'^+" },
+    1470             :       {      -8214, "Sigma*_t'~^-" },
+    1471             :       {       8222, "Sigma_t'^++" },
+    1472             :       {      -8222, "Sigma_t'~^--" },
+    1473             :       {       8224, "Sigma*_t'^++" },
+    1474             :       {      -8224, "Sigma*_t'~^--" },
+    1475             :       {       8232, "Xi_t'^+" },
+    1476             :       {      -8232, "Xi_t'~^-" },
+    1477             :       {       8242, "Xi_t'c^++" },
+    1478             :       {      -8242, "Xi_t'c~^--" },
+    1479             :       {       8252, "Xi_t'b^+" },
+    1480             :       {      -8252, "Xi_t'b~^-" },
+    1481             :       {       8262, "Xi_t't^++" },
+    1482             :       {      -8262, "Xi_t't~^--" },
+    1483             :       {       8272, "Xi_t'b'^+" },
+    1484             :       {      -8272, "Xi_t'b'~^-" },
+    1485             :       {       8312, "Xi'_t'^0" },
+    1486             :       {      -8312, "Xi'_t'~^0" },
+    1487             :       {       8314, "Xi*_t'^0" },
+    1488             :       {      -8314, "Xi*_t'~^0" },
+    1489             :       {       8322, "Xi'_t'^+" },
+    1490             :       {      -8322, "Xi'_t'~^-" },
+    1491             :       {       8324, "Xi*_t'^+" },
+    1492             :       {      -8324, "Xi*_t'~^-" },
+    1493             :       {       8332, "Omega'_t'^0" },
+    1494             :       {      -8332, "Omega'_t'~^0" },
+    1495             :       {       8334, "Omega*_t'^0" },
+    1496             :       {      -8334, "Omega*_t'~^0" },
+    1497             :       {       8342, "Omega_t'c^+" },
+    1498             :       {      -8342, "Omega_t'c~^-" },
+    1499             :       {       8352, "Omega_t'b^0" },
+    1500             :       {      -8352, "Omega_t'b~^0" },
+    1501             :       {       8362, "Omega_t't^+" },
+    1502             :       {      -8362, "Omega_t't~^-" },
+    1503             :       {       8372, "Omega_t'b'^0" },
+    1504             :       {      -8372, "Omega_t'b'~^0" },
+    1505             :       {       8412, "Xi'_t'c^+" },
+    1506             :       {      -8412, "Xi'_t'c~^-" },
+    1507             :       {       8414, "Xi*_t'c^+" },
+    1508             :       {      -8414, "Xi*_t'c~^-" },
+    1509             :       {       8422, "Xi'_t'c^++" },
+    1510             :       {      -8422, "Xi'_t'c~^--" },
+    1511             :       {       8424, "Xi*_t'c^++" },
+    1512             :       {      -8424, "Xi*_t'c~^--" },
+    1513             :       {       8432, "Omega'_t'c^+" },
+    1514             :       {      -8432, "Omega'_t'c~^-" },
+    1515             :       {       8434, "Omega*_t'c^+" },
+    1516             :       {      -8434, "Omega*_t'c~^-" },
+    1517             :       {       8442, "Omega'_t'cc^++" },
+    1518             :       {      -8442, "Omega'_t'cc~^--" },
+    1519             :       {       8444, "Omega*_t'cc^++" },
+    1520             :       {      -8444, "Omega*_t'cc~^--" },
+    1521             :       {       8452, "Omega_t'bc^+" },
+    1522             :       {      -8452, "Omega_t'bc~^-" },
+    1523             :       {       8462, "Omega_t'tc^++" },
+    1524             :       {      -8462, "Omega_t'tc~^--" },
+    1525             :       {       8472, "Omega_t'b'c ^+" },
+    1526             :       {      -8472, "Omega_t'b'c ~^-" },
+    1527             :       {       8512, "Xi'_t'b^0" },
+    1528             :       {      -8512, "Xi'_t'b~^0" },
+    1529             :       {       8514, "Xi*_t'b^0" },
+    1530             :       {      -8514, "Xi*_t'b~^0" },
+    1531             :       {       8522, "Xi'_t'b^+" },
+    1532             :       {      -8522, "Xi'_t'b~^-" },
+    1533             :       {       8524, "Xi*_t'b^+" },
+    1534             :       {      -8524, "Xi*_t'b~^-" },
+    1535             :       {       8532, "Omega'_t'b^0" },
+    1536             :       {      -8532, "Omega'_t'b~^0" },
+    1537             :       {       8534, "Omega*_t'b^0" },
+    1538             :       {      -8534, "Omega*_t'b~^0" },
+    1539             :       {       8542, "Omega'_t'bc^+" },
+    1540             :       {      -8542, "Omega'_t'bc~^-" },
+    1541             :       {       8544, "Omega*_t'bc^+" },
+    1542             :       {      -8544, "Omega*_t'bc~^-" },
+    1543             :       {       8552, "Omega'_t'bb^0" },
+    1544             :       {      -8552, "Omega'_t'bb~^0" },
+    1545             :       {       8554, "Omega*_t'bb^0" },
+    1546             :       {      -8554, "Omega*_t'bb~^0" },
+    1547             :       {       8562, "Omega_t'tb^+" },
+    1548             :       {      -8562, "Omega_t'tb~^-" },
+    1549             :       {       8572, "Omega_t'b'b ^0" },
+    1550             :       {      -8572, "Omega_t'b'b ~^0" },
+    1551             :       {       8612, "Xi'_t't^+" },
+    1552             :       {      -8612, "Xi'_t't~^-" },
+    1553             :       {       8614, "Xi*_t't^+" },
+    1554             :       {      -8614, "Xi*_t't~^-" },
+    1555             :       {       8622, "Xi'_t't^++" },
+    1556             :       {      -8622, "Xi'_t't~^--" },
+    1557             :       {       8624, "Xi*_t't^++" },
+    1558             :       {      -8624, "Xi*_t't~^--" },
+    1559             :       {       8632, "Omega'_t't^+" },
+    1560             :       {      -8632, "Omega'_t't~^-" },
+    1561             :       {       8634, "Omega*_t't^+" },
+    1562             :       {      -8634, "Omega*_t't~^-" },
+    1563             :       {       8642, "Omega'_t'tc^++" },
+    1564             :       {      -8642, "Omega'_t'tc~^--" },
+    1565             :       {       8644, "Omega*_t'tc^++" },
+    1566             :       {      -8644, "Omega*_t'tc~^--" },
+    1567             :       {       8652, "Omega'_t'tb^+" },
+    1568             :       {      -8652, "Omega'_t'tb~^-" },
+    1569             :       {       8654, "Omega*_t'tb^+" },
+    1570             :       {      -8654, "Omega*_t'tb~^-" },
+    1571             :       {       8662, "Omega'_t'tt^++" },
+    1572             :       {      -8662, "Omega'_t'tt~^--" },
+    1573             :       {       8664, "Omega*_t'tt^++" },
+    1574             :       {      -8664, "Omega*_t'tt~^--" },
+    1575             :       {       8672, "Omega_t'b't ^+" },
+    1576             :       {      -8672, "Omega_t'b't ~^-" },
+    1577             :       {       8712, "Xi'_t'b'^0" },
+    1578             :       {      -8712, "Xi'_t'b'~^0" },
+    1579             :       {       8714, "Xi*_t'b'^0" },
+    1580             :       {      -8714, "Xi*_t'b'~^0" },
+    1581             :       {       8722, "Xi'_t'b'^+" },
+    1582             :       {      -8722, "Xi'_t'b'~^-" },
+    1583             :       {       8724, "Xi*_t'b'^+" },
+    1584             :       {      -8724, "Xi*_t'b'~^-" },
+    1585             :       {       8732, "Omega'_t'b'^0" },
+    1586             :       {      -8732, "Omega'_t'b'~^0" },
+    1587             :       {       8734, "Omega*_t'b'^0" },
+    1588             :       {      -8734, "Omega*_t'b'~^0" },
+    1589             :       {       8742, "Omega'_t'b'c^+" },
+    1590             :       {      -8742, "Omega'_t'b'c~^-" },
+    1591             :       {       8744, "Omega*_t'b'c^+" },
+    1592             :       {      -8744, "Omega*_t'b'c~^-" },
+    1593             :       {       8752, "Omega'_t'b'b^0" },
+    1594             :       {      -8752, "Omega'_t'b'b~^0" },
+    1595             :       {       8754, "Omega*_t'b'b^0" },
+    1596             :       {      -8754, "Omega*_t'b'b~^0" },
+    1597             :       {       8762, "Omega'_t'b't^+" },
+    1598             :       {      -8762, "Omega'_t'b't~^-" },
+    1599             :       {       8764, "Omega*_t'b't^+" },
+    1600             :       {      -8764, "Omega*_t'b't~^-" },
+    1601             :       {       8772, "Omega'_t'b'b'^0" },
+    1602             :       {      -8772, "Omega'_t'b'b'~^0" },
+    1603             :       {       8774, "Omega*_t'b'b'^0" },
+    1604             :       {      -8774, "Omega*_t'b'b'~^0" },
+    1605             :       {       8812, "Xi'_t't'^+" },
+    1606             :       {      -8812, "Xi'_t't'~^-" },
+    1607             :       {       8814, "Xi*_t't'^+" },
+    1608             :       {      -8814, "Xi*_t't'~^-" },
+    1609             :       {       8822, "Xi'_t't'^++" },
+    1610             :       {      -8822, "Xi'_t't'~^--" },
+    1611             :       {       8824, "Xi*_t't'^++" },
+    1612             :       {      -8824, "Xi*_t't'~^--" },
+    1613             :       {       8832, "Omega'_t't'^+" },
+    1614             :       {      -8832, "Omega'_t't'~^-" },
+    1615             :       {       8834, "Omega*_t't'^+" },
+    1616             :       {      -8834, "Omega*_t't'~^-" },
+    1617             :       {       8842, "Omega'_t't'c^++" },
+    1618             :       {      -8842, "Omega'_t't'c~^--" },
+    1619             :       {       8844, "Omega*_t't'c^++" },
+    1620             :       {      -8844, "Omega*_t't'c~^--" },
+    1621             :       {       8852, "Omega'_t't'b^+" },
+    1622             :       {      -8852, "Omega'_t't'b~^-" },
+    1623             :       {       8854, "Omega*_t't'b^+" },
+    1624             :       {      -8854, "Omega*_t't'b~^-" },
+    1625             :       {       8862, "Omega'_t't't^++" },
+    1626             :       {      -8862, "Omega'_t't't~^--" },
+    1627             :       {       8864, "Omega*_t't't^++" },
+    1628             :       {      -8864, "Omega*_t't't~^--" },
+    1629             :       {       8872, "Omega'_t't'b'^+" },
+    1630             :       {      -8872, "Omega'_t't'b'~^-" },
+    1631             :       {       8874, "Omega*_t't'b'^+" },
+    1632             :       {      -8874, "Omega*_t't'b'~^-" },
+    1633             :       {       8884, "Omega*_t't't'^++" },
+    1634             :       {      -8884, "Omega*_t't't'~^--" },
+    1635             :       {    9221132, "Theta^+" },
+    1636             :       {    9331122, "Phi^--" },
+    1637             :       {    1000993, "R_~gg^0" },
+    1638             :       {    1009113, "R_~gd~d^0" },
+    1639             :       {    1009213, "R_~gu~d^+" },
+    1640             :       {    1009223, "R_~gu~u^0" },
+    1641             :       {    1009313, "R_~gd~s^0" },
+    1642             :       {    1009323, "R_~gu~s^+" },
+    1643             :       {    1009333, "R_~gs~s^0" },
+    1644             :       {    1091114, "R_~gddd^-" },
+    1645             :       {    1092114, "R_~gudd^0" },
+    1646             :       {    1092214, "R_~guud^+" },
+    1647             :       {    1092224, "R_~guuu^++" },
+    1648             :       {    1093114, "R_~gsdd^-" },
+    1649             :       {    1093214, "R_~gsud^0" },
+    1650             :       {    1093224, "R_~gsuu^+" },
+    1651             :       {    1093314, "R_~gssd^-" },
+    1652             :       {    1093324, "R_~gssu^0" },
+    1653             :       {    1093334, "R_~gsss^-" },
+    1654             :       {    1000612, "R_~t_1~d^+" },
+    1655             :       {    1000622, "R_~t_1~u^0" },
+    1656             :       {    1000632, "R_~t_1~s^+" },
+    1657             :       {    1000642, "R_~t_1~c^0" },
+    1658             :       {    1000652, "R_~t_1~b^+" },
+    1659             :       {    1006113, "R_~t_1dd_1^0" },
+    1660             :       {    1006211, "R_~t_1ud_0^+" },
+    1661             :       {    1006213, "R_~t_1ud_1^+" },
+    1662             :       {    1006223, "R_~t_1uu_1^++" },
+    1663             :       {    1006311, "R_~t_1sd_0^0" },
+    1664             :       {    1006313, "R_~t_1sd_1^0" },
+    1665             :       {    1006321, "R_~t_1su_0^+" },
+    1666             :       {    1006323, "R_~t_1su_1^+" },
+    1667             :       {    1006333, "R_~t_1ss_1^0" },
+    1668             :       { 1000010010, "Hydrogen" },
+    1669             :       { 1000010020, "Deuterium" },
+    1670             :       {-1000010020, "Anti-Deuterium" },
+    1671             :       { 1000010030, "Tritium" },
+    1672             :       {-1000010030, "Anti-Tritium" },
+    1673             :       { 1000020030, "He3" },
+    1674             :       {-1000020030, "Anti-He3" },
+    1675             :       { 1000020040, "Alpha-(He4)" },
+    1676             :       {-1000020040, "Anti-Alpha-(He4)" }
+    1677             :   };
+    1678             : 
+    1679             :   int lnames = sizeof(SNames)/sizeof(SNames[0]);
+    1680           0 :   for( int k=0; k!=lnames; ++k) {
+    1681           0 :       m.insert( std::make_pair( SNames[k].pid, std::string(SNames[k].pname)) );
+    1682           0 :       nameMap.insert( std::make_pair( std::string(SNames[k].pname), SNames[k].pid ) );
+    1683             :   }
+    1684           0 :   static ParticleNameMap mymaps(m,nameMap);
+    1685             : 
+    1686           0 :   return mymaps;
+    1687             : }  // ParticleNameInit()
+    1688             : 
+    1689           0 : void writeParticleNameLine( int i, std::ostream & os  )
+    1690             : {
+    1691           0 :     if ( validParticleName( i ) ) {
+    1692           0 :         std::string pn = particleName( i );
+    1693           0 :         int pid = particleName( pn );
+    1694           0 :         os << " PDT number: " ;
+    1695           0 :         os.width(12);
+    1696           0 :         os << i << " PDT name: " << pn << std::endl;
+    1697             :         // verify reverse lookup
+    1698           0 :         if( pid != i ) {
+    1699             :             os << "HepPID::writeParticleNameLine ERROR: "
+    1700           0 :                << " got " << pid << " instead of " << i << std::endl;
+    1701             :         }
+    1702             :     }
+    1703           0 :     return;
+    1704             : }  // writeParticleNameLine()
+    1705             : 
+    1706           0 : std::string dyonName( const int & pid )
+    1707             : {
+    1708           0 :     std::ostringstream pn;
+    1709           0 :     pn << "Dyon^" << digit(nq1,pid) << digit(nq2,pid) << digit(nq3,pid);
+    1710           0 :     if ( digit(nl,pid) == 1 ) {
+    1711           0 :        if ( pid > 0 ) {
+    1712           0 :           pn << "++";
+    1713             :        } else {
+    1714           0 :           pn << "--";
+    1715             :        }
+    1716           0 :     } else if ( digit(nl,pid) == 2 ) {
+    1717           0 :        if ( pid > 0 ) {
+    1718           0 :           pn << "+-";
+    1719             :        } else {
+    1720           0 :           pn << "-+";
+    1721             :        }
+    1722             :     }
+    1723           0 :     return pn.str();
+    1724           0 : }
+    1725             : 
+    1726           0 : std::string qballName( const int & pid )
+    1727             : {
+    1728           0 :     std::ostringstream pn;
+    1729           0 :     pn << "QBall^" << ((abspid(pid)/100)%1000) << "." << digit(nq3,pid);
+    1730           0 :     if ( pid > 0 ) {
+    1731           0 :        pn << "+";
+    1732             :     } else {
+    1733           0 :        pn << "-";
+    1734             :     }
+    1735           0 :     return pn.str();
+    1736           0 : }
+    1737             : 
+    1738           0 : int  checkForSpecialParticle( const std::string & s )
+    1739             : {
+    1740             :     int chg, chg2, id;
+    1741             :     int m = 1;
+    1742           0 :     int len = s.length();
+    1743           0 :     if( s.substr(0,4) == "Dyon" ) {
+    1744           0 :        std::istringstream var1(s.substr(5,3).c_str());
+    1745           0 :        var1 >> chg;
+    1746           0 :        if( s.substr(len-2,1) == "+" && s.substr(len-1,1) == "-") m = 2;
+    1747           0 :        if( s.substr(len-2,1) == "-" && s.substr(len-1,1) == "+") m = 2;
+    1748           0 :        id = 4100000 + m*10000 + chg*10;
+    1749           0 :        if( s.substr(len-2,1) == "-" ) id = -id;
+    1750             :        return id;
+    1751           0 :     }
+    1752           0 :     if( s.substr(0,5) == "QBall" ) {
+    1753           0 :        int rem = len - 9;
+    1754           0 :        std::istringstream var2(s.substr(6,rem).c_str());
+    1755           0 :        var2 >> chg;
+    1756           0 :        std::istringstream var3(s.substr(7+rem,1).c_str());
+    1757           0 :        var3 >> chg2;
+    1758           0 :        id = 10000000 + chg*100+chg2*10;
+    1759           0 :        if( s.substr(len-1,1) == "-" ) id = -id;
+    1760             :        return id;
+    1761           0 :     }
+    1762             :     return 0;
+    1763             : }
+    1764             : 
+    1765             : } // unnamed namespace
+    1766             : 
+    1767             : //
+    1768             : // getPartcleIdMap is the ONLY function allowed to call ParticleNameInit
+    1769             : //
+    1770           0 : ParticleNameMap const &  getParticleNameMap()
+    1771             : {
+    1772           0 :   static  ParticleNameMap const &  pmap = ParticleNameInit();
+    1773           0 :   return pmap;
+    1774             : }  // getPartcleIdMap()
+    1775             : 
+    1776           0 : bool validParticleName( const int & pid )
+    1777             : {
+    1778             :     // check for the special cases first
+    1779           0 :     if ( isDyon(pid) ) return true;
+    1780           0 :     if ( isQBall(pid) ) return true;
+    1781             :     
+    1782           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
+    1783             : 
+    1784           0 :     ParticleNameMap::idIterator const cit = pmap.find( pid );
+    1785             :     return ( cit == pmap.end() )
+    1786           0 :          ? false
+    1787             :          : true;
+    1788             : }  // validParticleName()
+    1789             : 
+    1790           0 : bool validParticleName( const std::string & s )
+    1791             : {
+    1792           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
+    1793           0 :     ParticleNameMap::nameIterator const cit = pmap.findString( s );
+    1794             :     return ( cit == pmap.endLookupMap() )
+    1795           0 :          ? false
+    1796           0 :          : true;
+    1797             : }  // validParticleName()
+    1798             : 
+    1799           0 : std::string  particleName( const int & pid )
+    1800             : {
+    1801             :     // check for the special cases first
+    1802           0 :     if ( isDyon(pid) ) return dyonName(pid);
+    1803           0 :     if ( isQBall(pid) ) return qballName(pid);
+    1804             :     
+    1805           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
+    1806             : 
+    1807           0 :     ParticleNameMap::idIterator const cit = pmap.find( pid );
+    1808             :     return ( cit == pmap.end() )
+    1809             :          ? std::string("not defined")
+    1810           0 :          : cit->second;
+    1811             : }  // particleName()
+    1812             : 
+    1813           0 : int  particleName( const std::string & s )
+    1814             : {
+    1815           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
+    1816           0 :     ParticleNameMap::nameIterator const cit = pmap.findString( s );
+    1817             :     return ( cit == pmap.endLookupMap() )
+    1818           0 :          ? checkForSpecialParticle(s)
+    1819           0 :          : cit->second;
+    1820             : }  // particleName()
+    1821             : 
+    1822             : //
+    1823             : // list all the defined names
+    1824             : //
+    1825           0 : void  listParticleNames( std::ostream & os  )
+    1826             : {
+    1827           0 :     writeVersion( os );
+    1828             :     os << "     HepPID Particle List" << std::endl;
+    1829             :     os << std::endl;
+    1830             : 
+    1831             :     // simple: static  PartcleIdMap const &  pmap = getPartcleIdMap();
+    1832             :     // simple: for( PartcleIdMap::const_iterator cit = pmap.begin(), mend = pmap.end(); 
+    1833             :     // simple:                                 cit != mend;
+    1834             :         // simple:                        ++cit ) {
+    1835             :         // simple: os << "  PDT number: " ;
+    1836             :         // simple: os.width(12);
+    1837             :         // simple: os << cit->first << "  PDT name: " << cit->second << std::endl;
+    1838             :     // simple: }
+    1839             :     int id, i, j, q1, q2, q3, l, m, n;
+    1840             :     // special cases
+    1841           0 :     for( id=1; id<101; ++id) {
+    1842           0 :         writeParticleNameLine(  id, os );
+    1843           0 :         writeParticleNameLine( -id, os );
+    1844             :     }
+    1845           0 :     for( i=11; i<1000; ++i) {
+    1846           0 :         id = i*10;
+    1847           0 :         writeParticleNameLine(  id, os );
+    1848           0 :         writeParticleNameLine( -id, os );
+    1849             :     }
+    1850             :     // SUSY
+    1851           0 :     for( n=1; n<3; ++n) {
+    1852           0 :         for( q1=0; q1<10; ++q1) {
+    1853           0 :             for( j=0; j<10; ++j) {
+    1854           0 :                 id = 1000000*n+10*q1+j;
+    1855           0 :                 writeParticleNameLine(  id, os );
+    1856           0 :                 writeParticleNameLine( -id, os );
+    1857             :             }
+    1858             :         }
+    1859             :     }
+    1860             :     // technicolor, etc.
+    1861           0 :     for( n=3; n<7; ++n) {
+    1862           0 :         for( q2=0; q2<10; ++q2) {
+    1863           0 :             for( q1=0; q1<10; ++q1) {
+    1864           0 :                 for( j=0; j<10; ++j) {
+    1865           0 :                     for( m=0; m<10; ++m) {
+    1866           0 :                         for( l=0; l<7; ++l) {
+    1867           0 :                             id = 1000000*n+100000*m+10000*l+100*q2+10*q1+j;
+    1868             :                             // save dyons for later
+    1869           0 :                             if( !(n == 4 && m == 1) ) {
+    1870           0 :                             writeParticleNameLine(  id, os );
+    1871           0 :                             writeParticleNameLine( -id, os );
+    1872             :                             }
+    1873             :                         }
+    1874             :                     }
+    1875             :                 }
+    1876             :             }
+    1877             :         }
+    1878             :     }
+    1879             :     // R-hadrons
+    1880           0 :     for( q3=0; q3<10; ++q3) {
+    1881           0 :         for( q2=1; q2<10; ++q2) {
+    1882           0 :             for( q1=1; q1<10; ++q1) {
+    1883           0 :                 for( j=1; j<5; ++j) {
+    1884           0 :                     id = 1000000+1000*q3+100*q2+10*q1+j;
+    1885           0 :                     writeParticleNameLine( id, os );
+    1886           0 :                     if(q3 > 0 ) id = 1000000+90000+1000*q3+100*q2+10*q1+j;
+    1887           0 :                     writeParticleNameLine( id, os );
+    1888             :                 }
+    1889             :             }
+    1890             :         }
+    1891             :     }
+    1892             :     // miscellaneous generator particles
+    1893           0 :     for( l=0; l<9; ++l) {
+    1894           0 :         for( i=1; i<100; ++i) {
+    1895           0 :             id = 9900000+10000*l+i;
+    1896           0 :             writeParticleNameLine(  id, os );
+    1897           0 :             writeParticleNameLine( -id, os );
+    1898             :         }
+    1899           0 :         for( q3=0; q3<10; ++q3) {
+    1900           0 :             for( q2=1; q2<10; ++q2) {
+    1901           0 :                 for( q1=1; q1<10; ++q1) {
+    1902           0 :                     for( j=0; j<10; ++j) {
+    1903           0 :                         id = 9900000+10000*l+1000*q3+100*q2+10*q1+j;
+    1904           0 :                         writeParticleNameLine(  id, os );
+    1905           0 :                         writeParticleNameLine( -id, os );
+    1906             :                     }
+    1907             :                 }
+    1908             :             }
+    1909             :         }
+    1910             :     }
+    1911             :     // diquark
+    1912           0 :     for( i=11; i<100; ++i) {
+    1913           0 :         for( j=0; j<10; ++j) {
+    1914           0 :             id = 100*i+j;
+    1915           0 :             writeParticleNameLine(  id, os );
+    1916           0 :             writeParticleNameLine( -id, os );
+    1917             :         }
+    1918             :     }
+    1919             :     // mesons
+    1920           0 :     for( q2=1; q2<10; ++q2) {
+    1921           0 :         for( q1=1; q1<10; ++q1) {
+    1922           0 :             for( j=1; j<10; ++j) {
+    1923           0 :                 for( m=0; m<9; ++m) {
+    1924           0 :                     for( l=0; l<10; ++l) {
+    1925           0 :                         id = 100000*m+10000*l+100*q2+10*q1+j;
+    1926           0 :                         writeParticleNameLine(  id, os );
+    1927           0 :                         writeParticleNameLine( -id, os );
+    1928           0 :                         id = 9000000+100000*m+10000*l+100*q2+10*q1+j;
+    1929           0 :                         writeParticleNameLine(  id, os );
+    1930           0 :                         writeParticleNameLine( -id, os );
+    1931             :                     }
+    1932             :                 }
+    1933             :             }
+    1934             :         }
+    1935             :     }
+    1936             :     // baryons
+    1937           0 :     for( q3=1; q3<10; ++q3) {
+    1938           0 :         for( q2=1; q2<10; ++q2) {
+    1939           0 :             for( q1=1; q1<10; ++q1) {
+    1940           0 :                 for( j=1; j<10; ++j) {
+    1941           0 :                     for( m=0; m<9; ++m) {
+    1942           0 :                         id = 10000*m+1000*q3+100*q2+10*q1+j;
+    1943           0 :                         writeParticleNameLine(  id, os );
+    1944           0 :                         writeParticleNameLine( -id, os );
+    1945             :                     }
+    1946             :                 }
+    1947             :             }
+    1948             :         }
+    1949             :     }
+    1950             :     // pentaquarks
+    1951           0 :     for( l=1; l<9; ++l ) {
+    1952           0 :         for ( m=1; m<9; ++m ) {
+    1953           0 :             for( q3=1; q3<9; ++q3) {
+    1954           0 :                 for( q2=1; q2<9; ++q2) {
+    1955           0 :                     for( q1=1; q1<9; ++q1) {
+    1956           0 :                         id = 9*1000000+l*100000+m*10000+1000*q3+100*q2+10*q1+2;
+    1957           0 :                         writeParticleNameLine(  id, os );
+    1958           0 :                         writeParticleNameLine( -id, os );
+    1959             :                     }
+    1960             :                 }
+    1961             :             }
+    1962             :         }
+    1963             :     }
+    1964             :     // ions
+    1965           0 :     for( i=1; i<3; ++i) {
+    1966           0 :         for( m=1; m<5; ++m) {
+    1967           0 :                 id = 1000000000+10*m+10000*i;
+    1968           0 :                 writeParticleNameLine(  id, os );
+    1969           0 :                 writeParticleNameLine( -id, os );
+    1970             :         }
+    1971             :     }
+    1972             :     // some Dyons
+    1973           0 :     for( q3=0; q3<2; ++q3) {
+    1974           0 :         for( q2=0; q2<4; ++q2) {
+    1975           0 :             for( q1=0; q1<10; ++q1) {
+    1976           0 :                 ++q1;
+    1977           0 :                 id = 4110000+1000*q3+100*q2+10*q1;
+    1978           0 :                 writeParticleNameLine(  id, os );
+    1979           0 :                 writeParticleNameLine( -id, os );
+    1980           0 :                 id = 4120000+1000*q3+100*q2+10*q1;
+    1981           0 :                 writeParticleNameLine(  id, os );
+    1982           0 :                 writeParticleNameLine( -id, os );
+    1983             :             }
+    1984             :         }
+    1985             :     }
+    1986             :     // a few QBalls
+    1987           0 :     for( i=1; i<199; ++i ) {
+    1988           0 :         for( m=1; m<10; ) {
+    1989           0 :                 id = 10000000+10*m+100*i;
+    1990           0 :                 writeParticleNameLine(  id, os );
+    1991           0 :                 writeParticleNameLine( -id, os );
+    1992           0 :                 m += 3;
+    1993             :         }
+    1994             :         i += 11;
+    1995             :     }
+    1996           0 :     return;
+    1997             : }  // listParticleNames()
+    1998             : 
+    1999             : }       // HepPID
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html b/doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html new file mode 100644 index 000000000..65c9d6164 --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/Version.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - Version.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:080.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID11versionNameB5cxx11Ev0
_ZN6HepPID12writeVersionERSo0
_ZN6HepPID7versionEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/Version.cc.func.html b/doc/coverageReport/libs/HepPID/src/Version.cc.func.html new file mode 100644 index 000000000..0a0efae49 --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/Version.cc.func.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/Version.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - Version.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:080.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID11versionNameB5cxx11Ev0
_ZN6HepPID12writeVersionERSo0
_ZN6HepPID7versionEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html b/doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html new file mode 100644 index 000000000..1d5d7f616 --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html @@ -0,0 +1,106 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src/Version.cc + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/src - Version.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:080.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : // ----------------------------------------------------------------------
+       2             : //
+       3             : // version.cc
+       4             : // Author: Lynn Garren
+       5             : //
+       6             : //  for now, this is a free function
+       7             : //
+       8             : // ----------------------------------------------------------------------
+       9             : 
+      10             : #include "HepPID/Version.hh"
+      11             : 
+      12             : namespace HepPID {
+      13             : 
+      14           0 : std::string versionName( )
+      15             : {
+      16           0 :     return "3.04.01";
+      17             : }
+      18             : 
+      19           0 : void version( )
+      20             : {
+      21           0 :     std::cout << " --------------- HepPID Version " << versionName()
+      22             :               << " --------------- " << std::endl;
+      23           0 : }
+      24             : 
+      25           0 : void writeVersion( std::ostream & os )
+      26             : {
+      27           0 :     os << "             HepPID Version: " << versionName() << std::endl;
+      28           0 : }
+      29             : 
+      30             : }       // HepPID
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/index-sort-f.html b/doc/coverageReport/libs/HepPID/src/index-sort-f.html new file mode 100644 index 000000000..0bc408cce --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/index-sort-f.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/srcHitTotalCoverage
Test:coverage.info.cleanedLines:5044011.4 %
Date:2024-04-08 14:58:22Functions:114822.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Version.cc +
0.0%
+
0.0 %0 / 80.0 %0 / 3
ParticleName.cc +
0.0%
+
0.0 %0 / 1830.0 %0 / 13
ParticleIDMethods.cc +
20.1%20.1%
+
20.1 %50 / 24934.4 %11 / 32
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/index-sort-l.html b/doc/coverageReport/libs/HepPID/src/index-sort-l.html new file mode 100644 index 000000000..5545aaf67 --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/index-sort-l.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/srcHitTotalCoverage
Test:coverage.info.cleanedLines:5044011.4 %
Date:2024-04-08 14:58:22Functions:114822.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Version.cc +
0.0%
+
0.0 %0 / 80.0 %0 / 3
ParticleName.cc +
0.0%
+
0.0 %0 / 1830.0 %0 / 13
ParticleIDMethods.cc +
20.1%20.1%
+
20.1 %50 / 24934.4 %11 / 32
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/HepPID/src/index.html b/doc/coverageReport/libs/HepPID/src/index.html new file mode 100644 index 000000000..cce8733cc --- /dev/null +++ b/doc/coverageReport/libs/HepPID/src/index.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/HepPID/src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/HepPID/srcHitTotalCoverage
Test:coverage.info.cleanedLines:5044011.4 %
Date:2024-04-08 14:58:22Functions:114822.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ParticleIDMethods.cc +
20.1%20.1%
+
20.1 %50 / 24934.4 %11 / 32
ParticleName.cc +
0.0%
+
0.0 %0 / 1830.0 %0 / 13
Version.cc +
0.0%
+
0.0 %0 / 80.0 %0 / 3
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html new file mode 100644 index 000000000..48630a2e2 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/error_handling.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - error_handling.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0120.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix11PlanckErrorC2EPKc0
_ZN7healpix11PlanckErrorC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix11PlanckErrorD0Ev0
_ZN7healpix11PlanckErrorD2Ev0
_ZN7healpix16planck_failure__EPKciS1_RKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix16planck_failure__EPKciS1_S1_0
_ZN7healpix9killjob__Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/error_handling.cc.func.html b/doc/coverageReport/libs/healpix_base/error_handling.cc.func.html new file mode 100644 index 000000000..3f1abe29a --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/error_handling.cc.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/error_handling.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - error_handling.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0120.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix11PlanckErrorC2EPKc0
_ZN7healpix11PlanckErrorC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix11PlanckErrorD0Ev0
_ZN7healpix11PlanckErrorD2Ev0
_ZN7healpix16planck_failure__EPKciS1_RKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix16planck_failure__EPKciS1_S1_0
_ZN7healpix9killjob__Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html b/doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html new file mode 100644 index 000000000..d09b41e69 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/error_handling.cc + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - error_handling.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0120.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : 
+       2             : /*
+       3             :  *  This file is part of libcxxsupport.
+       4             :  *
+       5             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       6             :  *  it under the terms of the GNU General Public License as published by
+       7             :  *  the Free Software Foundation; either version 2 of the License, or
+       8             :  *  (at your option) any later version.
+       9             :  *
+      10             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      11             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      12             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      13             :  *  GNU General Public License for more details.
+      14             :  *
+      15             :  *  You should have received a copy of the GNU General Public License
+      16             :  *  along with libcxxsupport; if not, write to the Free Software
+      17             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      18             :  */
+      19             : 
+      20             : /*
+      21             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      22             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      23             :  *  (DLR).
+      24             :  */
+      25             : 
+      26             : /*
+      27             :  *  Utilities for error reporting
+      28             :  *
+      29             :  *  Copyright (C) 2003-2011 Max-Planck-Society
+      30             :  *  Author: Martin Reinecke
+      31             :  */
+      32             : 
+      33             : #include "healpix_base/error_handling.h"
+      34             : 
+      35             : namespace healpix{
+      36             : using namespace std;
+      37             : 
+      38           0 : PlanckError::PlanckError(const string &message) : msg (message) {}
+      39           0 : PlanckError::PlanckError(const char *message) : msg (message) {}
+      40             : 
+      41             : //virtual
+      42           0 : PlanckError::~PlanckError() {}
+      43             : 
+      44           0 : void planck_failure__(const char *file, int line, const char *func,
+      45             :   const string &msg)
+      46             :   {
+      47           0 :   cerr << "Error encountered at " << file << ", line " << line << endl;
+      48           0 :   if (func) cerr << "(function " << func << ")" << endl;
+      49           0 :   if (msg!="") cerr << endl << msg << endl;
+      50             :   cerr << endl;
+      51           0 :   }
+      52             : 
+      53           0 : void planck_failure__(const char *file, int line, const char *func,
+      54             :   const char *msg)
+      55           0 :   { planck_failure__ (file,line,func,string(msg)); }
+      56             : 
+      57           0 : void killjob__()
+      58           0 :   { throw; }
+      59             : } // namespace healpix
+      60             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html new file mode 100644 index 000000000..c1777f967 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/geom_utils.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - geom_utils.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0250.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmRS2_Rd0
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmmRS2_Rd0
_ZN7healpix21find_enclosing_circleERKNS_3arrINS_6vec3_tIdEEEERS2_Rd0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html b/doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html new file mode 100644 index 000000000..db584b322 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/geom_utils.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - geom_utils.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0250.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmRS2_Rd0
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmmRS2_Rd0
_ZN7healpix21find_enclosing_circleERKNS_3arrINS_6vec3_tIdEEEERS2_Rd0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html b/doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html new file mode 100644 index 000000000..2fdacf966 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html @@ -0,0 +1,151 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/geom_utils.cc + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - geom_utils.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0250.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*
+      26             :  *  Copyright (C) 2011 Max-Planck-Society
+      27             :  *  \author Martin Reinecke
+      28             :  */
+      29             : 
+      30             : #include "healpix_base/geom_utils.h"
+      31             : #include "healpix_base/arr.h"
+      32             : 
+      33             : 
+      34             : namespace healpix{
+      35             : using namespace std;
+      36             : 
+      37             : 
+      38           0 : void get_circle (const arr<vec3> &point, tsize q1, tsize q2, vec3 &center,
+      39             :   double &cosrad)
+      40             :   {
+      41           0 :   center = (point[q1]+point[q2]).Norm();
+      42           0 :   cosrad = dotprod(point[q1],center);
+      43           0 :   for (tsize i=0; i<q1; ++i)
+      44           0 :     if (dotprod(point[i],center)<cosrad) // point outside the current circle
+      45             :       {
+      46           0 :       center=crossprod(point[q1]-point[i],point[q2]-point[i]).Norm();
+      47           0 :       cosrad=dotprod(point[i],center);
+      48           0 :       if (cosrad<0)
+      49           0 :         { center.Flip(); cosrad=-cosrad; }
+      50             :       }
+      51           0 :   }
+      52           0 : void get_circle (const arr<vec3> &point, tsize q, vec3 &center,
+      53             :   double &cosrad)
+      54             :   {
+      55           0 :   center = (point[0]+point[q]).Norm();
+      56           0 :   cosrad = dotprod(point[0],center);
+      57           0 :   for (tsize i=1; i<q; ++i)
+      58           0 :     if (dotprod(point[i],center)<cosrad) // point outside the current circle
+      59           0 :       get_circle(point,i,q,center,cosrad);
+      60           0 :   }
+      61             : 
+      62             : 
+      63           0 : void find_enclosing_circle (const arr<vec3> &point, vec3 &center,
+      64             :   double &cosrad)
+      65             :   {
+      66             :   tsize np=point.size();
+      67           0 :   planck_assert(np>=3,"too few points");
+      68           0 :   center = (point[0]+point[1]).Norm();
+      69           0 :   cosrad = dotprod(point[0],center);
+      70           0 :   for (tsize i=2; i<np; ++i)
+      71           0 :     if (dotprod(point[i],center)<cosrad) // point outside the current circle
+      72           0 :       get_circle(point,i,center,cosrad);
+      73           0 :   }
+      74             : } // namespace healpix
+      75             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html new file mode 100644 index 000000000..522a3b809 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html @@ -0,0 +1,436 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/healpix_base.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - healpix_base.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11273415.3 %
Date:2024-04-08 14:58:22Functions:109111.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12_GLOBAL__N_111check_pixelIiiEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIliEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIllEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIiEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIlEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_19locToVec3Edddb0
_ZN7healpix14T_Healpix_BaseIiE10npix2nsideEi0
_ZN7healpix14T_Healpix_BaseIiE11nside2orderEi0
_ZN7healpix14T_Healpix_BaseIiE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIiE8SetNsideEiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2Ev0
_ZN7healpix14T_Healpix_BaseIlE10npix2nsideEl0
_ZN7healpix14T_Healpix_BaseIlE11nside2orderEl0
_ZN7healpix14T_Healpix_BaseIlE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIlE8SetNsideElNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2Ev0
_ZNK7healpix14T_Healpix_BaseIiE10boundariesEimRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEi0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIiE10nest2peanoEi0
_ZNK7healpix14T_Healpix_BaseIiE10peano2nestEi0
_ZNK7healpix14T_Healpix_BaseIiE10query_discENS_8pointingEdRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIiE11query_stripEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIiE12get_interpolERKNS_8pointingERNS_7fix_arrIiLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIiE13get_ring_infoEiRiS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIiE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE14get_ring_info2EiRiS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIiE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE17nest_peano_helperEii0
_ZNK7healpix14T_Healpix_BaseIiE19get_ring_info_smallEiRiS2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE20query_strip_internalEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE6ring2zEi0
_ZNK7healpix14T_Healpix_BaseIiE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE8nest2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE8pix2ringEi0
_ZNK7healpix14T_Healpix_BaseIiE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIiE9neighborsEiRNS_7fix_arrIiLm8EEE0
_ZNK7healpix14T_Healpix_BaseIiE9nest2ringEi0
_ZNK7healpix14T_Healpix_BaseIlE10boundariesElmRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEl0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIlE10nest2peanoEl0
_ZNK7healpix14T_Healpix_BaseIlE10peano2nestEl0
_ZNK7healpix14T_Healpix_BaseIlE10query_discENS_8pointingEdRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIlE11query_stripEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11spread_bitsEi0
_ZNK7healpix14T_Healpix_BaseIlE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIlE12get_interpolERKNS_8pointingERNS_7fix_arrIlLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIlE13get_ring_infoElRlS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIlE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE14get_ring_info2ElRlS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIlEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE17nest_peano_helperEli0
_ZNK7healpix14T_Healpix_BaseIlE19get_ring_info_smallElRlS2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIlEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE20query_strip_internalEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIlEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE6ring2zEl0
_ZNK7healpix14T_Healpix_BaseIlE7loc2pixEdddb0
_ZNK7healpix14T_Healpix_BaseIlE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE8pix2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE8ring2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2nestEiii0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIlE9neighborsElRNS_7fix_arrIlLm8EEE0
_ZNK7healpix14T_Healpix_BaseIlE9nest2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE9ring2nestEl0
_ZN7healpix14T_Healpix_BaseIiE3SetEiNS_23Healpix_Ordering_SchemeE10
_ZN7healpix14T_Healpix_BaseIlE3SetEiNS_23Healpix_Ordering_SchemeE19
_ZNK7healpix14T_Healpix_BaseIiE8ring2xyfEiRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIiE8xyf2nestEiii421
_ZNK7healpix14T_Healpix_BaseIiE9ring2nestEi421
_ZNK7healpix14T_Healpix_BaseIlE7pix2locElRdS2_S2_Rb421
_ZNK7healpix14T_Healpix_BaseIlE8nest2xyfElRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIlE13compress_bitsEl842
_ZNK7healpix14T_Healpix_BaseIiE7loc2pixEdddb24585
_ZNK7healpix14T_Healpix_BaseIiE7pix2locEiRdS2_S2_Rb135172
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html b/doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html new file mode 100644 index 000000000..30c46e124 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html @@ -0,0 +1,436 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/healpix_base.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - healpix_base.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11273415.3 %
Date:2024-04-08 14:58:22Functions:109111.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12_GLOBAL__N_111check_pixelIiiEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIliEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIllEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIiEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIlEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_19locToVec3Edddb0
_ZN7healpix14T_Healpix_BaseIiE10npix2nsideEi0
_ZN7healpix14T_Healpix_BaseIiE11nside2orderEi0
_ZN7healpix14T_Healpix_BaseIiE3SetEiNS_23Healpix_Ordering_SchemeE10
_ZN7healpix14T_Healpix_BaseIiE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIiE8SetNsideEiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2Ev0
_ZN7healpix14T_Healpix_BaseIlE10npix2nsideEl0
_ZN7healpix14T_Healpix_BaseIlE11nside2orderEl0
_ZN7healpix14T_Healpix_BaseIlE3SetEiNS_23Healpix_Ordering_SchemeE19
_ZN7healpix14T_Healpix_BaseIlE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIlE8SetNsideElNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2Ev0
_ZNK7healpix14T_Healpix_BaseIiE10boundariesEimRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEi0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIiE10nest2peanoEi0
_ZNK7healpix14T_Healpix_BaseIiE10peano2nestEi0
_ZNK7healpix14T_Healpix_BaseIiE10query_discENS_8pointingEdRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIiE11query_stripEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIiE12get_interpolERKNS_8pointingERNS_7fix_arrIiLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIiE13get_ring_infoEiRiS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIiE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE14get_ring_info2EiRiS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIiE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE17nest_peano_helperEii0
_ZNK7healpix14T_Healpix_BaseIiE19get_ring_info_smallEiRiS2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE20query_strip_internalEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE6ring2zEi0
_ZNK7healpix14T_Healpix_BaseIiE7loc2pixEdddb24585
_ZNK7healpix14T_Healpix_BaseIiE7pix2locEiRdS2_S2_Rb135172
_ZNK7healpix14T_Healpix_BaseIiE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE8nest2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE8pix2ringEi0
_ZNK7healpix14T_Healpix_BaseIiE8ring2xyfEiRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIiE8xyf2nestEiii421
_ZNK7healpix14T_Healpix_BaseIiE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIiE9neighborsEiRNS_7fix_arrIiLm8EEE0
_ZNK7healpix14T_Healpix_BaseIiE9nest2ringEi0
_ZNK7healpix14T_Healpix_BaseIiE9ring2nestEi421
_ZNK7healpix14T_Healpix_BaseIlE10boundariesElmRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEl0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIlE10nest2peanoEl0
_ZNK7healpix14T_Healpix_BaseIlE10peano2nestEl0
_ZNK7healpix14T_Healpix_BaseIlE10query_discENS_8pointingEdRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIlE11query_stripEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11spread_bitsEi0
_ZNK7healpix14T_Healpix_BaseIlE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIlE12get_interpolERKNS_8pointingERNS_7fix_arrIlLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIlE13compress_bitsEl842
_ZNK7healpix14T_Healpix_BaseIlE13get_ring_infoElRlS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIlE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE14get_ring_info2ElRlS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIlEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE17nest_peano_helperEli0
_ZNK7healpix14T_Healpix_BaseIlE19get_ring_info_smallElRlS2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIlEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE20query_strip_internalEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIlEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE6ring2zEl0
_ZNK7healpix14T_Healpix_BaseIlE7loc2pixEdddb0
_ZNK7healpix14T_Healpix_BaseIlE7pix2locElRdS2_S2_Rb421
_ZNK7healpix14T_Healpix_BaseIlE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE8nest2xyfElRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIlE8pix2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE8ring2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2nestEiii0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIlE9neighborsElRNS_7fix_arrIlLm8EEE0
_ZNK7healpix14T_Healpix_BaseIlE9nest2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE9ring2nestEl0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html b/doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html new file mode 100644 index 000000000..be3123d75 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html @@ -0,0 +1,1454 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/healpix_base.cc + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - healpix_base.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11273415.3 %
Date:2024-04-08 14:58:22Functions:109111.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of Healpix_cxx.
+       3             :  *
+       4             :  *  Healpix_cxx is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  Healpix_cxx is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with Healpix_cxx; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  *
+      18             :  *  For more information about HEALPix, see http://healpix.sourceforge.net
+      19             :  */
+      20             : 
+      21             : /*
+      22             :  *  Healpix_cxx is being developed at the Max-Planck-Institut fuer Astrophysik
+      23             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      24             :  *  (DLR).
+      25             :  */
+      26             : 
+      27             : /*
+      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
+      29             :  *  Author: Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #include "healpix_base/healpix_base.h"
+      33             : #include "healpix_base/geom_utils.h"
+      34             : #include "healpix_base/lsconstants.h"
+      35             : 
+      36             : namespace healpix{
+      37             : 
+      38             : using namespace std;
+      39             : 
+      40             : template<> const int T_Healpix_Base<int  >::order_max=13;
+      41             : template<> const int T_Healpix_Base<int64>::order_max=29;
+      42             : 
+      43           0 : template<typename I> int T_Healpix_Base<I>::nside2order (I nside)
+      44             :   {
+      45           0 :   planck_assert (nside>I(0), "invalid value for Nside");
+      46           0 :   return ((nside)&(nside-1)) ? -1 : ilog2(nside);
+      47             :   }
+      48           0 : template<typename I> I T_Healpix_Base<I>::npix2nside (I npix)
+      49             :   {
+      50           0 :   I res=isqrt(npix/I(12));
+      51           0 :   planck_assert (npix==res*res*I(12), "invalid value for npix");
+      52           0 :   return res;
+      53             :   }
+      54             : 
+      55           0 : template<typename I> I T_Healpix_Base<I>::ring_above (double z) const
+      56             :   {
+      57             :   double az=abs(z);
+      58           0 :   if (az<=twothird) // equatorial region
+      59           0 :     return I(nside_*(2-1.5*z));
+      60           0 :   I iring = I(nside_*sqrt(3*(1-az)));
+      61           0 :   return (z>0) ? iring : 4*nside_-iring-1;
+      62             :   }
+      63             : 
+      64             : namespace {
+      65             : 
+      66             : /* Short note on the "zone":
+      67             :    zone = 0: pixel lies completely outside the queried shape
+      68             :           1: pixel may overlap with the shape, pixel center is outside
+      69             :           2: pixel center is inside the shape, but maybe not the complete pixel
+      70             :           3: pixel lies completely inside the shape */
+      71             : 
+      72           0 : template<typename I, typename I2> inline void check_pixel (int o, int order_,
+      73             :   int omax, int zone, rangeset<I2> &pixset, I pix, vector<pair<I,int> > &stk,
+      74             :   bool inclusive, int &stacktop)
+      75             :   {
+      76           0 :   if (zone==0) return;
+      77             : 
+      78           0 :   if (o<order_)
+      79             :     {
+      80           0 :     if (zone>=3)
+      81             :       {
+      82           0 :       int sdist=2*(order_-o); // the "bit-shift distance" between map orders
+      83           0 :       pixset.append(pix<<sdist,(pix+1)<<sdist); // output all subpixels
+      84             :       }
+      85             :     else // (zone>=1)
+      86           0 :       for (int i=0; i<4; ++i)
+      87           0 :         stk.push_back(make_pair(4*pix+3-i,o+1)); // add children
+      88             :     }
+      89           0 :   else if (o>order_) // this implies that inclusive==true
+      90             :     {
+      91           0 :     if (zone>=2) // pixel center in shape
+      92             :       {
+      93           0 :       pixset.append(pix>>(2*(o-order_))); // output the parent pixel at order_
+      94           0 :       stk.resize(stacktop); // unwind the stack
+      95             :       }
+      96             :     else // (zone>=1): pixel center in safety range
+      97             :       {
+      98           0 :       if (o<omax) // check sublevels
+      99           0 :         for (int i=0; i<4; ++i) // add children in reverse order
+     100           0 :           stk.push_back(make_pair(4*pix+3-i,o+1));
+     101             :       else // at resolution limit
+     102             :         {
+     103           0 :         pixset.append(pix>>(2*(o-order_))); // output the parent pixel at order_
+     104           0 :         stk.resize(stacktop); // unwind the stack
+     105             :         }
+     106             :       }
+     107             :     }
+     108             :   else // o==order_
+     109             :     {
+     110           0 :     if (zone>=2)
+     111           0 :       pixset.append(pix);
+     112           0 :     else if (inclusive) // and (zone>=1)
+     113             :       {
+     114           0 :       if (order_<omax) // check sublevels
+     115             :         {
+     116           0 :         stacktop=stk.size(); // remember current stack position
+     117           0 :         for (int i=0; i<4; ++i) // add children in reverse order
+     118           0 :           stk.push_back(make_pair(4*pix+3-i,o+1));
+     119             :         }
+     120             :       else // at resolution limit
+     121           0 :         pixset.append(pix); // output the pixel
+     122             :       }
+     123             :     }
+     124             :   }
+     125             : 
+     126           0 : template<typename I> bool check_pixel_ring (const T_Healpix_Base<I> &b1,
+     127             :   const T_Healpix_Base<I> &b2, I pix, I nr, I ipix1, int fct,
+     128             :   double cz, double cphi, double cosrp2, I cpix)
+     129             :   {
+     130           0 :   if (pix>=nr) pix-=nr;
+     131           0 :   if (pix<0) pix+=nr;
+     132           0 :   pix+=ipix1;
+     133           0 :   if (pix==cpix) return false; // disk center in pixel => overlap
+     134             :   int px,py,pf;
+     135           0 :   b1.pix2xyf(pix,px,py,pf);
+     136           0 :   for (int i=0; i<fct-1; ++i) // go along the 4 edges
+     137             :     {
+     138           0 :     I ox=fct*px, oy=fct*py;
+     139             :     double pz,pphi;
+     140           0 :     b2.pix2zphi(b2.xyf2pix(ox+i,oy,pf),pz,pphi);
+     141           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
+     142           0 :       return false;
+     143           0 :     b2.pix2zphi(b2.xyf2pix(ox+fct-1,oy+i,pf),pz,pphi);
+     144           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
+     145             :       return false;
+     146           0 :     b2.pix2zphi(b2.xyf2pix(ox+fct-1-i,oy+fct-1,pf),pz,pphi);
+     147           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
+     148             :       return false;
+     149           0 :     b2.pix2zphi(b2.xyf2pix(ox,oy+fct-1-i,pf),pz,pphi);
+     150           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
+     151             :       return false;
+     152             :     }
+     153             :   return true;
+     154             :   }
+     155             : 
+     156             : } // unnamed namespace
+     157             : 
+     158             : template<typename I> template<typename I2>
+     159           0 :   void T_Healpix_Base<I>::query_disc_internal
+     160             :   (pointing ptg, double radius, int fact, rangeset<I2> &pixset) const
+     161             :   {
+     162           0 :   bool inclusive = (fact!=0);
+     163             :   pixset.clear();
+     164           0 :   ptg.normalize();
+     165             : 
+     166           0 :   if (scheme_==RING)
+     167             :     {
+     168             :     I fct=1;
+     169           0 :     if (inclusive)
+     170             :       {
+     171           0 :       planck_assert (((I(1)<<order_max)/nside_)>=fact,
+     172             :         "invalid oversampling factor");
+     173             :       fct = fact;
+     174             :       }
+     175           0 :     T_Healpix_Base b2;
+     176             :     double rsmall, rbig;
+     177           0 :     if (fct>1)
+     178             :       {
+     179           0 :       b2.SetNside(fct*nside_,RING);
+     180           0 :       rsmall = radius+b2.max_pixrad();
+     181           0 :       rbig = radius+max_pixrad();
+     182             :       }
+     183             :     else
+     184           0 :       rsmall = rbig = inclusive ? radius+max_pixrad() : radius;
+     185             : 
+     186           0 :     if (rsmall>=pi)
+     187           0 :       { pixset.append(0,npix_); return; }
+     188             : 
+     189           0 :     rbig = min(pi,rbig);
+     190             : 
+     191           0 :     double cosrsmall = cos(rsmall);
+     192           0 :     double cosrbig = cos(rbig);
+     193             : 
+     194           0 :     double z0 = cos(ptg.theta);
+     195           0 :     double xa = 1./sqrt((1-z0)*(1+z0));
+     196             : 
+     197           0 :     I cpix=zphi2pix(z0,ptg.phi);
+     198             : 
+     199           0 :     double rlat1 = ptg.theta - rsmall;
+     200           0 :     double zmax = cos(rlat1);
+     201           0 :     I irmin = ring_above (zmax)+1;
+     202             : 
+     203           0 :     if ((rlat1<=0) && (irmin>1)) // north pole in the disk
+     204             :       {
+     205             :       I sp,rp; bool dummy;
+     206           0 :       get_ring_info_small(irmin-1,sp,rp,dummy);
+     207           0 :       pixset.append(0,sp+rp);
+     208             :       }
+     209             : 
+     210           0 :     if ((fct>1) && (rlat1>0)) irmin=max(I(1),irmin-1);
+     211             : 
+     212           0 :     double rlat2 = ptg.theta + rsmall;
+     213           0 :     double zmin = cos(rlat2);
+     214           0 :     I irmax = ring_above (zmin);
+     215             : 
+     216           0 :     if ((fct>1) && (rlat2<pi)) irmax=min(4*nside_-1,irmax+1);
+     217             : 
+     218           0 :     for (I iz=irmin; iz<=irmax; ++iz)
+     219             :       {
+     220           0 :       double z=ring2z(iz);
+     221           0 :       double x = (cosrbig-z*z0)*xa;
+     222           0 :       double ysq = 1-z*z-x*x;
+     223           0 :       double dphi = (ysq<=0) ? pi-1e-15 : atan2(sqrt(ysq),x);
+     224             :       I nr, ipix1;
+     225             :       bool shifted;
+     226           0 :       get_ring_info_small(iz,ipix1,nr,shifted);
+     227           0 :       double shift = shifted ? 0.5 : 0.;
+     228             : 
+     229           0 :       I ipix2 = ipix1 + nr - 1; // highest pixel number in the ring
+     230             : 
+     231           0 :       I ip_lo = ifloor<I>(nr*inv_twopi*(ptg.phi-dphi) - shift)+1;
+     232           0 :       I ip_hi = ifloor<I>(nr*inv_twopi*(ptg.phi+dphi) - shift);
+     233             : 
+     234           0 :       if (fct>1)
+     235             :         {
+     236           0 :         while ((ip_lo<=ip_hi) && check_pixel_ring
+     237           0 :                (*this,b2,ip_lo,nr,ipix1,fct,z0,ptg.phi,cosrsmall,cpix))
+     238           0 :           ++ip_lo;
+     239           0 :         while ((ip_hi>ip_lo) && check_pixel_ring
+     240           0 :                (*this,b2,ip_hi,nr,ipix1,fct,z0,ptg.phi,cosrsmall,cpix))
+     241           0 :           --ip_hi;
+     242             :         }
+     243             : 
+     244           0 :       if (ip_lo<=ip_hi)
+     245             :         {
+     246           0 :         if (ip_hi>=nr)
+     247           0 :           { ip_lo-=nr; ip_hi-=nr; }
+     248           0 :         if (ip_lo<0)
+     249             :           {
+     250           0 :           pixset.append(ipix1,ipix1+ip_hi+1);
+     251           0 :           pixset.append(ipix1+ip_lo+nr,ipix2+1);
+     252             :           }
+     253             :         else
+     254           0 :           pixset.append(ipix1+ip_lo,ipix1+ip_hi+1);
+     255             :         }
+     256             :       }
+     257           0 :     if ((rlat2>=pi) && (irmax+1<4*nside_)) // south pole in the disk
+     258             :       {
+     259             :       I sp,rp; bool dummy;
+     260           0 :       get_ring_info_small(irmax+1,sp,rp,dummy);
+     261           0 :       pixset.append(sp,npix_);
+     262             :       }
+     263             :     }
+     264             :   else // scheme_==NEST
+     265             :     {
+     266           0 :     if (radius>=pi) // disk covers the whole sphere
+     267           0 :       { pixset.append(0,npix_); return; }
+     268             : 
+     269             :     int oplus = 0;
+     270           0 :     if (inclusive)
+     271             :       {
+     272           0 :       planck_assert ((I(1)<<(order_max-order_))>=fact,
+     273             :         "invalid oversampling factor");
+     274           0 :       planck_assert ((fact&(fact-1))==0,
+     275             :         "oversampling factor must be a power of 2");
+     276           0 :       oplus=ilog2(fact);
+     277             :       }
+     278           0 :     int omax=order_+oplus; // the order up to which we test
+     279             : 
+     280             :     vec3 vptg(ptg);
+     281           0 :     arr<T_Healpix_Base<I> > base(omax+1);
+     282             :     arr<double> crpdr(omax+1), crmdr(omax+1);
+     283           0 :     double cosrad=cos(radius);
+     284           0 :     for (int o=0; o<=omax; ++o) // prepare data at the required orders
+     285             :       {
+     286           0 :       base[o].Set(o,NEST);
+     287           0 :       double dr=base[o].max_pixrad(); // safety distance
+     288           0 :       crpdr[o] = (radius+dr>pi) ? -1. : cos(radius+dr);
+     289           0 :       crmdr[o] = (radius-dr<0.) ?  1. : cos(radius-dr);
+     290             :       }
+     291             :     vector<pair<I,int> > stk; // stack for pixel numbers and their orders
+     292           0 :     stk.reserve(12+3*omax); // reserve maximum size to avoid reallocation
+     293           0 :     for (int i=0; i<12; ++i) // insert the 12 base pixels in reverse order
+     294           0 :       stk.push_back(make_pair(I(11-i),0));
+     295             : 
+     296           0 :     int stacktop=0; // a place to save a stack position
+     297             : 
+     298           0 :     while (!stk.empty()) // as long as there are pixels on the stack
+     299             :       {
+     300             :       // pop current pixel number and order from the stack
+     301           0 :       I pix=stk.back().first;
+     302           0 :       int o=stk.back().second;
+     303             :       stk.pop_back();
+     304             : 
+     305             :       double z,phi;
+     306             :       base[o].pix2zphi(pix,z,phi);
+     307             :       // cosine of angular distance between pixel center and disk center
+     308           0 :       double cangdist=cosdist_zphi(vptg.z,ptg.phi,z,phi);
+     309             : 
+     310           0 :       if (cangdist>crpdr[o])
+     311             :         {
+     312           0 :         int zone = (cangdist<cosrad) ? 1 : ((cangdist<=crmdr[o]) ? 2 : 3);
+     313             : 
+     314           0 :         check_pixel (o, order_, omax, zone, pixset, pix, stk, inclusive,
+     315             :           stacktop);
+     316             :         }
+     317             :       }
+     318             :     }
+     319             :   }
+     320             : 
+     321           0 : template<typename I> void T_Healpix_Base<I>::query_disc
+     322             :   (pointing ptg, double radius, rangeset<I> &pixset) const
+     323             :   {
+     324           0 :   query_disc_internal (ptg, radius, 0, pixset);
+     325           0 :   }
+     326             : 
+     327           0 : template<typename I> void T_Healpix_Base<I>::query_disc_inclusive
+     328             :   (pointing ptg, double radius, rangeset<I> &pixset, int fact) const
+     329             :   {
+     330           0 :   planck_assert(fact>0,"fact must be a positive integer");
+     331           0 :   if ((sizeof(I)<8) && (((I(1)<<order_max)/nside_)<fact))
+     332             :     {
+     333           0 :     T_Healpix_Base<int64> base2(nside_,scheme_,SET_NSIDE);
+     334           0 :     base2.query_disc_internal(ptg,radius,fact,pixset);
+     335             :     return;
+     336             :     }
+     337           0 :   query_disc_internal (ptg, radius, fact, pixset);
+     338             :   }
+     339             : 
+     340             : template<typename I> template<typename I2>
+     341           0 :   void T_Healpix_Base<I>::query_multidisc (const arr<vec3> &norm,
+     342             :   const arr<double> &rad, int fact, rangeset<I2> &pixset) const
+     343             :   {
+     344           0 :   bool inclusive = (fact!=0);
+     345             :   tsize nv=norm.size();
+     346           0 :   planck_assert(nv==rad.size(),"inconsistent input arrays");
+     347             :   pixset.clear();
+     348             : 
+     349           0 :   if (scheme_==RING)
+     350             :     {
+     351             :     I fct=1;
+     352           0 :     if (inclusive)
+     353             :       {
+     354           0 :       planck_assert (((I(1)<<order_max)/nside_)>=fact,
+     355             :         "invalid oversampling factor");
+     356             :       fct = fact;
+     357             :       }
+     358           0 :     T_Healpix_Base b2;
+     359             :     double rpsmall, rpbig;
+     360           0 :     if (fct>1)
+     361             :       {
+     362           0 :       b2.SetNside(fct*nside_,RING);
+     363           0 :       rpsmall = b2.max_pixrad();
+     364           0 :       rpbig = max_pixrad();
+     365             :       }
+     366             :     else
+     367           0 :       rpsmall = rpbig = inclusive ? max_pixrad() : 0;
+     368             : 
+     369           0 :     I irmin=1, irmax=4*nside_-1;
+     370             :     vector<double> z0,xa,cosrsmall,cosrbig;
+     371             :     vector<pointing> ptg;
+     372             :     vector<I> cpix;
+     373           0 :     for (tsize i=0; i<nv; ++i)
+     374             :       {
+     375           0 :       double rsmall=rad[i]+rpsmall;
+     376           0 :       if (rsmall<pi)
+     377             :         {
+     378           0 :         double rbig=min(pi,rad[i]+rpbig);
+     379             :         pointing pnt=pointing(norm[i]);
+     380           0 :         cosrsmall.push_back(cos(rsmall));
+     381           0 :         cosrbig.push_back(cos(rbig));
+     382           0 :         double cth=cos(pnt.theta);
+     383           0 :         z0.push_back(cth);
+     384           0 :         if (fct>1) cpix.push_back(zphi2pix(cth,pnt.phi));
+     385           0 :         xa.push_back(1./sqrt((1-cth)*(1+cth)));
+     386           0 :         ptg.push_back(pnt);
+     387             : 
+     388           0 :         double rlat1 = pnt.theta - rsmall;
+     389           0 :         double zmax = cos(rlat1);
+     390           0 :         I irmin_t = (rlat1<=0) ? 1 : ring_above (zmax)+1;
+     391             : 
+     392           0 :         if ((fct>1) && (rlat1>0)) irmin_t=max(I(1),irmin_t-1);
+     393             : 
+     394           0 :         double rlat2 = pnt.theta + rsmall;
+     395           0 :         double zmin = cos(rlat2);
+     396           0 :         I irmax_t = (rlat2>=pi) ? 4*nside_-1 : ring_above (zmin);
+     397             : 
+     398           0 :         if ((fct>1) && (rlat2<pi)) irmax_t=min(4*nside_-1,irmax_t+1);
+     399             : 
+     400             :         if (irmax_t < irmax) irmax=irmax_t;
+     401             :         if (irmin_t > irmin) irmin=irmin_t;
+     402             :         }
+     403             :       }
+     404             : 
+     405           0 :     for (I iz=irmin; iz<=irmax; ++iz)
+     406             :       {
+     407           0 :       double z=ring2z(iz);
+     408             :       I ipix1,nr;
+     409             :       bool shifted;
+     410           0 :       get_ring_info_small(iz,ipix1,nr,shifted);
+     411           0 :       double shift = shifted ? 0.5 : 0.;
+     412             :       rangeset<I2> tr;
+     413           0 :       tr.append(ipix1,ipix1+nr);
+     414           0 :       for (tsize j=0; j<z0.size(); ++j)
+     415             :         {
+     416           0 :         double x = (cosrbig[j]-z*z0[j])*xa[j];
+     417           0 :         double ysq = 1.-z*z-x*x;
+     418           0 :         double dphi = (ysq<=0) ? pi-1e-15 : atan2(sqrt(ysq),x);
+     419           0 :         I ip_lo = ifloor<I>(nr*inv_twopi*(ptg[j].phi-dphi) - shift)+1;
+     420           0 :         I ip_hi = ifloor<I>(nr*inv_twopi*(ptg[j].phi+dphi) - shift);
+     421           0 :         if (fct>1)
+     422             :           {
+     423           0 :           while ((ip_lo<=ip_hi) && check_pixel_ring
+     424           0 :             (*this,b2,ip_lo,nr,ipix1,fct,z0[j],ptg[j].phi,cosrsmall[j],cpix[j]))
+     425           0 :             ++ip_lo;
+     426           0 :           while ((ip_hi>ip_lo) && check_pixel_ring
+     427           0 :             (*this,b2,ip_hi,nr,ipix1,fct,z0[j],ptg[j].phi,cosrsmall[j],cpix[j]))
+     428           0 :             --ip_hi;
+     429             :           }
+     430           0 :         if (ip_hi>=nr)
+     431           0 :           { ip_lo-=nr; ip_hi-=nr;}
+     432           0 :         if (ip_lo<0)
+     433           0 :           tr.remove(ipix1+ip_hi+1,ipix1+ip_lo+nr);
+     434             :         else
+     435           0 :           tr.intersect(ipix1+ip_lo,ipix1+ip_hi+1);
+     436             :         }
+     437           0 :       pixset.append(tr);
+     438             :       }
+     439             :     }
+     440             :   else // scheme_ == NEST
+     441             :     {
+     442             :     int oplus = 0;
+     443           0 :     if (inclusive)
+     444             :       {
+     445           0 :       planck_assert ((I(1)<<(order_max-order_))>=fact,
+     446             :         "invalid oversampling factor");
+     447           0 :       planck_assert ((fact&(fact-1))==0,
+     448             :         "oversampling factor must be a power of 2");
+     449           0 :       oplus=ilog2(fact);
+     450             :       }
+     451           0 :     int omax=order_+oplus; // the order up to which we test
+     452             : 
+     453             :     // TODO: ignore all disks with radius>=pi
+     454             : 
+     455           0 :     arr<T_Healpix_Base<I> > base(omax+1);
+     456             :     arr3<double> crlimit(omax+1,nv,3);
+     457           0 :     for (int o=0; o<=omax; ++o) // prepare data at the required orders
+     458             :       {
+     459           0 :       base[o].Set(o,NEST);
+     460           0 :       double dr=base[o].max_pixrad(); // safety distance
+     461           0 :       for (tsize i=0; i<nv; ++i)
+     462             :         {
+     463           0 :         crlimit(o,i,0) = (rad[i]+dr>pi) ? -1. : cos(rad[i]+dr);
+     464           0 :         crlimit(o,i,1) = (o==0) ? cos(rad[i]) : crlimit(0,i,1);
+     465           0 :         crlimit(o,i,2) = (rad[i]-dr<0.) ?  1. : cos(rad[i]-dr);
+     466             :         }
+     467             :       }
+     468             : 
+     469             :     vector<pair<I,int> > stk; // stack for pixel numbers and their orders
+     470           0 :     stk.reserve(12+3*omax); // reserve maximum size to avoid reallocation
+     471           0 :     for (int i=0; i<12; ++i) // insert the 12 base pixels in reverse order
+     472           0 :       stk.push_back(make_pair(I(11-i),0));
+     473             : 
+     474           0 :     int stacktop=0; // a place to save a stack position
+     475             : 
+     476           0 :     while (!stk.empty()) // as long as there are pixels on the stack
+     477             :       {
+     478             :       // pop current pixel number and order from the stack
+     479           0 :       I pix=stk.back().first;
+     480           0 :       int o=stk.back().second;
+     481             :       stk.pop_back();
+     482             : 
+     483           0 :       vec3 pv(base[o].pix2vec(pix));
+     484             : 
+     485             :       tsize zone=3;
+     486           0 :       for (tsize i=0; i<nv; ++i)
+     487             :         {
+     488             :         double crad=dotprod(pv,norm[i]);
+     489           0 :         for (tsize iz=0; iz<zone; ++iz)
+     490           0 :           if (crad<crlimit(o,i,iz))
+     491           0 :             if ((zone=iz)==0) goto bailout;
+     492             :         }
+     493             : 
+     494           0 :       check_pixel (o, order_, omax, zone, pixset, pix, stk, inclusive,
+     495             :         stacktop);
+     496           0 :       bailout:;
+     497             :       }
+     498             :     }
+     499           0 :   }
+     500             : 
+     501           0 : template<typename I> void T_Healpix_Base<I>::query_multidisc_general
+     502             :   (const arr<vec3> &norm, const arr<double> &rad, bool inclusive,
+     503             :   const vector<int> &cmds, rangeset<I> &pixset) const
+     504             :   {
+     505             :   tsize nv=norm.size();
+     506           0 :   planck_assert(nv==rad.size(),"inconsistent input arrays");
+     507             :   pixset.clear();
+     508             : 
+     509           0 :   if (scheme_==RING)
+     510             :     {
+     511           0 :     planck_fail ("not yet implemented");
+     512             :     }
+     513             :   else // scheme_ == NEST
+     514             :     {
+     515           0 :     int oplus=inclusive ? 2 : 0;
+     516           0 :     int omax=min(order_max,order_+oplus); // the order up to which we test
+     517             : 
+     518             :     // TODO: ignore all disks with radius>=pi
+     519             : 
+     520           0 :     arr<T_Healpix_Base<I> > base(omax+1);
+     521             :     arr3<double> crlimit(omax+1,nv,3);
+     522           0 :     for (int o=0; o<=omax; ++o) // prepare data at the required orders
+     523             :       {
+     524           0 :       base[o].Set(o,NEST);
+     525           0 :       double dr=base[o].max_pixrad(); // safety distance
+     526           0 :       for (tsize i=0; i<nv; ++i)
+     527             :         {
+     528           0 :         crlimit(o,i,0) = (rad[i]+dr>pi) ? -1. : cos(rad[i]+dr);
+     529           0 :         crlimit(o,i,1) = (o==0) ? cos(rad[i]) : crlimit(0,i,1);
+     530           0 :         crlimit(o,i,2) = (rad[i]-dr<0.) ?  1. : cos(rad[i]-dr);
+     531             :         }
+     532             :       }
+     533             : 
+     534             :     vector<pair<I,int> > stk; // stack for pixel numbers and their orders
+     535           0 :     stk.reserve(12+3*omax); // reserve maximum size to avoid reallocation
+     536           0 :     for (int i=0; i<12; ++i) // insert the 12 base pixels in reverse order
+     537           0 :       stk.push_back(make_pair(I(11-i),0));
+     538             : 
+     539           0 :     int stacktop=0; // a place to save a stack position
+     540             :     arr<tsize> zone(nv);
+     541             : 
+     542           0 :     vector<tsize> zstk; zstk.reserve(cmds.size());
+     543             : 
+     544           0 :     while (!stk.empty()) // as long as there are pixels on the stack
+     545             :       {
+     546             :       // pop current pixel number and order from the stack
+     547           0 :       I pix=stk.back().first;
+     548           0 :       int o=stk.back().second;
+     549             :       stk.pop_back();
+     550             : 
+     551           0 :       vec3 pv(base[o].pix2vec(pix));
+     552             : 
+     553           0 :       for (tsize i=0; i<nv; ++i)
+     554             :         {
+     555           0 :         zone[i]=3;
+     556             :         double crad=dotprod(pv,norm[i]);
+     557           0 :         for (tsize iz=0; iz<zone[i]; ++iz)
+     558           0 :           if (crad<crlimit(o,i,iz))
+     559           0 :             zone[i]=iz;
+     560             :         }
+     561             : 
+     562           0 :       for (tsize i=0; i<cmds.size(); ++i)
+     563             :         {
+     564             :         tsize tmp;
+     565           0 :         switch (cmds[i])
+     566             :           {
+     567             :           case -1: // union
+     568           0 :             tmp=zstk.back(); zstk.pop_back();
+     569           0 :             zstk.back() = max(zstk.back(),tmp);
+     570           0 :             break;
+     571             :           case -2: // intersection
+     572           0 :             tmp=zstk.back(); zstk.pop_back();
+     573           0 :             zstk.back() = min(zstk.back(),tmp);
+     574           0 :             break;
+     575             :           default: // add value
+     576           0 :             zstk.push_back(zone[cmds[i]]);
+     577             :           }
+     578             :         }
+     579           0 :       planck_assert(zstk.size()==1,"inconsistent commands");
+     580           0 :       tsize zn=zstk[0]; zstk.pop_back();
+     581             : 
+     582           0 :       check_pixel (o, order_, omax, zn, pixset, pix, stk, inclusive,
+     583             :         stacktop);
+     584             :       }
+     585             :     }
+     586           0 :   }
+     587             : 
+     588             : template<> inline int T_Healpix_Base<int>::spread_bits (int v) const
+     589         421 :   { return utab[v&0xff] | (utab[(v>>8)&0xff]<<16); }
+     590           0 : template<> inline int64 T_Healpix_Base<int64>::spread_bits (int v) const
+     591             :   {
+     592           0 :   return  int64(utab[ v     &0xff])      | (int64(utab[(v>> 8)&0xff])<<16)
+     593           0 :        | (int64(utab[(v>>16)&0xff])<<32) | (int64(utab[(v>>24)&0xff])<<48);
+     594             :   }
+     595             : 
+     596             : template<> inline int T_Healpix_Base<int>::compress_bits (int v) const
+     597             :   {
+     598           0 :   int raw = (v&0x5555) | ((v&0x55550000)>>15);
+     599           0 :   return ctab[raw&0xff] | (ctab[raw>>8]<<4);
+     600             :   }
+     601         842 : template<> inline int T_Healpix_Base<int64>::compress_bits (int64 v) const
+     602             :   {
+     603         842 :   int64 raw = v&0x5555555555555555ull;
+     604         842 :   raw|=raw>>15;
+     605         842 :   return ctab[ raw     &0xff]      | (ctab[(raw>> 8)&0xff]<< 4)
+     606         842 :       | (ctab[(raw>>32)&0xff]<<16) | (ctab[(raw>>40)&0xff]<<20);
+     607             :   }
+     608             : 
+     609         421 : template<typename I> inline void T_Healpix_Base<I>::nest2xyf (I pix, int &ix,
+     610             :   int &iy, int &face_num) const
+     611             :   {
+     612         421 :   face_num = pix>>(2*order_);
+     613         421 :   pix &= (npface_-1);
+     614         421 :   ix = compress_bits(pix);
+     615         421 :   iy = compress_bits(pix>>1);
+     616         421 :   }
+     617             : 
+     618         421 : template<typename I> inline I T_Healpix_Base<I>::xyf2nest (int ix, int iy,
+     619             :   int face_num) const
+     620         421 :   { return (I(face_num)<<(2*order_)) + spread_bits(ix) + (spread_bits(iy)<<1); }
+     621             : 
+     622         421 : template<typename I> void T_Healpix_Base<I>::ring2xyf (I pix, int &ix, int &iy,
+     623             :   int &face_num) const
+     624             :   {
+     625             :   I iring, iphi, kshift, nr;
+     626         421 :   I nl2 = 2*nside_;
+     627             : 
+     628         421 :   if (pix<ncap_) // North Polar cap
+     629             :     {
+     630           0 :     iring = (1+isqrt(1+2*pix))>>1; //counted from North pole
+     631           0 :     iphi  = (pix+1) - 2*iring*(iring-1);
+     632             :     kshift = 0;
+     633             :     nr = iring;
+     634           0 :     face_num=(iphi-1)/nr;
+     635             :     }
+     636         421 :   else if (pix<(npix_-ncap_)) // Equatorial region
+     637             :     {
+     638         421 :     I ip = pix - ncap_;
+     639         421 :     I tmp = (order_>=0) ? ip>>(order_+2) : ip/(4*nside_);
+     640         421 :     iring = tmp+nside_;
+     641         421 :     iphi = ip-tmp*4*nside_ + 1;
+     642         421 :     kshift = (iring+nside_)&1;
+     643             :     nr = nside_;
+     644         421 :     I ire = iring-nside_+1,
+     645         421 :       irm = nl2+2-ire;
+     646         421 :     I ifm = iphi - ire/2 + nside_ -1,
+     647         421 :       ifp = iphi - irm/2 + nside_ -1;
+     648         421 :     if (order_>=0)
+     649         421 :       { ifm >>= order_; ifp >>= order_; }
+     650             :     else
+     651           0 :       { ifm /= nside_; ifp /= nside_; }
+     652         421 :     face_num = (ifp==ifm) ? (ifp|4) : ((ifp<ifm) ? ifp : (ifm+8));
+     653             :     }
+     654             :   else // South Polar cap
+     655             :     {
+     656           0 :     I ip = npix_ - pix;
+     657           0 :     iring = (1+isqrt(2*ip-1))>>1; //counted from South pole
+     658           0 :     iphi  = 4*iring + 1 - (ip - 2*iring*(iring-1));
+     659             :     kshift = 0;
+     660             :     nr = iring;
+     661           0 :     iring = 2*nl2-iring;
+     662           0 :     face_num = 8 + (iphi-1)/nr;
+     663             :     }
+     664             : 
+     665         421 :   I irt = iring - (jrll[face_num]*nside_) + 1;
+     666         421 :   I ipt = 2*iphi- jpll[face_num]*nr - kshift -1;
+     667         421 :   if (ipt>=nl2) ipt-=8*nside_;
+     668             : 
+     669         421 :   ix =  (ipt-irt) >>1;
+     670         421 :   iy = (-ipt-irt) >>1;
+     671         421 :   }
+     672             : 
+     673           0 : template<typename I> I T_Healpix_Base<I>::xyf2ring (int ix, int iy,
+     674             :   int face_num) const
+     675             :   {
+     676           0 :   I nl4 = 4*nside_;
+     677           0 :   I jr = (jrll[face_num]*nside_) - ix - iy  - 1;
+     678             : 
+     679             :   I nr, kshift, n_before;
+     680             : 
+     681             :   bool shifted;
+     682           0 :   get_ring_info_small(jr,n_before,nr,shifted);
+     683           0 :   nr>>=2;
+     684           0 :   kshift=1-shifted;
+     685           0 :   I jp = (jpll[face_num]*nr + ix - iy + 1 + kshift) / 2;
+     686           0 :   planck_assert(jp<=4*nr,"must not happen");
+     687           0 :   if (jp<1) jp+=nl4; // assumption: if this triggers, then nl4==4*nr
+     688             : 
+     689           0 :   return n_before + jp - 1;
+     690             :   }
+     691             : 
+     692           0 : template<typename I> T_Healpix_Base<I>::T_Healpix_Base ()
+     693           0 :   : order_(-1), nside_(0), npface_(0), ncap_(0), npix_(0),
+     694           0 :     fact1_(0), fact2_(0), scheme_(RING) {}
+     695             : 
+     696          29 : template<typename I> void T_Healpix_Base<I>::Set (int order,
+     697             :   Healpix_Ordering_Scheme scheme)
+     698             :   {
+     699          29 :   planck_assert ((order>=0)&&(order<=order_max), "bad order");
+     700          29 :   order_  = order;
+     701          29 :   nside_  = I(1)<<order;
+     702          29 :   npface_ = nside_<<order_;
+     703          29 :   ncap_   = (npface_-nside_)<<1;
+     704          29 :   npix_   = 12*npface_;
+     705          29 :   fact2_  = 4./npix_;
+     706          29 :   fact1_  = (nside_<<1)*fact2_;
+     707          29 :   scheme_ = scheme;
+     708          29 :   }
+     709           0 : template<typename I> void T_Healpix_Base<I>::SetNside (I nside,
+     710             :   Healpix_Ordering_Scheme scheme)
+     711             :   {
+     712           0 :   order_  = nside2order(nside);
+     713           0 :   planck_assert ((scheme!=NEST) || (order_>=0),
+     714             :     "SetNside: nside must be power of 2 for nested maps");
+     715           0 :   nside_  = nside;
+     716           0 :   npface_ = nside_*nside_;
+     717           0 :   ncap_   = (npface_-nside_)<<1;
+     718           0 :   npix_   = 12*npface_;
+     719           0 :   fact2_  = 4./npix_;
+     720           0 :   fact1_  = (nside_<<1)*fact2_;
+     721           0 :   scheme_ = scheme;
+     722           0 :   }
+     723             : 
+     724           0 : template<typename I> double T_Healpix_Base<I>::ring2z (I ring) const
+     725             :   {
+     726           0 :   if (ring<nside_)
+     727           0 :     return 1 - ring*ring*fact2_;
+     728           0 :   if (ring <=3*nside_)
+     729           0 :     return (2*nside_-ring)*fact1_;
+     730           0 :   ring=4*nside_ - ring;
+     731           0 :   return ring*ring*fact2_ - 1;
+     732             :   }
+     733             : 
+     734           0 : template<typename I> I T_Healpix_Base<I>::pix2ring (I pix) const
+     735             :   {
+     736           0 :   if (scheme_==RING)
+     737             :     {
+     738           0 :     if (pix<ncap_) // North Polar cap
+     739           0 :       return (1+I(isqrt(1+2*pix)))>>1; // counted from North pole
+     740           0 :     else if (pix<(npix_-ncap_)) // Equatorial region
+     741           0 :       return (pix-ncap_)/(4*nside_) + nside_; // counted from North pole
+     742             :     else // South Polar cap
+     743           0 :       return 4*nside_-((1+I(isqrt(2*(npix_-pix)-1)))>>1);
+     744             :     }
+     745             :   else
+     746             :     {
+     747             :     int face_num, ix, iy;
+     748           0 :     nest2xyf(pix,ix,iy,face_num);
+     749           0 :     return (I(jrll[face_num])<<order_) - ix - iy - 1;
+     750             :     }
+     751             :   }
+     752             : 
+     753           0 : template<typename I> I T_Healpix_Base<I>::nest2ring (I pix) const
+     754             :   {
+     755           0 :   planck_assert(order_>=0, "hierarchical map required");
+     756             :   int ix, iy, face_num;
+     757           0 :   nest2xyf (pix, ix, iy, face_num);
+     758           0 :   return xyf2ring (ix, iy, face_num);
+     759             :   }
+     760             : 
+     761         421 : template<typename I> I T_Healpix_Base<I>::ring2nest (I pix) const
+     762             :   {
+     763         421 :   planck_assert(order_>=0, "hierarchical map required");
+     764             :   int ix, iy, face_num;
+     765         421 :   ring2xyf (pix, ix, iy, face_num);
+     766         421 :   return xyf2nest (ix, iy, face_num);
+     767             :   }
+     768             : 
+     769           0 : template<typename I> inline I T_Healpix_Base<I>::nest_peano_helper
+     770             :   (I pix, int dir) const
+     771             :   {
+     772           0 :   int face = pix>>(2*order_);
+     773             :   I result = 0;
+     774           0 :   uint8 path = peano_face2path[dir][face];
+     775             : 
+     776           0 :   for (int shift=2*order_-2; shift>=0; shift-=2)
+     777             :     {
+     778           0 :     uint8 spix = uint8((pix>>shift) & 0x3);
+     779           0 :     result <<= 2;
+     780           0 :     result |= peano_subpix[dir][path][spix];
+     781           0 :     path=peano_subpath[dir][path][spix];
+     782             :     }
+     783             : 
+     784           0 :   return result + (I(peano_face2face[dir][face])<<(2*order_));
+     785             :   }
+     786             : 
+     787           0 : template<typename I> I T_Healpix_Base<I>::nest2peano (I pix) const
+     788           0 :   { return nest_peano_helper(pix,0); }
+     789             : 
+     790           0 : template<typename I> I T_Healpix_Base<I>::peano2nest (I pix) const
+     791           0 :   { return nest_peano_helper(pix,1); }
+     792             : 
+     793       24585 : template<typename I> I T_Healpix_Base<I>::loc2pix (double z, double phi,
+     794             :   double sth, bool have_sth) const
+     795             :   {
+     796             :   double za = abs(z);
+     797       24585 :   double tt = fmodulo(phi*inv_halfpi,4.0); // in [0,4)
+     798             : 
+     799       24585 :   if (scheme_==RING)
+     800             :     {
+     801       24585 :     if (za<=twothird) // Equatorial region
+     802             :       {
+     803       16535 :       I nl4 = 4*nside_;
+     804       16535 :       double temp1 = nside_*(0.5+tt);
+     805       16535 :       double temp2 = nside_*z*0.75;
+     806       16535 :       I jp = I(temp1-temp2); // index of  ascending edge line
+     807       16535 :       I jm = I(temp1+temp2); // index of descending edge line
+     808             : 
+     809             :       // ring number counted from z=2/3
+     810       16535 :       I ir = nside_ + 1 + jp - jm; // in {1,2n+1}
+     811       16535 :       I kshift = 1-(ir&1); // kshift=1 if ir even, 0 otherwise
+     812             : 
+     813       16535 :       I t1 = jp+jm-nside_+kshift+1+nl4+nl4;
+     814       16535 :       I ip = (order_>0) ?
+     815       16535 :         (t1>>1)&(nl4-1) : ((t1>>1)%nl4); // in {0,4n-1}
+     816             : 
+     817       16535 :       return ncap_ + (ir-1)*nl4 + ip;
+     818             :       }
+     819             :     else  // North & South polar caps
+     820             :       {
+     821        8050 :       double tp = tt-I(tt);
+     822        8050 :       double tmp = ((za<0.99)||(!have_sth)) ?
+     823        7809 :                    nside_*sqrt(3*(1-za)) :
+     824         241 :                    nside_*sth/sqrt((1.+za)/3.);
+     825             : 
+     826        8050 :       I jp = I(tp*tmp); // increasing edge line index
+     827        8050 :       I jm = I((1.0-tp)*tmp); // decreasing edge line index
+     828             : 
+     829        8050 :       I ir = jp+jm+1; // ring number counted from the closest pole
+     830        8050 :       I ip = I(tt*ir); // in {0,4*ir-1}
+     831        8050 :       planck_assert((ip>=0)&&(ip<4*ir),"must not happen");
+     832             :       //ip %= 4*ir;
+     833             : 
+     834        8050 :       return (z>0)  ?  2*ir*(ir-1) + ip  :  npix_ - 2*ir*(ir+1) + ip;
+     835             :       }
+     836             :     }
+     837             :   else // scheme_ == NEST
+     838             :     {
+     839           0 :     if (za<=twothird) // Equatorial region
+     840             :       {
+     841           0 :       double temp1 = nside_*(0.5+tt);
+     842           0 :       double temp2 = nside_*(z*0.75);
+     843           0 :       I jp = I(temp1-temp2); // index of  ascending edge line
+     844           0 :       I jm = I(temp1+temp2); // index of descending edge line
+     845           0 :       I ifp = jp >> order_;  // in {0,4}
+     846           0 :       I ifm = jm >> order_;
+     847           0 :       int face_num = (ifp==ifm) ? (ifp|4) : ((ifp<ifm) ? ifp : (ifm+8));
+     848             : 
+     849           0 :       int ix = jm & (nside_-1),
+     850           0 :           iy = nside_ - (jp & (nside_-1)) - 1;
+     851           0 :       return xyf2nest(ix,iy,face_num);
+     852             :       }
+     853             :     else // polar region, za > 2/3
+     854             :       {
+     855           0 :       int ntt = min(3,int(tt));
+     856           0 :       double tp = tt-ntt;
+     857           0 :       double tmp = ((za<0.99)||(!have_sth)) ?
+     858           0 :                    nside_*sqrt(3*(1-za)) :
+     859           0 :                    nside_*sth/sqrt((1.+za)/3.);
+     860             : 
+     861           0 :       I jp = I(tp*tmp); // increasing edge line index
+     862           0 :       I jm = I((1.0-tp)*tmp); // decreasing edge line index
+     863           0 :       jp=min(jp,nside_-1); // for points too close to the boundary
+     864           0 :       jm=min(jm,nside_-1);
+     865           0 :       return (z>=0) ?
+     866           0 :         xyf2nest(nside_-jm -1,nside_-jp-1,ntt) : xyf2nest(jp,jm,ntt+8);
+     867             :       }
+     868             :     }
+     869             :   }
+     870             : 
+     871      135593 : template<typename I> void T_Healpix_Base<I>::pix2loc (I pix, double &z,
+     872             :   double &phi, double &sth, bool &have_sth) const
+     873             :   {
+     874      135593 :   have_sth=false;
+     875      135593 :   if (scheme_==RING)
+     876             :     {
+     877      135172 :     if (pix<ncap_) // North Polar cap
+     878             :       {
+     879       22080 :       I iring = (1+I(isqrt(1+2*pix)))>>1; // counted from North pole
+     880       22080 :       I iphi  = (pix+1) - 2*iring*(iring-1);
+     881             : 
+     882       22080 :       double tmp=(iring*iring)*fact2_;
+     883       22080 :       z = 1.0 - tmp;
+     884       22080 :       if (z>0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
+     885       22080 :       phi = (iphi-0.5) * halfpi/iring;
+     886             :       }
+     887      113092 :     else if (pix<(npix_-ncap_)) // Equatorial region
+     888             :       {
+     889       91010 :       I nl4 = 4*nside_;
+     890       91010 :       I ip  = pix - ncap_;
+     891       91010 :       I tmp = (order_>=0) ? ip>>(order_+2) : ip/nl4;
+     892       91010 :       I iring = tmp + nside_,
+     893       91010 :         iphi = ip-nl4*tmp+1;
+     894             :       // 1 if iring+nside is odd, 1/2 otherwise
+     895       91010 :       double fodd = ((iring+nside_)&1) ? 1 : 0.5;
+     896             : 
+     897       91010 :       z = (2*nside_-iring)*fact1_;
+     898       91010 :       phi = (iphi-fodd) * pi*0.75*fact1_;
+     899             :       }
+     900             :     else // South Polar cap
+     901             :       {
+     902       22082 :       I ip = npix_ - pix;
+     903       22082 :       I iring = (1+I(isqrt(2*ip-1)))>>1; // counted from South pole
+     904       22082 :       I iphi  = 4*iring + 1 - (ip - 2*iring*(iring-1));
+     905             : 
+     906       22082 :       double tmp=(iring*iring)*fact2_;
+     907       22082 :       z = tmp - 1.0;
+     908       22082 :       if (z<-0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
+     909       22082 :       phi = (iphi-0.5) * halfpi/iring;
+     910             :       }
+     911             :     }
+     912             :   else
+     913             :     {
+     914             :     int face_num, ix, iy;
+     915         421 :     nest2xyf(pix,ix,iy,face_num);
+     916             : 
+     917         421 :     I jr = (I(jrll[face_num])<<order_) - ix - iy - 1;
+     918             : 
+     919             :     I nr;
+     920         421 :     if (jr<nside_)
+     921             :       {
+     922             :       nr = jr;
+     923           0 :       double tmp=(nr*nr)*fact2_;
+     924           0 :       z = 1 - tmp;
+     925           0 :       if (z>0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
+     926             :       }
+     927         421 :     else if (jr > 3*nside_)
+     928             :       {
+     929           0 :       nr = nside_*4-jr;
+     930           0 :       double tmp=(nr*nr)*fact2_;
+     931           0 :       z = tmp - 1;
+     932           0 :       if (z<-0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
+     933             :       }
+     934             :     else
+     935             :       {
+     936             :       nr = nside_;
+     937         421 :       z = (2*nside_-jr)*fact1_;
+     938             :       }
+     939             : 
+     940         421 :     I tmp=I(jpll[face_num])*nr+ix-iy;
+     941         421 :     planck_assert(tmp<8*nr,"must not happen");
+     942         421 :     if (tmp<0) tmp+=8*nr;
+     943         421 :     phi = (nr==nside_) ? 0.75*halfpi*tmp*fact1_ :
+     944           0 :                          (0.5*halfpi*tmp)/nr;
+     945             :     }
+     946      135593 :   }
+     947             : 
+     948             : template<typename I> template<typename I2>
+     949           0 :   void T_Healpix_Base<I>::query_polygon_internal
+     950             :   (const vector<pointing> &vertex, int fact, rangeset<I2> &pixset) const
+     951             :   {
+     952             :   bool inclusive = (fact!=0);
+     953             :   tsize nv=vertex.size();
+     954           0 :   tsize ncirc = inclusive ? nv+1 : nv;
+     955           0 :   planck_assert(nv>=3,"not enough vertices in polygon");
+     956             :   arr<vec3> vv(nv);
+     957           0 :   for (tsize i=0; i<nv; ++i)
+     958           0 :     vv[i]=vertex[i].to_vec3();
+     959             :   arr<vec3> normal(ncirc);
+     960             :   int flip=0;
+     961           0 :   for (tsize i=0; i<nv; ++i)
+     962             :     {
+     963           0 :     normal[i]=crossprod(vv[i],vv[(i+1)%nv]);
+     964           0 :     double hnd=dotprod(normal[i],vv[(i+2)%nv]);
+     965           0 :     planck_assert(abs(hnd)>1e-10,"degenerate corner");
+     966           0 :     if (i==0)
+     967           0 :       flip = (hnd<0.) ? -1 : 1;
+     968             :     else
+     969           0 :       planck_assert(flip*hnd>0,"polygon is not convex");
+     970           0 :     normal[i]*=flip/normal[i].Length();
+     971             :     }
+     972             :   arr<double> rad(ncirc,halfpi);
+     973           0 :   if (inclusive)
+     974             :     {
+     975             :     double cosrad;
+     976           0 :     find_enclosing_circle (vv, normal[nv], cosrad);
+     977           0 :     rad[nv]=acos(cosrad);
+     978             :     }
+     979           0 :   query_multidisc(normal,rad,fact,pixset);
+     980           0 :   }
+     981             : 
+     982           0 : template<typename I> void T_Healpix_Base<I>::query_polygon
+     983             :   (const vector<pointing> &vertex, rangeset<I> &pixset) const
+     984             :   {
+     985           0 :   query_polygon_internal(vertex, 0, pixset);
+     986           0 :   }
+     987             : 
+     988           0 : template<typename I> void T_Healpix_Base<I>::query_polygon_inclusive
+     989             :   (const vector<pointing> &vertex, rangeset<I> &pixset, int fact) const
+     990             :   {
+     991           0 :   planck_assert(fact>0,"fact must be a positive integer");
+     992           0 :   if ((sizeof(I)<8) && (((I(1)<<order_max)/nside_)<fact))
+     993             :     {
+     994           0 :     T_Healpix_Base<int64> base2(nside_,scheme_,SET_NSIDE);
+     995           0 :     base2.query_polygon_internal(vertex,fact,pixset);
+     996             :     return;
+     997             :     }
+     998           0 :   query_polygon_internal(vertex, fact, pixset);
+     999             :   }
+    1000             : 
+    1001           0 : template<typename I> void T_Healpix_Base<I>::query_strip_internal
+    1002             :   (double theta1, double theta2, bool inclusive, rangeset<I> &pixset) const
+    1003             :   {
+    1004           0 :   if (scheme_==RING)
+    1005             :     {
+    1006           0 :     I ring1 = max(I(1),1+ring_above(cos(theta1))),
+    1007           0 :       ring2 = min(4*nside_-1,ring_above(cos(theta2)));
+    1008           0 :     if (inclusive)
+    1009             :       {
+    1010           0 :       ring1 = max(I(1),ring1-1);
+    1011           0 :       ring2 = min(4*nside_-1,ring2+1);
+    1012             :       }
+    1013             : 
+    1014             :     I sp1,rp1,sp2,rp2;
+    1015             :     bool dummy;
+    1016           0 :     get_ring_info_small(ring1,sp1,rp1,dummy);
+    1017           0 :     get_ring_info_small(ring2,sp2,rp2,dummy);
+    1018           0 :     I pix1 = sp1,
+    1019           0 :       pix2 = sp2+rp2;
+    1020           0 :     if (pix1<=pix2) pixset.append(pix1,pix2);
+    1021             :     }
+    1022             :   else
+    1023           0 :     planck_fail("query_strip not yet implemented for NESTED");
+    1024           0 :   }
+    1025             : 
+    1026           0 : template<typename I> void T_Healpix_Base<I>::query_strip (double theta1,
+    1027             :   double theta2, bool inclusive, rangeset<I> &pixset) const
+    1028             :   {
+    1029             :   pixset.clear();
+    1030             : 
+    1031           0 :   if (theta1<theta2)
+    1032           0 :     query_strip_internal(theta1,theta2,inclusive,pixset);
+    1033             :   else
+    1034             :     {
+    1035           0 :     query_strip_internal(0.,theta2,inclusive,pixset);
+    1036             :     rangeset<I> ps2;
+    1037           0 :     query_strip_internal(theta1,pi,inclusive,ps2);
+    1038           0 :     pixset.append(ps2);
+    1039             :     }
+    1040           0 :   }
+    1041             : 
+    1042           0 : template<typename I> inline void T_Healpix_Base<I>::get_ring_info_small
+    1043             :   (I ring, I &startpix, I &ringpix, bool &shifted) const
+    1044             :   {
+    1045           0 :   if (ring < nside_)
+    1046             :     {
+    1047           0 :     shifted = true;
+    1048           0 :     ringpix = 4*ring;
+    1049           0 :     startpix = 2*ring*(ring-1);
+    1050             :     }
+    1051           0 :   else if (ring < 3*nside_)
+    1052             :     {
+    1053           0 :     shifted = ((ring-nside_) & 1) == 0;
+    1054           0 :     ringpix = 4*nside_;
+    1055           0 :     startpix = ncap_ + (ring-nside_)*ringpix;
+    1056             :     }
+    1057             :   else
+    1058             :     {
+    1059           0 :     shifted = true;
+    1060           0 :     I nr= 4*nside_-ring;
+    1061           0 :     ringpix = 4*nr;
+    1062           0 :     startpix = npix_-2*nr*(nr+1);
+    1063             :     }
+    1064           0 :   }
+    1065             : 
+    1066           0 : template<typename I> void T_Healpix_Base<I>::get_ring_info (I ring, I &startpix,
+    1067             :   I &ringpix, double &costheta, double &sintheta, bool &shifted) const
+    1068             :   {
+    1069           0 :   I northring = (ring>2*nside_) ? 4*nside_-ring : ring;
+    1070           0 :   if (northring < nside_)
+    1071             :     {
+    1072           0 :     double tmp = northring*northring*fact2_;
+    1073           0 :     costheta = 1 - tmp;
+    1074           0 :     sintheta = sqrt(tmp*(2-tmp));
+    1075           0 :     ringpix = 4*northring;
+    1076           0 :     shifted = true;
+    1077           0 :     startpix = 2*northring*(northring-1);
+    1078             :     }
+    1079             :   else
+    1080             :     {
+    1081           0 :     costheta = (2*nside_-northring)*fact1_;
+    1082           0 :     sintheta = sqrt((1+costheta)*(1-costheta));
+    1083           0 :     ringpix = 4*nside_;
+    1084           0 :     shifted = ((northring-nside_) & 1) == 0;
+    1085           0 :     startpix = ncap_ + (northring-nside_)*ringpix;
+    1086             :     }
+    1087           0 :   if (northring != ring) // southern hemisphere
+    1088             :     {
+    1089           0 :     costheta = -costheta;
+    1090           0 :     startpix = npix_ - startpix - ringpix;
+    1091             :     }
+    1092           0 :   }
+    1093           0 : template<typename I> void T_Healpix_Base<I>::get_ring_info2 (I ring,
+    1094             :   I &startpix, I &ringpix, double &theta, bool &shifted) const
+    1095             :   {
+    1096           0 :   I northring = (ring>2*nside_) ? 4*nside_-ring : ring;
+    1097           0 :   if (northring < nside_)
+    1098             :     {
+    1099           0 :     double tmp = northring*northring*fact2_;
+    1100           0 :     double costheta = 1 - tmp;
+    1101           0 :     double sintheta = sqrt(tmp*(2-tmp));
+    1102           0 :     theta = atan2(sintheta,costheta);
+    1103           0 :     ringpix = 4*northring;
+    1104           0 :     shifted = true;
+    1105           0 :     startpix = 2*northring*(northring-1);
+    1106             :     }
+    1107             :   else
+    1108             :     {
+    1109           0 :     theta = acos((2*nside_-northring)*fact1_);
+    1110           0 :     ringpix = 4*nside_;
+    1111           0 :     shifted = ((northring-nside_) & 1) == 0;
+    1112           0 :     startpix = ncap_ + (northring-nside_)*ringpix;
+    1113             :     }
+    1114           0 :   if (northring != ring) // southern hemisphere
+    1115             :     {
+    1116           0 :     theta = pi-theta;
+    1117           0 :     startpix = npix_ - startpix - ringpix;
+    1118             :     }
+    1119           0 :   }
+    1120             : 
+    1121           0 : template<typename I> void T_Healpix_Base<I>::neighbors (I pix,
+    1122             :   fix_arr<I,8> &result) const
+    1123             :   {
+    1124             :   int ix, iy, face_num;
+    1125           0 :   (scheme_==RING) ?
+    1126           0 :     ring2xyf(pix,ix,iy,face_num) : nest2xyf(pix,ix,iy,face_num);
+    1127             : 
+    1128           0 :   const I nsm1 = nside_-1;
+    1129           0 :   if ((ix>0)&&(ix<nsm1)&&(iy>0)&&(iy<nsm1))
+    1130             :     {
+    1131           0 :     if (scheme_==RING)
+    1132           0 :       for (int m=0; m<8; ++m)
+    1133           0 :         result[m] = xyf2ring(ix+nb_xoffset[m],iy+nb_yoffset[m],face_num);
+    1134             :     else
+    1135             :       {
+    1136           0 :       I fpix = I(face_num)<<(2*order_),
+    1137           0 :         px0=spread_bits(ix  ), py0=spread_bits(iy  )<<1,
+    1138           0 :         pxp=spread_bits(ix+1), pyp=spread_bits(iy+1)<<1,
+    1139           0 :         pxm=spread_bits(ix-1), pym=spread_bits(iy-1)<<1;
+    1140             : 
+    1141           0 :       result[0] = fpix+pxm+py0; result[1] = fpix+pxm+pyp;
+    1142           0 :       result[2] = fpix+px0+pyp; result[3] = fpix+pxp+pyp;
+    1143           0 :       result[4] = fpix+pxp+py0; result[5] = fpix+pxp+pym;
+    1144           0 :       result[6] = fpix+px0+pym; result[7] = fpix+pxm+pym;
+    1145             :       }
+    1146             :     }
+    1147             :   else
+    1148             :     {
+    1149           0 :     for (int i=0; i<8; ++i)
+    1150             :       {
+    1151           0 :       int x=ix+nb_xoffset[i], y=iy+nb_yoffset[i];
+    1152             :       int nbnum=4;
+    1153           0 :       if (x<0)
+    1154           0 :         { x+=nside_; nbnum-=1; }
+    1155           0 :       else if (x>=nside_)
+    1156           0 :         { x-=nside_; nbnum+=1; }
+    1157           0 :       if (y<0)
+    1158           0 :         { y+=nside_; nbnum-=3; }
+    1159           0 :       else if (y>=nside_)
+    1160           0 :         { y-=nside_; nbnum+=3; }
+    1161             : 
+    1162           0 :       int f = nb_facearray[nbnum][face_num];
+    1163           0 :       if (f>=0)
+    1164             :         {
+    1165           0 :         int bits = nb_swaparray[nbnum][face_num>>2];
+    1166           0 :         if (bits&1) x=nside_-x-1;
+    1167           0 :         if (bits&2) y=nside_-y-1;
+    1168           0 :         if (bits&4) std::swap(x,y);
+    1169           0 :         result[i] = (scheme_==RING) ? xyf2ring(x,y,f) : xyf2nest(x,y,f);
+    1170             :         }
+    1171             :       else
+    1172           0 :         result[i] = -1;
+    1173             :       }
+    1174             :     }
+    1175           0 :   }
+    1176             : 
+    1177           0 : template<typename I> void T_Healpix_Base<I>::get_interpol (const pointing &ptg,
+    1178             :   fix_arr<I,4> &pix, fix_arr<double,4> &wgt) const
+    1179             :   {
+    1180           0 :   planck_assert((ptg.theta>=0)&&(ptg.theta<=pi),"invalid theta value");
+    1181           0 :   double z = cos (ptg.theta);
+    1182           0 :   I ir1 = ring_above(z);
+    1183           0 :   I ir2 = ir1+1;
+    1184             :   double theta1, theta2, w1, tmp, dphi;
+    1185             :   I sp,nr;
+    1186             :   bool shift;
+    1187             :   I i1,i2;
+    1188           0 :   if (ir1>0)
+    1189             :     {
+    1190           0 :     get_ring_info2 (ir1, sp, nr, theta1, shift);
+    1191           0 :     dphi = twopi/nr;
+    1192           0 :     tmp = (ptg.phi/dphi - .5*shift);
+    1193           0 :     i1 = (tmp<0) ? I(tmp)-1 : I(tmp);
+    1194           0 :     w1 = (ptg.phi-(i1+.5*shift)*dphi)/dphi;
+    1195           0 :     i2 = i1+1;
+    1196           0 :     if (i1<0) i1 +=nr;
+    1197           0 :     if (i2>=nr) i2 -=nr;
+    1198           0 :     pix[0] = sp+i1; pix[1] = sp+i2;
+    1199           0 :     wgt[0] = 1-w1; wgt[1] = w1;
+    1200             :     }
+    1201           0 :   if (ir2<(4*nside_))
+    1202             :     {
+    1203           0 :     get_ring_info2 (ir2, sp, nr, theta2, shift);
+    1204           0 :     dphi = twopi/nr;
+    1205           0 :     tmp = (ptg.phi/dphi - .5*shift);
+    1206           0 :     i1 = (tmp<0) ? I(tmp)-1 : I(tmp);
+    1207           0 :     w1 = (ptg.phi-(i1+.5*shift)*dphi)/dphi;
+    1208           0 :     i2 = i1+1;
+    1209           0 :     if (i1<0) i1 +=nr;
+    1210           0 :     if (i2>=nr) i2 -=nr;
+    1211           0 :     pix[2] = sp+i1; pix[3] = sp+i2;
+    1212           0 :     wgt[2] = 1-w1; wgt[3] = w1;
+    1213             :     }
+    1214             : 
+    1215           0 :   if (ir1==0)
+    1216             :     {
+    1217           0 :     double wtheta = ptg.theta/theta2;
+    1218           0 :     wgt[2] *= wtheta; wgt[3] *= wtheta;
+    1219           0 :     double fac = (1-wtheta)*0.25;
+    1220           0 :     wgt[0] = fac; wgt[1] = fac; wgt[2] += fac; wgt[3] +=fac;
+    1221           0 :     pix[0] = (pix[2]+2)&3;
+    1222           0 :     pix[1] = (pix[3]+2)&3;
+    1223             :     }
+    1224           0 :   else if (ir2==4*nside_)
+    1225             :     {
+    1226           0 :     double wtheta = (ptg.theta-theta1)/(pi-theta1);
+    1227           0 :     wgt[0] *= (1-wtheta); wgt[1] *= (1-wtheta);
+    1228           0 :     double fac = wtheta*0.25;
+    1229           0 :     wgt[0] += fac; wgt[1] += fac; wgt[2] = fac; wgt[3] =fac;
+    1230           0 :     pix[2] = ((pix[0]+2)&3)+npix_-4;
+    1231           0 :     pix[3] = ((pix[1]+2)&3)+npix_-4;
+    1232             :     }
+    1233             :   else
+    1234             :     {
+    1235           0 :     double wtheta = (ptg.theta-theta1)/(theta2-theta1);
+    1236           0 :     wgt[0] *= (1-wtheta); wgt[1] *= (1-wtheta);
+    1237           0 :     wgt[2] *= wtheta; wgt[3] *= wtheta;
+    1238             :     }
+    1239             : 
+    1240           0 :   if (scheme_==NEST)
+    1241           0 :     for (tsize m=0; m<pix.size(); ++m)
+    1242           0 :       pix[m] = ring2nest(pix[m]);
+    1243           0 :   }
+    1244             : 
+    1245           0 : template<typename I> void T_Healpix_Base<I>::swap (T_Healpix_Base &other)
+    1246             :   {
+    1247             :   std::swap(order_,other.order_);
+    1248             :   std::swap(nside_,other.nside_);
+    1249             :   std::swap(npface_,other.npface_);
+    1250             :   std::swap(ncap_,other.ncap_);
+    1251             :   std::swap(npix_,other.npix_);
+    1252             :   std::swap(fact1_,other.fact1_);
+    1253             :   std::swap(fact2_,other.fact2_);
+    1254             :   std::swap(scheme_,other.scheme_);
+    1255           0 :   }
+    1256             : 
+    1257           0 : template<typename I> double T_Healpix_Base<I>::max_pixrad() const
+    1258             :   {
+    1259             :   vec3 va,vb;
+    1260           0 :   va.set_z_phi (2./3., pi/(4*nside_));
+    1261           0 :   double t1 = 1.-1./nside_;
+    1262           0 :   t1*=t1;
+    1263           0 :   vb.set_z_phi (1-t1/3, 0);
+    1264           0 :   return v_angle(va,vb);
+    1265             :   }
+    1266             : 
+    1267           0 : template<typename I> double T_Healpix_Base<I>::max_pixrad(I ring) const
+    1268             :   {
+    1269           0 :   if (ring>=2*nside_) ring=4*nside_-ring;
+    1270           0 :   double z=ring2z(ring), z_up=(ring>1) ? ring2z(ring-1) : 1.;
+    1271             :   vec3 mypos, uppos;
+    1272           0 :   uppos.set_z_phi(z_up,0);
+    1273           0 :   if (ring<=nside_)
+    1274             :     {
+    1275           0 :     mypos.set_z_phi(z,pi/(4*ring));
+    1276           0 :     return v_angle(mypos,uppos);
+    1277             :     }
+    1278           0 :   mypos.set_z_phi(z,0);
+    1279           0 :   double vdist=v_angle(mypos,uppos);
+    1280           0 :   double hdist=sqrt(1.-z*z)*pi/(4*nside_);
+    1281           0 :   return max(hdist,vdist);
+    1282             :   }
+    1283             : 
+    1284           0 : template<typename I> void T_Healpix_Base<I>::xyf2loc (double x, double y,
+    1285             :   int face, double &z, double &phi, double &sth, bool &have_sth) const
+    1286             :   {
+    1287           0 :   have_sth = false;
+    1288           0 :   double jr = jrll[face] - x - y;
+    1289             :   double nr;
+    1290           0 :   if (jr<1)
+    1291             :     {
+    1292             :     nr = jr;
+    1293           0 :     double tmp = nr*nr/3.;
+    1294           0 :     z = 1 - tmp;
+    1295           0 :     if (z > 0.99)
+    1296             :       {
+    1297           0 :       sth = std::sqrt(tmp*(2.0-tmp));
+    1298           0 :       have_sth = true;
+    1299             :       }
+    1300             :     }
+    1301           0 :   else if (jr>3)
+    1302             :     {
+    1303           0 :     nr = 4-jr;
+    1304           0 :     double tmp = nr*nr/3.;
+    1305           0 :     z = tmp - 1;
+    1306           0 :     if (z<-0.99)
+    1307             :       {
+    1308           0 :       sth = std::sqrt(tmp*(2.-tmp));
+    1309           0 :       have_sth = true;
+    1310             :       }
+    1311             :     }
+    1312             :   else
+    1313             :     {
+    1314             :     nr = 1;
+    1315           0 :     z = (2-jr)*2./3.;
+    1316             :     }
+    1317             : 
+    1318           0 :   double tmp=jpll[face]*nr+x-y;
+    1319           0 :   if (tmp<0) tmp+=8;
+    1320           0 :   if (tmp>=8) tmp-=8;
+    1321           0 :   phi = (nr<1e-15) ? 0 : (0.5*halfpi*tmp)/nr;
+    1322           0 :   }
+    1323             : 
+    1324             : namespace {
+    1325             : 
+    1326           0 : vec3 locToVec3 (double z, double phi, double sth, bool have_sth)
+    1327             :   {
+    1328           0 :   if (have_sth)
+    1329           0 :     return vec3(sth*cos(phi),sth*sin(phi),z);
+    1330             :   else
+    1331             :     {
+    1332             :     vec3 res;
+    1333           0 :     res.set_z_phi (z, phi);
+    1334           0 :     return res;
+    1335             :     }
+    1336             :   }
+    1337             : 
+    1338             : } // unnamed namespace
+    1339             : 
+    1340           0 : template<typename I> void T_Healpix_Base<I>::boundaries(I pix, tsize step,
+    1341             :   vector<vec3> &out) const
+    1342             :   {
+    1343           0 :   out.resize(4*step);
+    1344             :   int ix, iy, face;
+    1345           0 :   pix2xyf(pix, ix, iy, face);
+    1346           0 :   double dc = 0.5 / nside_;
+    1347           0 :   double xc = (ix + 0.5)/nside_, yc = (iy + 0.5)/nside_;
+    1348           0 :   double d = 1.0/(step*nside_);
+    1349           0 :   for (tsize i=0; i<step; ++i)
+    1350             :     {
+    1351             :     double z, phi, sth;
+    1352             :     bool have_sth;
+    1353           0 :     xyf2loc(xc+dc-i*d, yc+dc, face, z, phi, sth, have_sth);
+    1354           0 :     out[i] = locToVec3(z, phi, sth, have_sth);
+    1355           0 :     xyf2loc(xc-dc, yc+dc-i*d, face, z, phi, sth, have_sth);
+    1356           0 :     out[i+step] = locToVec3(z, phi, sth, have_sth);
+    1357           0 :     xyf2loc(xc-dc+i*d, yc-dc, face, z, phi, sth, have_sth);
+    1358           0 :     out[i+2*step] = locToVec3(z, phi, sth, have_sth);
+    1359           0 :     xyf2loc(xc+dc, yc-dc+i*d, face, z, phi, sth, have_sth);
+    1360           0 :     out[i+3*step] = locToVec3(z, phi, sth, have_sth);
+    1361             :     }
+    1362           0 :   }
+    1363             : 
+    1364           0 : template<typename I> arr<int> T_Healpix_Base<I>::swap_cycles() const
+    1365             :   {
+    1366           0 :   planck_assert(order_>=0, "need hierarchical map");
+    1367           0 :   planck_assert(order_<=13, "map too large");
+    1368           0 :   arr<int> result(swap_clen[order_]);
+    1369             :   tsize ofs=0;
+    1370           0 :   for (int m=0; m<order_;++m) ofs+=swap_clen[m];
+    1371           0 :   for (tsize m=0; m<result.size();++m) result[m]=swap_cycle[m+ofs];
+    1372           0 :   return result;
+    1373             :   }
+    1374             : 
+    1375             : template class T_Healpix_Base<int>;
+    1376             : template class T_Healpix_Base<int64>;
+    1377             : } // namespace healpix
+    1378             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html new file mode 100644 index 000000000..7fadb1a05 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/alloc_utils.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - alloc_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIiEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIlEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_6vec3_tIdEEE5allocEm0
_ZNK7healpix13normalAlloc__IdE5allocEm0
_ZNK7healpix13normalAlloc__IiE5allocEm0
_ZNK7healpix13normalAlloc__ImE5allocEm0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html new file mode 100644 index 000000000..4e93cb259 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/alloc_utils.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - alloc_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIiEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIlEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_6vec3_tIdEEE5allocEm0
_ZNK7healpix13normalAlloc__IdE5allocEm0
_ZNK7healpix13normalAlloc__IiE5allocEm0
_ZNK7healpix13normalAlloc__ImE5allocEm0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html new file mode 100644 index 000000000..6d1cc4bf4 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html @@ -0,0 +1,154 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/alloc_utils.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - alloc_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : 
+       2             : /*
+       3             :  *  This file is part of libcxxsupport.
+       4             :  *
+       5             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       6             :  *  it under the terms of the GNU General Public License as published by
+       7             :  *  the Free Software Foundation; either version 2 of the License, or
+       8             :  *  (at your option) any later version.
+       9             :  *
+      10             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      11             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      12             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      13             :  *  GNU General Public License for more details.
+      14             :  *
+      15             :  *  You should have received a copy of the GNU General Public License
+      16             :  *  along with libcxxsupport; if not, write to the Free Software
+      17             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      18             :  */
+      19             : 
+      20             : /*
+      21             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      22             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      23             :  *  (DLR).
+      24             :  */
+      25             : 
+      26             : /*! \file alloc_utils.h
+      27             :  *  Classes providing raw memory allocation and deallocation support.
+      28             :  *
+      29             :  *  Copyright (C) 2011 Max-Planck-Society
+      30             :  *  \author Martin Reinecke
+      31             :  */
+      32             : 
+      33             : #ifndef PLANCK_ALLOC_UTILS_H
+      34             : #define PLANCK_ALLOC_UTILS_H
+      35             : 
+      36             : #include <cstdlib>
+      37             : #include "healpix_base/datatypes.h"
+      38             : 
+      39             : namespace healpix{
+      40             : template <typename T> class normalAlloc__
+      41             :   {
+      42             :   public:
+      43           0 :     T *alloc(tsize sz) const { return (sz>0) ? new T[sz] : 0; }
+      44           0 :     void dealloc (T *ptr) const { delete[] ptr; }
+      45             :   };
+      46             : 
+      47             : template <typename T, int align> class alignAlloc__
+      48             :   {
+      49             :   public:
+      50             :     T *alloc(tsize sz) const
+      51             :       {
+      52             :       using namespace std;
+      53             :       if (sz==0) return 0;
+      54             :       planck_assert((align&(align-1))==0,"alignment must be power of 2");
+      55             :       void *res;
+      56             : /* OSX up to version 10.5 does not define posix_memalign(), but fortunately
+      57             :    the normal malloc() returns 16 byte aligned storage */
+      58             : #ifdef __APPLE__
+      59             :       planck_assert(align<=16, "bad alignment requested");
+      60             :       res=malloc(sz*sizeof(T));
+      61             :       planck_assert(res!=0,"error in malloc()");
+      62             : #else
+      63             :       planck_assert(posix_memalign(&res,align,sz*sizeof(T))==0,
+      64             :         "error in posix_memalign()");
+      65             : #endif
+      66             :       return static_cast<T *>(res);
+      67             :       }
+      68             :     void dealloc(T *ptr) const
+      69             :       {
+      70             :       using namespace std;
+      71             :       free(ptr);
+      72             :       }
+      73             :   };
+      74             : 
+      75             : 
+      76             : } // namespace healpix
+      77             : 
+      78             : #endif
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html new file mode 100644 index 000000000..9bd6e3a5a --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/arr.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - arr.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0150.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix4arrTIdNS_13normalAlloc__IdEEEC2EmRKd0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html new file mode 100644 index 000000000..782efedc9 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/arr.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - arr.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0150.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix4arrTIdNS_13normalAlloc__IdEEEC2EmRKd0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html new file mode 100644 index 000000000..b9803ade1 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html @@ -0,0 +1,734 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/arr.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - arr.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0150.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*! \file arr.h
+      26             :  *  Various high-performance array classes used by the Planck LevelS package.
+      27             :  *
+      28             :  *  Copyright (C) 2002-2012 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #ifndef PLANCK_ARR_H
+      33             : #define PLANCK_ARR_H
+      34             : 
+      35             : #include <algorithm>
+      36             : #include <vector>
+      37             : #include <cstdlib>
+      38             : #include "healpix_base/alloc_utils.h"
+      39             : #include "healpix_base/datatypes.h"
+      40             : #include "healpix_base/math_utils.h"
+      41             : 
+      42             : namespace healpix{
+      43             : 
+      44             : /*! \defgroup arraygroup Array classes */
+      45             : /*! \{ */
+      46             : 
+      47             : /*! View of a 1D array */
+      48             : template <typename T> class arr_ref
+      49             :   {
+      50             :   protected:
+      51             :     tsize s;
+      52             :     T *d;
+      53             : 
+      54             :   public:
+      55             :     /*! Constructs an \a arr_ref of size \a s_, starting at \a d_. */
+      56           0 :     arr_ref(T *d_, tsize s_) : s(s_),d(d_) {}
+      57             : 
+      58             :     /*! Returns the current array size. */
+      59           0 :     tsize size() const { return s; }
+      60             : 
+      61             :     /*! Writes \a val into every element of the array. */
+      62             :     void fill (const T &val)
+      63           0 :       { for (tsize m=0; m<s; ++m) d[m]=val; }
+      64             : 
+      65             :     /*! Returns a reference to element \a n */
+      66           0 :     template<typename T2> T &operator[] (T2 n) {return d[n];}
+      67             :     /*! Returns a constant reference to element \a n */
+      68           0 :     template<typename T2> const T &operator[] (T2 n) const {return d[n];}
+      69             : 
+      70             :     /*! Returns a pointer to the first array element, or NULL if the array
+      71             :         is zero-sized. */
+      72             :     T *begin() { return d; }
+      73             :     /*! Returns a pointer to the one-past-last array element, or NULL if the
+      74             :         array is zero-sized. */
+      75             :     T *end() { return d+s; }
+      76             :     /*! Returns a constant pointer to the first array element, or NULL if the
+      77             :         array is zero-sized. */
+      78             :     const T *begin() const { return d; }
+      79             :     /*! Returns a constant pointer to the one-past-last array element, or NULL
+      80             :         if the array is zero-sized. */
+      81             :     const T *end() const { return d+s; }
+      82             : 
+      83             :     /*! Copies all array elements to \a ptr. */
+      84             :     template<typename T2> void copyToPtr (T *ptr) const
+      85             :       { for (tsize m=0; m<s; ++m) ptr[m]=d[m]; }
+      86             : 
+      87             :     /*! Sorts the elements in the array, in ascending order. */
+      88             :     void sort()
+      89             :       { std::sort (d,d+s); }
+      90             : 
+      91             :     /*! Sorts the elements in the array, such that \a comp(d[i],d[j])==true
+      92             :         for \a i<j. */
+      93             :     template<typename Comp> void sort(Comp comp)
+      94             :       { std::sort (d,d+s,comp); }
+      95             : 
+      96             :     /*! Helper function for linear interpolation (or extrapolation).
+      97             :         \a idx and \a val are computed such that
+      98             :         \a val=d[idx]+frac*(d[idx+1]-d[idx]). If \a val<d[0], \a frac will be
+      99             :         negative, if \a val>d[s-1], frac will be larger than 1. In all other
+     100             :         cases \a 0<=frac<=1.
+     101             : 
+     102             :         The array must be ordered in ascending order; no two values may be
+     103             :         equal. */
+     104             :     void interpol_helper (const T &val, tsize &idx, double &frac) const
+     105             :       { healpix::interpol_helper (d, d+s, val, idx, frac); }
+     106             : 
+     107             :     /*! Helper function for linear interpolation (or extrapolation).
+     108             :         \a idx and \a val are computed such that
+     109             :         \a val=d[idx]+frac*(d[idx+1]-d[idx]). If \a comp(val,d[0])==true,
+     110             :         \a frac will be negative, if \a comp(val,d[s-1])==false, frac will be
+     111             :         larger than 1. In all other cases \a 0<=frac<=1.
+     112             : 
+     113             :         The array must be ordered such that \a comp(d[i],d[j])==true
+     114             :         for \a i<j; no two values may be equal. */
+     115             :     template<typename Comp> void interpol_helper (const T &val, Comp comp,
+     116             :       tsize &idx, double &frac) const
+     117             :       { healpix::interpol_helper (d, d+s, val, comp, idx, frac); }
+     118             : 
+     119             :     /*! Returns the minimum and maximum entry in \a minv and \a maxv,
+     120             :         respectively. Throws an exception if the array is zero-sized. */
+     121             :     void minmax (T &minv, T &maxv) const
+     122             :       {
+     123             :       planck_assert(s>0,"trying to find min and max of a zero-sized array");
+     124             :       minv=maxv=d[0];
+     125             :       for (tsize m=1; m<s; ++m)
+     126             :         {
+     127             :         if (d[m]<minv) minv=d[m];
+     128             :         else if (d[m]>maxv) maxv=d[m];
+     129             :         }
+     130             :       }
+     131             : 
+     132             :     /*! Returns \a true, if \a val is found in the array, else \a false. */
+     133             :     bool contains (const T &val) const
+     134             :       {
+     135             :       for (tsize m=0; m<s; ++m)
+     136             :         if (d[m]==val) return true;
+     137             :       return false;
+     138             :       }
+     139             : 
+     140             :     /*! Returns the index of the first occurrence of \a val in the array.
+     141             :         If it is not found, an exception is thrown. */
+     142             :     tsize find (const T &val) const
+     143             :       {
+     144             :       for (tsize m=0; m<s; ++m)
+     145             :         if (d[m]==val) return m;
+     146             :       planck_fail ("entry not found in array");
+     147             :       }
+     148             : 
+     149             :     /*! Returns \a true if the array has the same size as \a other and all
+     150             :         elements of both arrays are equal, else \a false. */
+     151             :     bool contentsEqual(const arr_ref &other) const
+     152             :       {
+     153             :       if (s!=other.s) return false;
+     154             :       for (tsize i=0; i<s; ++i)
+     155             :         if (d[i]!=other.d[i]) return false;
+     156             :       return true;
+     157             :       }
+     158             :   };
+     159             : 
+     160             : /*! An array whose size is known at compile time. Very useful for storing
+     161             :     small arrays on the stack, without need for \a new and \a delete(). */
+     162             : template <typename T, tsize sz> class fix_arr
+     163             :   {
+     164             :   private:
+     165             :     T d[sz];
+     166             : 
+     167             :   public:
+     168             :     /*! Returns the size of the array. */
+     169             :     tsize size() const { return sz; }
+     170             : 
+     171             :     /*! Returns a reference to element \a n */
+     172             :     template<typename T2> T &operator[] (T2 n) {return d[n];}
+     173             :     /*! Returns a constant reference to element \a n */
+     174             :     template<typename T2> const T &operator[] (T2 n) const {return d[n];}
+     175             :   };
+     176             : 
+     177             : 
+     178             : /*! One-dimensional array type, with selectable storage management. */
+     179             : template <typename T, typename storageManager> class arrT: public arr_ref<T>
+     180             :   {
+     181             :   private:
+     182             :     storageManager stm;
+     183             :     bool own;
+     184             : 
+     185             :     void reset()
+     186             :       { this->d=0; this->s=0; own=true; }
+     187             : 
+     188             :   public:
+     189             :     /*! Creates a zero-sized array. */
+     190             :     arrT() : arr_ref<T>(0,0), own(true) {}
+     191             :     /*! Creates an array with \a sz entries. */
+     192           0 :     arrT(tsize sz) : arr_ref<T>(stm.alloc(sz),sz), own(true) {}
+     193             :     /*! Creates an array with \a sz entries, and initializes them with
+     194             :         \a inival. */
+     195           0 :     arrT(tsize sz, const T &inival) : arr_ref<T>(stm.alloc(sz),sz), own(true)
+     196           0 :       { this->fill(inival); }
+     197             :     /*! Creates an array with \a sz entries, which uses the memory pointed
+     198             :         to by \a ptr.
+     199             :         \note \a ptr will <i>not</i> be deallocated by the destructor.
+     200             :         \warning Only use this if you REALLY know what you are doing.
+     201             :         In particular, this is only safely usable if
+     202             :           <ul>
+     203             :           <li>\a T is a POD type</li>
+     204             :           <li>\a ptr survives during the lifetime of the array object</li>
+     205             :           <li>\a ptr is not subject to garbage collection</li>
+     206             :           </ul>
+     207             :         Other restrictions may apply. You have been warned. */
+     208             :     arrT (T *ptr, tsize sz): arr_ref<T>(ptr,sz), own(false) {}
+     209             :     /*! Creates an array which is a copy of \a orig. The data in \a orig
+     210             :         is duplicated. */
+     211             :     arrT (const arrT &orig): arr_ref<T>(stm.alloc(orig.s),orig.s), own(true)
+     212             :       { for (tsize m=0; m<this->s; ++m) this->d[m] = orig.d[m]; }
+     213             :     /*! Frees the memory allocated by the object. */
+     214           0 :     ~arrT() { if (own) stm.dealloc(this->d); }
+     215             : 
+     216             :     /*! Allocates space for \a sz elements. The content of the array is
+     217             :         undefined on exit. \a sz can be 0. If \a sz is the
+     218             :         same as the current size, no reallocation is performed. */
+     219             :     void alloc (tsize sz)
+     220             :       {
+     221             :       if (sz==this->s) return;
+     222             :       if (own) stm.dealloc(this->d);
+     223             :       this->s = sz;
+     224             :       this->d = stm.alloc(sz);
+     225             :       own = true;
+     226             :       }
+     227             :     /*! Allocates space for \a sz elements. If \a sz is the
+     228             :         same as the current size, no reallocation is performed.
+     229             :         All elements are set to \a inival. */
+     230             :     void allocAndFill (tsize sz, const T &inival)
+     231             :       { alloc(sz); this->fill(inival); }
+     232             :     /*! Deallocates the memory held by the array, and sets the array size
+     233             :         to 0. */
+     234             :     void dealloc() {if (own) stm.dealloc(this->d); reset();}
+     235             :     /*! Resizes the array to hold \a sz elements. The existing content of the
+     236             :         array is copied over to the new array to the extent possible.
+     237             :         \a sz can be 0. If \a sz is the same as the current size, no
+     238             :         reallocation is performed. */
+     239             :     void resize (tsize sz)
+     240             :       {
+     241             :       using namespace std;
+     242             :       if (sz==this->s) return;
+     243             :       T *tmp = stm.alloc(sz);
+     244             :       for (tsize m=0; m<min(sz,this->s); ++m)
+     245             :         tmp[m]=this->d[m];
+     246             :       if (own) stm.dealloc(this->d);
+     247             :       this->s = sz;
+     248             :       this->d = tmp;
+     249             :       own = true;
+     250             :       }
+     251             : 
+     252             :     /*! Changes the array to be a copy of \a orig. */
+     253             :     arrT &operator= (const arrT &orig)
+     254             :       {
+     255             :       if (this==&orig) return *this;
+     256             :       alloc (orig.s);
+     257             :       for (tsize m=0; m<this->s; ++m) this->d[m] = orig.d[m];
+     258             :       return *this;
+     259             :       }
+     260             : 
+     261             :     /*! Changes the array to be a copy of the std::vector \a orig. */
+     262             :     template<typename T2> void copyFrom (const std::vector<T2> &orig)
+     263             :       {
+     264             :       alloc (orig.size());
+     265             :       for (tsize m=0; m<this->s; ++m) this->d[m] = orig[m];
+     266             :       }
+     267             :     /*! Changes the std::vector \a vec to be a copy of the object. */
+     268             :     template<typename T2> void copyTo (std::vector<T2> &vec) const
+     269             :       {
+     270             :       vec.clear(); vec.reserve(this->s);
+     271             :       for (tsize m=0; m<this->s; ++m) vec.push_back(this->d[m]);
+     272             :       }
+     273             : 
+     274             :     /*! Reserves space for \a sz elements, then copies \a sz elements
+     275             :         from \a ptr into the array. */
+     276             :     template<typename T2> void copyFromPtr (const T2 *ptr, tsize sz)
+     277             :       {
+     278             :       alloc(sz);
+     279             :       for (tsize m=0; m<this->s; ++m) this->d[m]=ptr[m];
+     280             :       }
+     281             : 
+     282             :     /*! Assigns the contents and size of \a other to the array.
+     283             :         \note On exit, \a other is zero-sized! */
+     284             :     void transfer (arrT &other)
+     285             :       {
+     286             :       if (own) stm.dealloc(this->d);
+     287             :       this->d=other.d;
+     288             :       this->s=other.s;
+     289             :       own=other.own;
+     290             :       other.reset();
+     291             :       }
+     292             :     /*! Swaps contents and size with \a other. */
+     293             :     void swap (arrT &other)
+     294             :       {
+     295             :       std::swap(this->d,other.d);
+     296             :       std::swap(this->s,other.s);
+     297             :       std::swap(own,other.own);
+     298             :       }
+     299             :   };
+     300             : 
+     301             : /*! One-dimensional array type. */
+     302             : template <typename T>
+     303           0 :   class arr: public arrT<T,normalAlloc__<T> >
+     304             :   {
+     305             :   public:
+     306             :     /*! Creates a zero-sized array. */
+     307             :     arr() : arrT<T,normalAlloc__<T> >() {}
+     308             :     /*! Creates an array with \a sz entries. */
+     309             :     arr(tsize sz) : arrT<T,normalAlloc__<T> >(sz) {}
+     310             :     /*! Creates an array with \a sz entries, and initializes them with
+     311             :         \a inival. */
+     312           0 :     arr(tsize sz, const T &inival) : arrT<T,normalAlloc__<T> >(sz,inival) {}
+     313             :     /*! Creates an array with \a sz entries, which uses the memory pointed
+     314             :         to by \a ptr.
+     315             :         \note \a ptr will <i>not</i> be deallocated by the destructor.
+     316             :         \warning Only use this if you REALLY know what you are doing.
+     317             :         In particular, this is only safely usable if
+     318             :           <ul>
+     319             :           <li>\a T is a POD type</li>
+     320             :           <li>\a ptr survives during the lifetime of the array object</li>
+     321             :           <li>\a ptr is not subject to garbage collection</li>
+     322             :           </ul>
+     323             :         Other restrictions may apply. You have been warned. */
+     324             :     arr (T *ptr, tsize sz): arrT<T,normalAlloc__<T> >(ptr,sz) {}
+     325             :     /*! Creates an array which is a copy of \a orig. The data in \a orig
+     326             :         is duplicated. */
+     327             :     arr (const arr &orig): arrT<T,normalAlloc__<T> >(orig) {}
+     328             :   };
+     329             : 
+     330             : /*! One-dimensional array type, with selectable storage alignment. */
+     331             : template <typename T, int align>
+     332             :   class arr_align: public arrT<T,alignAlloc__<T,align> >
+     333             :   {
+     334             :   public:
+     335             :     /*! Creates a zero-sized array. */
+     336             :     arr_align() : arrT<T,alignAlloc__<T,align> >() {}
+     337             :     /*! Creates an array with \a sz entries. */
+     338             :     arr_align(tsize sz) : arrT<T,alignAlloc__<T,align> >(sz) {}
+     339             :     /*! Creates an array with \a sz entries, and initializes them with
+     340             :         \a inival. */
+     341             :     arr_align(tsize sz, const T &inival)
+     342             :       : arrT<T,alignAlloc__<T,align> >(sz,inival) {}
+     343             :   };
+     344             : 
+     345             : 
+     346             : /*! Two-dimensional array type, with selectable storage management.
+     347             :     The storage ordering is the same as in C.
+     348             :     An entry is located by address arithmetic, not by double dereferencing.
+     349             :     The indices start at zero. */
+     350             : template <typename T, typename storageManager> class arr2T
+     351             :   {
+     352             :   private:
+     353             :     tsize s1, s2;
+     354             :     arrT<T, storageManager> d;
+     355             : 
+     356             :   public:
+     357             :     /*! Creates a zero-sized array. */
+     358             :     arr2T() : s1(0), s2(0) {}
+     359             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
+     360             :     arr2T(tsize sz1, tsize sz2)
+     361             :       : s1(sz1), s2(sz2), d(s1*s2) {}
+     362             :     /*! Creates an array with the dimensions  \a sz1 and \a sz2
+     363             :         and initializes them with \a inival. */
+     364             :     arr2T(tsize sz1, tsize sz2, const T &inival)
+     365             :       : s1(sz1), s2(sz2), d (s1*s2)
+     366             :       { fill(inival); }
+     367             :     /*! Creates the array as a copy of \a orig. */
+     368             :     arr2T(const arr2T &orig)
+     369             :       : s1(orig.s1), s2(orig.s2), d(orig.d) {}
+     370             :     /*! Frees the memory associated with the array. */
+     371             :     ~arr2T() {}
+     372             : 
+     373             :     /*! Returns the first array dimension. */
+     374             :     tsize size1() const { return s1; }
+     375             :     /*! Returns the second array dimension. */
+     376             :     tsize size2() const { return s2; }
+     377             :     /*! Returns the total array size, i.e. the product of both dimensions. */
+     378             :     tsize size () const { return s1*s2; }
+     379             : 
+     380             :     /*! Allocates space for an array with \a sz1*sz2 elements.
+     381             :         The content of the array is undefined on exit.
+     382             :         \a sz1 or \a sz2 can be 0. If \a sz1*sz2 is the same as the
+     383             :         currently allocated space, no reallocation is performed. */
+     384             :     void alloc (tsize sz1, tsize sz2)
+     385             :       {
+     386             :       if (sz1*sz2 != d.size())
+     387             :         d.alloc(sz1*sz2);
+     388             :       s1=sz1; s2=sz2;
+     389             :       }
+     390             :     /*! Allocates space for an array with \a sz1*sz2 elements.
+     391             :         All elements are set to \a inival.
+     392             :         \a sz1 or \a sz2 can be 0. If \a sz1*sz2 is the same as the
+     393             :         currently allocated space, no reallocation is performed. */
+     394             :     void allocAndFill (tsize sz1, tsize sz2, const T &inival)
+     395             :       { alloc(sz1,sz2); fill(inival); }
+     396             :     /*! Allocates space for an array with \a sz1*sz2 elements.
+     397             :         The content of the array is undefined on exit.
+     398             :         \a sz1 or \a sz2 can be 0. If \a sz1*sz2 is smaller than the
+     399             :         currently allocated space, no reallocation is performed. */
+     400             :     void fast_alloc (tsize sz1, tsize sz2)
+     401             :       {
+     402             :       if (sz1*sz2<=d.size())
+     403             :         { s1=sz1; s2=sz2; }
+     404             :       else
+     405             :         alloc(sz1,sz2);
+     406             :       }
+     407             :     /*! Deallocates the space and makes the array zero-sized. */
+     408             :     void dealloc () {d.dealloc(); s1=0; s2=0;}
+     409             : 
+     410             :     /*! Sets all array elements to \a val. */
+     411             :     void fill (const T &val)
+     412             :       { for (tsize m=0; m<s1*s2; ++m) d[m]=val; }
+     413             : 
+     414             :     /*! Multiplies all array elements by \a val. */
+     415             :     void scale (const T &val)
+     416             :       { for (tsize m=0; m<s1*s2; ++m) d[m]*=val; }
+     417             : 
+     418             :     /*! Changes the array to be a copy of \a orig. */
+     419             :     arr2T &operator= (const arr2T &orig)
+     420             :       {
+     421             :       if (this==&orig) return *this;
+     422             :       alloc (orig.s1, orig.s2);
+     423             :       d = orig.d;
+     424             :       return *this;
+     425             :       }
+     426             : 
+     427             :     /*! Returns a pointer to the beginning of slice \a n. */
+     428             :     template<typename T2> T *operator[] (T2 n) {return &d[n*s2];}
+     429             :     /*! Returns a constant pointer to the beginning of slice \a n. */
+     430             :     template<typename T2> const T *operator[] (T2 n) const {return &d[n*s2];}
+     431             : 
+     432             :     /*! Returns a reference to the element with the indices \a n1 and \a n2. */
+     433             :     template<typename T2, typename T3> T &operator() (T2 n1, T3 n2)
+     434             :       {return d[n1*s2 + n2];}
+     435             :     /*! Returns a constant reference to the element with the indices
+     436             :         \a n1 and \a n2. */
+     437             :     template<typename T2, typename T3> const T &operator() (T2 n1, T3 n2) const
+     438             :       {return d[n1*s2 + n2];}
+     439             : 
+     440             :     /*! Returns the minimum and maximum entry in \a minv and \a maxv,
+     441             :         respectively. Throws an exception if the array is zero-sized. */
+     442             :     void minmax (T &minv, T &maxv) const
+     443             :       {
+     444             :       planck_assert(s1*s2>0,
+     445             :         "trying to find min and max of a zero-sized array");
+     446             :       minv=maxv=d[0];
+     447             :       for (tsize m=1; m<s1*s2; ++m)
+     448             :         {
+     449             :         if (d[m]<minv) minv=d[m];
+     450             :         if (d[m]>maxv) maxv=d[m];
+     451             :         }
+     452             :       }
+     453             : 
+     454             :     /*! Swaps contents and sizes with \a other. */
+     455             :     void swap (arr2T &other)
+     456             :       {
+     457             :       d.swap(other.d);
+     458             :       std::swap(s1,other.s1);
+     459             :       std::swap(s2,other.s2);
+     460             :       }
+     461             : 
+     462             :     /*! Returns \c true if the array and \a other have the same dimensions,
+     463             :         else \c false. */
+     464             :     template<typename T2, typename T3> bool conformable
+     465             :       (const arr2T<T2,T3> &other) const
+     466             :       { return (other.size1()==s1) && (other.size2()==s2); }
+     467             :   };
+     468             : 
+     469             : /*! Two-dimensional array type. The storage ordering is the same as in C.
+     470             :     An entry is located by address arithmetic, not by double dereferencing.
+     471             :     The indices start at zero. */
+     472             : template <typename T>
+     473             :   class arr2: public arr2T<T,normalAlloc__<T> >
+     474             :   {
+     475             :   public:
+     476             :     /*! Creates a zero-sized array. */
+     477             :     arr2() : arr2T<T,normalAlloc__<T> > () {}
+     478             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
+     479             :     arr2(tsize sz1, tsize sz2) : arr2T<T,normalAlloc__<T> > (sz1,sz2) {}
+     480             :     /*! Creates an array with the dimensions  \a sz1 and \a sz2
+     481             :         and initializes them with \a inival. */
+     482             :     arr2(tsize sz1, tsize sz2, const T &inival)
+     483             :       : arr2T<T,normalAlloc__<T> > (sz1,sz2,inival) {}
+     484             :   };
+     485             : 
+     486             : /*! Two-dimensional array type, with selectable storage alignment.
+     487             :     The storage ordering is the same as in C.
+     488             :     An entry is located by address arithmetic, not by double dereferencing.
+     489             :     The indices start at zero. */
+     490             : template <typename T, int align>
+     491             :   class arr2_align: public arr2T<T,alignAlloc__<T,align> >
+     492             :   {
+     493             :   public:
+     494             :     /*! Creates a zero-sized array. */
+     495             :     arr2_align() : arr2T<T,alignAlloc__<T,align> > () {}
+     496             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
+     497             :     arr2_align(tsize sz1, tsize sz2)
+     498             :       : arr2T<T,alignAlloc__<T,align> > (sz1,sz2) {}
+     499             :     /*! Creates an array with the dimensions  \a sz1 and \a sz2
+     500             :         and initializes them with \a inival. */
+     501             :     arr2_align(tsize sz1, tsize sz2, const T &inival)
+     502             :       : arr2T<T,alignAlloc__<T,align> > (sz1,sz2,inival) {}
+     503             :   };
+     504             : 
+     505             : /*! Two-dimensional array type. An entry is located by double dereferencing,
+     506             :     i.e. via an array of pointers. The indices start at zero. */
+     507             : template <typename T> class arr2b
+     508             :   {
+     509             :   private:
+     510             :     tsize s1, s2;
+     511             :     arr<T> d;
+     512             :     arr<T *> d1;
+     513             : 
+     514             :     void fill_d1()
+     515             :       { for (tsize m=0; m<s1; ++m) d1[m] = &d[m*s2]; }
+     516             : 
+     517             :   public:
+     518             :     /*! Creates a zero-sized array. */
+     519             :     arr2b() : s1(0), s2(0), d(0), d1(0) {}
+     520             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
+     521             :     arr2b(tsize sz1, tsize sz2)
+     522             :       : s1(sz1), s2(sz2), d(s1*s2), d1(s1)
+     523             :       { fill_d1(); }
+     524             :     /*! Creates the array as a copy of \a orig. */
+     525             :     arr2b(const arr2b &orig)
+     526             :       : s1(orig.s1), s2(orig.s2), d(orig.d), d1(s1)
+     527             :       { fill_d1(); }
+     528             :     /*! Frees the memory associated with the array. */
+     529             :     ~arr2b() {}
+     530             : 
+     531             :     /*! Returns the first array dimension. */
+     532             :     tsize size1() const { return s1; }
+     533             :     /*! Returns the second array dimension. */
+     534             :     tsize size2() const { return s2; }
+     535             :     /*! Returns the total array size, i.e. the product of both dimensions. */
+     536             :     tsize size () const { return s1*s2; }
+     537             : 
+     538             :     /*! Allocates space for an array with \a sz1*sz2 elements.
+     539             :         The content of the array is undefined on exit. */
+     540             :     void alloc (tsize sz1, tsize sz2)
+     541             :       {
+     542             :       if ((s1==sz1) && (s2==sz2)) return;
+     543             :       s1=sz1; s2=sz2;
+     544             :       d.alloc(s1*s2);
+     545             :       d1.alloc(s1);
+     546             :       fill_d1();
+     547             :       }
+     548             :     /*! Deallocates the space and makes the array zero-sized. */
+     549             :     void dealloc () {d.dealloc(); d1.dealloc(); s1=0; s2=0;}
+     550             : 
+     551             :     /*! Sets all array elements to \a val. */
+     552             :     void fill (const T &val)
+     553             :       { d.fill(val); }
+     554             : 
+     555             :     /*! Changes the array to be a copy of \a orig. */
+     556             :     arr2b &operator= (const arr2b &orig)
+     557             :       {
+     558             :       if (this==&orig) return *this;
+     559             :       alloc (orig.s1, orig.s2);
+     560             :       for (tsize m=0; m<s1*s2; ++m) d[m] = orig.d[m];
+     561             :       return *this;
+     562             :       }
+     563             : 
+     564             :     /*! Returns a pointer to the beginning of slice \a n. */
+     565             :     template<typename T2> T *operator[] (T2 n) {return d1[n];}
+     566             :     /*! Returns a constant pointer to the beginning of slice \a n. */
+     567             :     template<typename T2> const T *operator[] (T2 n) const {return d1[n];}
+     568             : 
+     569             :     /*! Returns a pointer to the beginning of the pointer array. */
+     570             :     T **p0() {return &d1[0];}
+     571             :   };
+     572             : 
+     573             : 
+     574             : /*! Three-dimensional array type. The storage ordering is the same as in C.
+     575             :     An entry is located by address arithmetic, not by multiple dereferencing.
+     576             :     The indices start at zero. */
+     577             : template <typename T> class arr3
+     578             :   {
+     579             :   private:
+     580             :     tsize s1, s2, s3, s2s3;
+     581             :     arr<T> d;
+     582             : 
+     583             :   public:
+     584             :     /*! Creates a zero-sized array. */
+     585             :     arr3() : s1(0), s2(0), s3(0), s2s3(0), d(0) {}
+     586             :     /*! Creates an array with the dimensions \a sz1, \a sz2 and \a sz3. */
+     587           0 :     arr3(tsize sz1, tsize sz2, tsize sz3)
+     588           0 :       : s1(sz1), s2(sz2), s3(sz3), s2s3(s2*s3), d(s1*s2*s3) {}
+     589             :     /*! Creates the array as a copy of \a orig. */
+     590             :     arr3(const arr3 &orig)
+     591             :       : s1(orig.s1), s2(orig.s2), s3(orig.s3), s2s3(orig.s2s3), d(orig.d) {}
+     592             :     /*! Frees the memory associated with the array. */
+     593           0 :     ~arr3() {}
+     594             : 
+     595             :     /*! Returns the first array dimension. */
+     596             :     tsize size1() const { return s1; }
+     597             :     /*! Returns the second array dimension. */
+     598             :     tsize size2() const { return s2; }
+     599             :     /*! Returns the third array dimension. */
+     600             :     tsize size3() const { return s3; }
+     601             :     /*! Returns the total array size, i.e. the product of all dimensions. */
+     602             :     tsize size () const { return s1*s2*s3; }
+     603             : 
+     604             :     /*! Allocates space for an array with \a sz1*sz2*sz3 elements.
+     605             :         The content of the array is undefined on exit. */
+     606             :     void alloc (tsize sz1, tsize sz2, tsize sz3)
+     607             :       {
+     608             :       d.alloc(sz1*sz2*sz3);
+     609             :       s1=sz1; s2=sz2; s3=sz3; s2s3=s2*s3;
+     610             :       }
+     611             :     /*! Deallocates the space and makes the array zero-sized. */
+     612             :     void dealloc () {d.dealloc(); s1=0; s2=0; s3=0; s2s3=0;}
+     613             : 
+     614             :     /*! Sets all array elements to \a val. */
+     615             :     void fill (const T &val)
+     616             :       { d.fill(val); }
+     617             : 
+     618             :     /*! Changes the array to be a copy of \a orig. */
+     619             :     arr3 &operator= (const arr3 &orig)
+     620             :       {
+     621             :       if (this==&orig) return *this;
+     622             :       alloc (orig.s1, orig.s2, orig.s3);
+     623             :       d = orig.d;
+     624             :       return *this;
+     625             :       }
+     626             : 
+     627             :     /*! Returns a reference to the element with the indices
+     628             :         \a n1, \a n2 and \a n3. */
+     629             :     template<typename T2, typename T3, typename T4> T &operator()
+     630             :       (T2 n1, T3 n2, T4 n3)
+     631           0 :       {return d[n1*s2s3 + n2*s3 + n3];}
+     632             :     /*! Returns a constant reference to the element with the indices
+     633             :         \a n1, \a n2 and \a n3. */
+     634             :     template<typename T2, typename T3, typename T4> const T &operator()
+     635             :       (T2 n1, T3 n2, T4 n3) const
+     636             :       {return d[n1*s2s3 + n2*s3 + n3];}
+     637             : 
+     638             :     /*! Swaps contents and sizes with \a other. */
+     639             :     void swap (arr3 &other)
+     640             :       {
+     641             :       d.swap(other.d);
+     642             :       std::swap(s1,other.s1);
+     643             :       std::swap(s2,other.s2);
+     644             :       std::swap(s3,other.s3);
+     645             :       std::swap(s2s3,other.s2s3);
+     646             :       }
+     647             : 
+     648             :     /*! Returns \c true if the array and \a other have the same dimensions,
+     649             :         else \c false. */
+     650             :     template<typename T2> bool conformable (const arr3<T2> &other) const
+     651             :       { return (other.size1()==s1)&&(other.size2()==s2)&&(other.size3()==s3); }
+     652             :   };
+     653             : 
+     654             : /*! \} */
+     655             : 
+     656             : } // namespace healpix
+     657             : #endif
+     658             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html new file mode 100644 index 000000000..3feba0c8f --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/error_handling.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - error_handling.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix11PlanckError4whatEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html new file mode 100644 index 000000000..256c36ce3 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/error_handling.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - error_handling.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix11PlanckError4whatEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html new file mode 100644 index 000000000..5a90a3d3f --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html @@ -0,0 +1,180 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/error_handling.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - error_handling.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : 
+       2             : /*
+       3             :  *  This file is part of libcxxsupport.
+       4             :  *
+       5             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       6             :  *  it under the terms of the GNU General Public License as published by
+       7             :  *  the Free Software Foundation; either version 2 of the License, or
+       8             :  *  (at your option) any later version.
+       9             :  *
+      10             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      11             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      12             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      13             :  *  GNU General Public License for more details.
+      14             :  *
+      15             :  *  You should have received a copy of the GNU General Public License
+      16             :  *  along with libcxxsupport; if not, write to the Free Software
+      17             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      18             :  */
+      19             : 
+      20             : /*
+      21             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      22             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      23             :  *  (DLR).
+      24             :  */
+      25             : 
+      26             : /*! \file error_handling.h
+      27             :  *  Utilities for error reporting
+      28             :  *
+      29             :  *  Copyright (C) 2003-2011 Max-Planck-Society
+      30             :  *  Authors: Reinhard Hell, Martin Reinecke
+      31             :  */
+      32             : 
+      33             : #ifndef PLANCK_ERROR_HANDLING_H
+      34             : #define PLANCK_ERROR_HANDLING_H
+      35             : 
+      36             : #include <string>
+      37             : #include <iostream>
+      38             : 
+      39             : namespace healpix{
+      40             : #if defined (__GNUC__)
+      41             : #define PLANCK_FUNC_NAME__ __PRETTY_FUNCTION__
+      42             : #else
+      43             : #define PLANCK_FUNC_NAME__ 0
+      44             : #endif
+      45             : 
+      46             : void planck_failure__(const char *file, int line, const char *func,
+      47             :   const std::string &msg);
+      48             : void planck_failure__(const char *file, int line, const char *func,
+      49             :   const char *msg);
+      50             : void killjob__();
+      51             : 
+      52             : class PlanckError
+      53             :   {
+      54             :   private:
+      55             :     std::string msg;
+      56             : 
+      57             :   public:
+      58             :     explicit PlanckError(const std::string &message);
+      59             :     explicit PlanckError(const char *message);
+      60             : 
+      61           0 :     virtual const char* what() const
+      62           0 :       { return msg.c_str(); }
+      63             : 
+      64             :     virtual ~PlanckError();
+      65             :   };
+      66             : 
+      67             : /*! \defgroup errorgroup Error handling */
+      68             : /*! \{ */
+      69             : 
+      70             : /*! Writes diagnostic output and exits with an error status. */
+      71             : #define planck_fail(msg) \
+      72             : do { planck_failure__(__FILE__,__LINE__,PLANCK_FUNC_NAME__,msg); \
+      73             : throw PlanckError(msg); } while(0)
+      74             : 
+      75             : /*! Throws a PlanckError without diagnostic message. */
+      76             : #define planck_fail_quietly(msg) \
+      77             : do { throw PlanckError(msg); } while(0)
+      78             : 
+      79             : /*! Writes diagnostic output and exits with an error status if \a testval
+      80             :     is \a false. */
+      81             : #define planck_assert(testval,msg) \
+      82             : do { if (testval); else planck_fail(msg); } while(0)
+      83             : 
+      84             : /*! Macro for improving error diagnostics. Should be placed immediately
+      85             :     after the opening brace of \c main(). Must be used in conjunction with
+      86             :     \c PLANCK_DIAGNOSIS_END. */
+      87             : #define PLANCK_DIAGNOSIS_BEGIN try {
+      88             : /*! Macro for improving error diagnostics. Should be placed immediately
+      89             :     before the closing brace of \c main(). Must be used in conjunction with
+      90             :     \c PLANCK_DIAGNOSIS_BEGIN. */
+      91             : #define PLANCK_DIAGNOSIS_END \
+      92             : } \
+      93             : catch (PlanckError &) \
+      94             :   { killjob__(); /* no need for further diagnostics; they were shown already */ } \
+      95             : catch (std::exception &e) \
+      96             :   { std::cerr << "std::exception: " << e.what() << std::endl; killjob__(); } \
+      97             : catch (...) \
+      98             :   { std::cerr << "Unknown exception" << std::endl; killjob__(); }
+      99             : 
+     100             : /*! \} */
+     101             : 
+     102             : } // namespace healpix
+     103             : #endif
+     104             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html new file mode 100644 index 000000000..19feeba32 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/geom_utils.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - geom_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12cosdist_zphiEdddd0
_ZN7healpix7v_angleERKNS_6vec3_tIdEES3_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html new file mode 100644 index 000000000..be6031adf --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/geom_utils.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - geom_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12cosdist_zphiEdddd0
_ZN7healpix7v_angleERKNS_6vec3_tIdEES3_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html new file mode 100644 index 000000000..42f3ff33f --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html @@ -0,0 +1,161 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/geom_utils.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - geom_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*! \file geom_utils.h
+      26             :  *  Geometric utility functions.
+      27             :  *
+      28             :  *  Copyright (C) 2003-2011 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  *  \author Reinhard Hell
+      31             :  */
+      32             : 
+      33             : #ifndef PLANCK_GEOM_UTILS_H
+      34             : #define PLANCK_GEOM_UTILS_H
+      35             : 
+      36             : #include "healpix_base/math_utils.h"
+      37             : #include "healpix_base/vec3.h"
+      38             : 
+      39             : namespace healpix{
+      40             : 
+      41             : template<typename T> class arr;
+      42             : 
+      43             : /*! Returns the orientation when looking from point \a loc on the unit
+      44             :     sphere in the direction \a dir. \a loc must be normalized. The result
+      45             :     ranges from -pi to pi, is 0 for North and pi/2 for West, i.e. the angle
+      46             :     is given in mathematically positive sense.
+      47             : 
+      48             :     If \a loc is the North or South pole, the returned angle is
+      49             :     \a atan2(dir.y,dir.x). */
+      50             : inline double orientation (const vec3 &loc, const vec3 &dir)
+      51             :   {
+      52             : // FIXME: here is still optimization potential
+      53             :   if (loc.x==0 && loc.y==0)
+      54             :     return (loc.z>0) ? safe_atan2(dir.y,-dir.x) : safe_atan2(dir.y,dir.x);
+      55             :   vec3 east (-loc.y, loc.x, 0);
+      56             :   vec3 north = crossprod(loc,east);
+      57             :   return safe_atan2(-dotprod(dir,east),dotprod(dir,north));
+      58             :   }
+      59             : 
+      60             : /*! Returns the angle between \a v1 and \a v2 in radians. */
+      61           0 : inline double v_angle (const vec3 &v1, const vec3 &v2)
+      62             :   {
+      63             :   using namespace std;
+      64           0 :   return atan2 (crossprod(v1,v2).Length(), dotprod(v1,v2));
+      65             :   }
+      66             : 
+      67             : /*! Returns the cosine of the angle between the two points on the sphere defined
+      68             :     by (\a z1, \a phi1) and (\a z2, \a phi2), respectively. \a z is the cosine
+      69             :     of the colatitude, and \a phi is the longitude. */
+      70           0 : inline double cosdist_zphi (double z1, double phi1, double z2, double phi2)
+      71             :   {
+      72             :   using namespace std;
+      73           0 :   return z1*z2+cos(phi1-phi2)*sqrt((1.-z1*z1)*(1.-z2*z2));
+      74             :   }
+      75             : 
+      76             : /*! Finds the smallest enclosing cone for a point set on the sphere according to
+      77             :     Barequet & Elber: Information Processing Letters 93(2005), p.83.
+      78             :     All points are expected to be passed as unit vectors.
+      79             :     The enclosing cone must have an opening angle <pi/2. */
+      80             : void find_enclosing_circle (const arr<vec3> &point, vec3 &center,
+      81             :   double &cosrad);
+      82             : 
+      83             : } // namespace healpix
+      84             : #endif
+      85             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html new file mode 100644 index 000000000..c2ac9dce4 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html @@ -0,0 +1,208 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/healpix_base.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - healpix_base.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:165032.0 %
Date:2024-04-08 14:58:22Functions:3348.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZN7healpix14T_Healpix_BaseIlEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2ElNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZNK7healpix14T_Healpix_BaseIiE10query_discERKNS_8pointingEdRSt6vectorIiSaIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIiSaIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIiE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIiE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIiE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIiE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIiE7pix2angEi0
_ZNK7healpix14T_Healpix_BaseIiE7pix2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIiE8pix2zphiEiRdS2_0
_ZNK7healpix14T_Healpix_BaseIiE8zphi2pixEdd0
_ZNK7healpix14T_Healpix_BaseIlE10query_discERKNS_8pointingEdRSt6vectorIlSaIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIlSaIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIlE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIlE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIlE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIlE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIlE7pix2angEl0
_ZNK7healpix14T_Healpix_BaseIlE7pix2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE7vec2pixERKNS_6vec3_tIdEE0
_ZNK7healpix14T_Healpix_BaseIlE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIlE8pix2zphiElRdS2_0
_ZNK7healpix14T_Healpix_BaseIlE8zphi2pixEdd0
_ZNK7healpix14T_Healpix_BaseIlE7pix2vecEl421
_ZNK7healpix14T_Healpix_BaseIiE7vec2pixERKNS_6vec3_tIdEE24585
_ZNK7healpix14T_Healpix_BaseIiE7pix2vecEi135172
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html new file mode 100644 index 000000000..b4d88f50c --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html @@ -0,0 +1,208 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/healpix_base.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - healpix_base.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:165032.0 %
Date:2024-04-08 14:58:22Functions:3348.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZN7healpix14T_Healpix_BaseIlEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2ElNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZNK7healpix14T_Healpix_BaseIiE10query_discERKNS_8pointingEdRSt6vectorIiSaIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIiSaIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIiE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIiE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIiE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIiE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIiE7pix2angEi0
_ZNK7healpix14T_Healpix_BaseIiE7pix2vecEi135172
_ZNK7healpix14T_Healpix_BaseIiE7pix2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE7vec2pixERKNS_6vec3_tIdEE24585
_ZNK7healpix14T_Healpix_BaseIiE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIiE8pix2zphiEiRdS2_0
_ZNK7healpix14T_Healpix_BaseIiE8zphi2pixEdd0
_ZNK7healpix14T_Healpix_BaseIlE10query_discERKNS_8pointingEdRSt6vectorIlSaIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIlSaIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIlE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIlE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIlE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIlE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIlE7pix2angEl0
_ZNK7healpix14T_Healpix_BaseIlE7pix2vecEl421
_ZNK7healpix14T_Healpix_BaseIlE7pix2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE7vec2pixERKNS_6vec3_tIdEE0
_ZNK7healpix14T_Healpix_BaseIlE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIlE8pix2zphiElRdS2_0
_ZNK7healpix14T_Healpix_BaseIlE8zphi2pixEdd0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html new file mode 100644 index 000000000..c89cc2a4d --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html @@ -0,0 +1,457 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/healpix_base.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - healpix_base.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:165032.0 %
Date:2024-04-08 14:58:22Functions:3348.8 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of Healpix_cxx.
+       3             :  *
+       4             :  *  Healpix_cxx is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  Healpix_cxx is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with Healpix_cxx; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  *
+      18             :  *  For more information about HEALPix, see http://healpix.sourceforge.net
+      19             :  */
+      20             : 
+      21             : /*
+      22             :  *  Healpix_cxx is being developed at the Max-Planck-Institut fuer Astrophysik
+      23             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      24             :  *  (DLR).
+      25             :  */
+      26             : 
+      27             : /*! \file healpix_base.h
+      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #ifndef HEALPIX_BASE_H
+      33             : #define HEALPIX_BASE_H
+      34             : 
+      35             : #include <vector>
+      36             : #include "healpix_base/healpix_tables.h"
+      37             : #include "healpix_base/pointing.h"
+      38             : #include "healpix_base/arr.h"
+      39             : #include "healpix_base/rangeset.h"
+      40             : 
+      41             : namespace healpix{
+      42             : 
+      43             : /*! Functionality related to the HEALPix pixelisation. */
+      44             : template<typename I> class T_Healpix_Base: public Healpix_Tables
+      45             :   {
+      46             :   protected:
+      47             :     /*! The order of the map; -1 for nonhierarchical map. */
+      48             :     int order_;
+      49             :     /*! The N_side parameter of the map; 0 if not allocated. */
+      50             :     I nside_;
+      51             :     I npface_, ncap_, npix_;
+      52             :     double fact1_, fact2_;
+      53             :     /*! The map's ordering scheme. */
+      54             :     Healpix_Ordering_Scheme scheme_;
+      55             : 
+      56             :     /*! Returns the number of the next ring to the north of \a z=cos(theta).
+      57             :         It may return 0; in this case \a z lies north of all rings. */
+      58             :     inline I ring_above (double z) const;
+      59             :     void in_ring (I iz, double phi0, double dphi, rangeset<I> &pixset) const;
+      60             : 
+      61             :     template<typename I2> void query_multidisc (const arr<vec3> &norm,
+      62             :       const arr<double> &rad, int fact, rangeset<I2> &pixset) const;
+      63             : 
+      64             :     void query_multidisc_general (const arr<vec3> &norm, const arr<double> &rad,
+      65             :       bool inclusive, const std::vector<int> &cmds, rangeset<I> &pixset) const;
+      66             : 
+      67             :     void query_strip_internal (double theta1, double theta2, bool inclusive,
+      68             :       rangeset<I> &pixset) const;
+      69             : 
+      70             :     inline I spread_bits (int v) const;
+      71             :     inline int compress_bits (I v) const;
+      72             : 
+      73             :     I xyf2nest(int ix, int iy, int face_num) const;
+      74             :     void nest2xyf(I pix, int &ix, int &iy, int &face_num) const;
+      75             :     I xyf2ring(int ix, int iy, int face_num) const;
+      76             :     void ring2xyf(I pix, int &ix, int &iy, int &face_num) const;
+      77             : 
+      78             :     I loc2pix (double z, double phi, double sth, bool have_sth) const;
+      79             :     void pix2loc (I pix, double &z, double &phi, double &sth, bool &have_sth)
+      80             :       const;
+      81             : 
+      82             :     void xyf2loc(double x, double y, int face, double &z, double &ph,
+      83             :       double &sth, bool &have_sth) const;
+      84             : 
+      85             :     I nest_peano_helper (I pix, int dir) const;
+      86             : 
+      87             :     typedef I (T_Healpix_Base::*swapfunc)(I pix) const;
+      88             : 
+      89             :   public:
+      90             :     static const int order_max;
+      91             : 
+      92             :     /*! Calculates the map order from its \a N_side parameter.
+      93             :         Returns -1 if \a nside is not a power of 2.
+      94             :         \param nside the \a N_side parameter */
+      95             :     static int nside2order (I nside);
+      96             :     /*! Calculates the \a N_side parameter from the number of pixels.
+      97             :         \param npix the number of pixels */
+      98             :     static I npix2nside (I npix);
+      99             :     /*! Constructs an unallocated object. */
+     100             :     T_Healpix_Base ();
+     101             :     /*! Constructs an object with a given \a order and the ordering
+     102             :         scheme \a scheme. */
+     103          10 :     T_Healpix_Base (int order, Healpix_Ordering_Scheme scheme)
+     104          10 :       { Set (order, scheme); }
+     105             :     /*! Constructs an object with a given \a nside and the ordering
+     106             :         scheme \a scheme. The \a nside_dummy parameter must be set to
+     107             :         SET_NSIDE. */
+     108           0 :     T_Healpix_Base (I nside, Healpix_Ordering_Scheme scheme, const nside_dummy)
+     109           0 :       { SetNside (nside, scheme); }
+     110             : 
+     111             :     /*! Adjusts the object to \a order and \a scheme. */
+     112             :     void Set (int order, Healpix_Ordering_Scheme scheme);
+     113             :     /*! Adjusts the object to \a nside and \a scheme. */
+     114             :     void SetNside (I nside, Healpix_Ordering_Scheme scheme);
+     115             : 
+     116             :     /*! Returns the z-coordinate of the ring \a ring. This also works
+     117             :         for the (not really existing) rings 0 and 4*nside. */
+     118             :     double ring2z (I ring) const;
+     119             :     /*! Returns the number of the ring in which \a pix lies. */
+     120             :     I pix2ring (I pix) const;
+     121             : 
+     122           0 :     I xyf2pix(int ix, int iy, int face_num) const
+     123             :       {
+     124           0 :       return (scheme_==RING) ?
+     125           0 :         xyf2ring(ix,iy,face_num) : xyf2nest(ix,iy,face_num);
+     126             :       }
+     127           0 :     void pix2xyf(I pix, int &ix, int &iy, int &face_num) const
+     128             :       {
+     129           0 :       (scheme_==RING) ?
+     130           0 :         ring2xyf(pix,ix,iy,face_num) : nest2xyf(pix,ix,iy,face_num);
+     131           0 :       }
+     132             : 
+     133             :     /*! Translates a pixel number from NEST to RING. */
+     134             :     I nest2ring (I pix) const;
+     135             :     /*! Translates a pixel number from RING to NEST. */
+     136             :     I ring2nest (I pix) const;
+     137             :     /*! Translates a pixel number from NEST to its Peano index. */
+     138             :     I nest2peano (I pix) const;
+     139             :     /*! Translates a pixel number from its Peano index to NEST. */
+     140             :     I peano2nest (I pix) const;
+     141             : 
+     142             :     /*! Returns the number of the pixel which contains the angular coordinates
+     143             :         (\a z:=cos(theta), \a phi).
+     144             :         \note This method is inaccurate near the poles at high resolutions. */
+     145           0 :     I zphi2pix (double z, double phi) const
+     146           0 :       { return loc2pix(z,phi,0.,false); }
+     147             : 
+     148             :     /*! Returns the number of the pixel which contains the angular coordinates
+     149             :         \a ang. */
+     150           0 :     I ang2pix (const pointing &ang) const
+     151             :       {
+     152             :       const double pi_=3.141592653589793238462643383279502884197;
+     153           0 :       planck_assert((ang.theta>=0)&&(ang.theta<=pi_),"invalid theta value");
+     154           0 :       return ((ang.theta<0.01) || (ang.theta > 3.14159-0.01)) ?
+     155           0 :         loc2pix(cos(ang.theta),ang.phi,sin(ang.theta),true) :
+     156           0 :         loc2pix(cos(ang.theta),ang.phi,0.,false);
+     157             :       }
+     158             :     /*! Returns the number of the pixel which contains the vector \a vec
+     159             :         (\a vec is normalized if necessary). */
+     160       24585 :     I vec2pix (const vec3 &vec) const
+     161             :       {
+     162       24585 :       double xl = 1./vec.Length();
+     163             :       double phi = safe_atan2(vec.y,vec.x);
+     164       24585 :       double nz = vec.z*xl;
+     165       24585 :       if (std::abs(nz)>0.99)
+     166         241 :         return loc2pix (nz,phi,sqrt(vec.x*vec.x+vec.y*vec.y)*xl,true);
+     167             :       else
+     168       24344 :         return loc2pix (nz,phi,0,false);
+     169             :       }
+     170             : 
+     171             :     /*! Returns the angular coordinates (\a z:=cos(theta), \a phi) of the center
+     172             :         of the pixel with number \a pix.
+     173             :         \note This method is inaccurate near the poles at high resolutions. */
+     174           0 :     void pix2zphi (I pix, double &z, double &phi) const
+     175             :       {
+     176             :       bool dum_b;
+     177             :       double dum_d;
+     178           0 :       pix2loc(pix,z,phi,dum_d,dum_b);
+     179           0 :       }
+     180             : 
+     181             :     /*! Returns the angular coordinates of the center of the pixel with
+     182             :         number \a pix. */
+     183           0 :     pointing pix2ang (I pix) const
+     184             :       {
+     185             :       double z, phi, sth;
+     186             :       bool have_sth;
+     187           0 :       pix2loc (pix,z,phi,sth,have_sth);
+     188           0 :       return have_sth ? pointing(atan2(sth,z),phi) : pointing(acos(z),phi);
+     189             :       }
+     190             :     /*! Returns the vector to the center of the pixel with number \a pix. */
+     191      135593 :     vec3 pix2vec (I pix) const
+     192             :       {
+     193             :       double z, phi, sth;
+     194             :       bool have_sth;
+     195      135593 :       pix2loc (pix,z,phi,sth,have_sth);
+     196      135593 :       if (have_sth)
+     197        1417 :         return vec3(sth*cos(phi),sth*sin(phi),z);
+     198             :       else
+     199             :         {
+     200             :         vec3 res;
+     201      134176 :         res.set_z_phi (z, phi);
+     202      134176 :         return res;
+     203             :         }
+     204             :       }
+     205             : 
+     206             :     template<typename I2> void query_disc_internal (pointing ptg, double radius,
+     207             :       int fact, rangeset<I2> &pixset) const;
+     208             : 
+     209             :     /*! Returns the range set of all pixels whose centers lie within the disk
+     210             :         defined by \a dir and \a radius.
+     211             :         \param dir the angular coordinates of the disk center
+     212             :         \param radius the radius (in radians) of the disk
+     213             :         \param pixset a \a rangeset object containing the indices of all pixels
+     214             :            whose centers lie inside the disk
+     215             :         \note This method is more efficient in the RING scheme. */
+     216             :     void query_disc (pointing ptg, double radius, rangeset<I> &pixset) const;
+     217             :     /*! Returns the range set of all pixels which overlap with the disk
+     218             :         defined by \a dir and \a radius.
+     219             :         \param dir the angular coordinates of the disk center
+     220             :         \param radius the radius (in radians) of the disk
+     221             :         \param pixset a \a rangeset object containing the indices of all pixels
+     222             :            overlapping with the disk.
+     223             :         \param fact The overlapping test will be done at the resolution
+     224             :            \a fact*nside. For NESTED ordering, \a fact must be a power of 2,
+     225             :            else it can be any positive integer. A typical choice would be 4.
+     226             :         \note This method may return some pixels which don't overlap with
+     227             :            the disk at all. The higher \a fact is chosen, the fewer false
+     228             :            positives are returned, at the cost of increased run time.
+     229             :         \note This method is more efficient in the RING scheme. */
+     230             :     void query_disc_inclusive (pointing ptg, double radius, rangeset<I> &pixset,
+     231             :       int fact=1) const;
+     232             : 
+     233             :     /*! \deprecated Please use the version based on \a rangeset */
+     234           0 :     void query_disc (const pointing &dir, double radius,
+     235             :       std::vector<I> &listpix) const
+     236             :       {
+     237             :       rangeset<I> pixset;
+     238           0 :       query_disc(dir,radius,pixset);
+     239           0 :       pixset.toVector(listpix);
+     240           0 :       }
+     241             :     /*! \deprecated Please use the version based on \a rangeset */
+     242           0 :     void query_disc_inclusive (const pointing &dir, double radius,
+     243             :       std::vector<I> &listpix, int fact=1) const
+     244             :       {
+     245             :       rangeset<I> pixset;
+     246           0 :       query_disc_inclusive(dir,radius,pixset,fact);
+     247           0 :       pixset.toVector(listpix);
+     248           0 :       }
+     249             : 
+     250             :     template<typename I2> void query_polygon_internal
+     251             :       (const std::vector<pointing> &vertex, int fact,
+     252             :       rangeset<I2> &pixset) const;
+     253             : 
+     254             :     /*! Returns a range set of pixels whose centers lie within the convex
+     255             :         polygon defined by the \a vertex array.
+     256             :         \param vertex array containing the vertices of the polygon.
+     257             :         \param pixset a \a rangeset object containing the indices of all pixels
+     258             :            whose centers lie inside the polygon
+     259             :         \note This method is more efficient in the RING scheme. */
+     260             :     void query_polygon (const std::vector<pointing> &vertex,
+     261             :       rangeset<I> &pixset) const;
+     262             : 
+     263             :     /*! Returns a range set of pixels which overlap with the convex
+     264             :         polygon defined by the \a vertex array.
+     265             :         \param vertex array containing the vertices of the polygon.
+     266             :         \param pixset a \a rangeset object containing the indices of all pixels
+     267             :            overlapping with the polygon.
+     268             :         \param fact The overlapping test will be done at the resolution
+     269             :            \a fact*nside. For NESTED ordering, \a fact must be a power of 2,
+     270             :            else it can be any positive integer. A typical choice would be 4.
+     271             :         \note This method may return some pixels which don't overlap with
+     272             :            the polygon at all. The higher \a fact is chosen, the fewer false
+     273             :            positives are returned, at the cost of increased run time.
+     274             :         \note This method is more efficient in the RING scheme. */
+     275             :     void query_polygon_inclusive (const std::vector<pointing> &vertex,
+     276             :       rangeset<I> &pixset, int fact=1) const;
+     277             : 
+     278             :     /*! Returns a range set of pixels whose centers lie within the colatitude
+     279             :         range defined by \a theta1 and \a theta2 (if \a inclusive==false), or
+     280             :         which overlap with this region (if \a inclusive==true). If
+     281             :         \a theta1<theta2, the region between both angles is considered,
+     282             :         otherwise the regions \a 0<theta<theta2 and \a theta1<theta<pi.
+     283             :         \param theta1 first colatitude
+     284             :         \param theta2 second colatitude
+     285             :         \param inclusive if \a false, return the exact set of pixels whose
+     286             :            pixels centers lie within the region; if \a true, return all pixels
+     287             :            that overlap with the region. */
+     288             :     void query_strip (double theta1, double theta2, bool inclusive,
+     289             :       rangeset<I> &pixset) const;
+     290             : 
+     291             :     /*! Returns useful information about a given ring of the map.
+     292             :         \param ring the ring number (the number of the first ring is 1)
+     293             :         \param startpix the number of the first pixel in the ring
+     294             :                (NOTE: this is always given in the RING numbering scheme!)
+     295             :         \param ringpix the number of pixels in the ring
+     296             :         \param costheta the cosine of the colatitude of the ring
+     297             :         \param sintheta the sine of the colatitude of the ring
+     298             :         \param shifted if \a true, the center of the first pixel is not at
+     299             :                \a phi=0 */
+     300             :     void get_ring_info (I ring, I &startpix, I &ringpix,
+     301             :       double &costheta, double &sintheta, bool &shifted) const;
+     302             :     /*! Returns useful information about a given ring of the map.
+     303             :         \param ring the ring number (the number of the first ring is 1)
+     304             :         \param startpix the number of the first pixel in the ring
+     305             :                (NOTE: this is always given in the RING numbering scheme!)
+     306             :         \param ringpix the number of pixels in the ring
+     307             :         \param theta the colatitude (in radians) of the ring
+     308             :         \param shifted if \a true, the center of the first pixel is not at
+     309             :                \a phi=0 */
+     310             :     void get_ring_info2 (I ring, I &startpix, I &ringpix,
+     311             :       double &theta, bool &shifted) const;
+     312             :     /*! Returns useful information about a given ring of the map.
+     313             :         \param ring the ring number (the number of the first ring is 1)
+     314             :         \param startpix the number of the first pixel in the ring
+     315             :                (NOTE: this is always given in the RING numbering scheme!)
+     316             :         \param ringpix the number of pixels in the ring
+     317             :         \param shifted if \a true, the center of the first pixel is not at
+     318             :                \a phi=0 */
+     319             :     void get_ring_info_small (I ring, I &startpix, I &ringpix,
+     320             :         bool &shifted) const;
+     321             :     /*! Returns the neighboring pixels of \a pix in \a result.
+     322             :         On exit, \a result contains (in this order)
+     323             :         the pixel numbers of the SW, W, NW, N, NE, E, SE and S neighbor
+     324             :         of \a pix. If a neighbor does not exist (this can only be the case
+     325             :         for the W, N, E and S neighbors), its entry is set to -1.
+     326             : 
+     327             :         \note This method works in both RING and NEST schemes, but is
+     328             :           considerably faster in the NEST scheme. */
+     329             :     void neighbors (I pix, fix_arr<I,8> &result) const;
+     330             :     /*! Returns interpolation information for the direction \a ptg.
+     331             :         The surrounding pixels are returned in \a pix, their corresponding
+     332             :         weights in \a wgt.
+     333             :         \note This method works in both RING and NEST schemes, but is
+     334             :           considerably faster in the RING scheme. */
+     335             :     void get_interpol (const pointing &ptg, fix_arr<I,4> &pix,
+     336             :                        fix_arr<double,4> &wgt) const;
+     337             : 
+     338             :     /*! Returns the order parameter of the object. */
+     339         421 :     int Order() const { return order_; }
+     340             :     /*! Returns the \a N_side parameter of the object. */
+     341           0 :     I Nside() const { return nside_; }
+     342             :     /*! Returns the number of pixels of the object. */
+     343    10403763 :     I Npix() const { return npix_; }
+     344             :     /*! Returns the ordering scheme of the object. */
+     345           0 :     Healpix_Ordering_Scheme Scheme() const { return scheme_; }
+     346             : 
+     347             :     /*! Returns \a true, if both objects have the same nside and scheme,
+     348             :         else \a false. */
+     349           0 :     bool conformable (const T_Healpix_Base &other) const
+     350           0 :       { return ((nside_==other.nside_) && (scheme_==other.scheme_)); }
+     351             : 
+     352             :     /*! Swaps the contents of two Healpix_Base objects. */
+     353             :     void swap (T_Healpix_Base &other);
+     354             : 
+     355             :     /*! Returns the maximum angular distance (in radian) between any pixel
+     356             :         center and its corners. */
+     357             :     double max_pixrad() const;
+     358             : 
+     359             :     /*! Returns the maximum angular distance (in radian) between any pixel
+     360             :         center and its corners in a given ring. */
+     361             :     double max_pixrad(I ring) const;
+     362             : 
+     363             :     /*! Returns a set of points along the boundary of the given pixel.
+     364             :         \a step=1 gives 4 points on the corners. The first point corresponds
+     365             :         to the northernmost corner, the subsequent points follow the pixel
+     366             :         boundary through west, south and east corners.
+     367             :         \param pix pixel index number
+     368             :         \param step the number of returned points is 4*step. */
+     369             :     void boundaries (I pix, tsize step, std::vector<vec3> &out) const;
+     370             : 
+     371             :     arr<int> swap_cycles() const;
+     372             :   };
+     373             : 
+     374             : /*! T_Healpix_Base for Nside up to 2^13. */
+     375             : typedef T_Healpix_Base<int> Healpix_Base;
+     376             : /*! T_Healpix_Base for Nside up to 2^29. */
+     377             : typedef T_Healpix_Base<int64> Healpix_Base2;
+     378             : 
+     379             : } // namespace healpix
+     380             : #endif
+     381             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html new file mode 100644 index 000000000..0195d8cd1 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html @@ -0,0 +1,173 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:3317319.1 %
Date:2024-04-08 14:58:22Functions:5628.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.h +
0.0%
+
0.0 %0 / 20.0 %0 / 1
arr.h +
0.0%
+
0.0 %0 / 150.0 %0 / 1
geom_utils.h +
0.0%
+
0.0 %0 / 40.0 %0 / 2
alloc_utils.h +
0.0%
+
0.0 %0 / 20.0 %0 / 6
rangeset.h +
0.0%
+
0.0 %0 / 510.0 %0 / 12
healpix_base.h +
32.0%32.0%
+
32.0 %16 / 508.8 %3 / 34
math_utils.h +
30.4%30.4%
+
30.4 %7 / 2325.0 %1 / 4
vec3.h +
45.5%45.5%
+
45.5 %10 / 2250.0 %1 / 2
pointing.h +
0.0%
+
0.0 %0 / 4-0 / 0
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html new file mode 100644 index 000000000..19da9ac89 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html @@ -0,0 +1,173 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:3317319.1 %
Date:2024-04-08 14:58:22Functions:5628.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.h +
0.0%
+
0.0 %0 / 20.0 %0 / 1
alloc_utils.h +
0.0%
+
0.0 %0 / 20.0 %0 / 6
geom_utils.h +
0.0%
+
0.0 %0 / 40.0 %0 / 2
pointing.h +
0.0%
+
0.0 %0 / 4-0 / 0
arr.h +
0.0%
+
0.0 %0 / 150.0 %0 / 1
rangeset.h +
0.0%
+
0.0 %0 / 510.0 %0 / 12
math_utils.h +
30.4%30.4%
+
30.4 %7 / 2325.0 %1 / 4
healpix_base.h +
32.0%32.0%
+
32.0 %16 / 508.8 %3 / 34
vec3.h +
45.5%45.5%
+
45.5 %10 / 2250.0 %1 / 2
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/index.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/index.html new file mode 100644 index 000000000..ce3223c46 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/index.html @@ -0,0 +1,173 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:3317319.1 %
Date:2024-04-08 14:58:22Functions:5628.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
alloc_utils.h +
0.0%
+
0.0 %0 / 20.0 %0 / 6
arr.h +
0.0%
+
0.0 %0 / 150.0 %0 / 1
error_handling.h +
0.0%
+
0.0 %0 / 20.0 %0 / 1
geom_utils.h +
0.0%
+
0.0 %0 / 40.0 %0 / 2
healpix_base.h +
32.0%32.0%
+
32.0 %16 / 508.8 %3 / 34
math_utils.h +
30.4%30.4%
+
30.4 %7 / 2325.0 %1 / 4
pointing.h +
0.0%
+
0.0 %0 / 4-0 / 0
rangeset.h +
0.0%
+
0.0 %0 / 510.0 %0 / 12
vec3.h +
45.5%45.5%
+
45.5 %10 / 2250.0 %1 / 2
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html new file mode 100644 index 000000000..822b61bad --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/math_utils.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - math_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:72330.4 %
Date:2024-04-08 14:58:22Functions:1425.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14isqrt_helper__IlLb1EE5isqrtEl0
_ZN7healpix5ilog2IiEEiT_0
_ZN7healpix5ilog2IlEEiT_0
_ZN7healpix7fmoduloEdd24585
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html new file mode 100644 index 000000000..0fdeff09e --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/math_utils.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - math_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:72330.4 %
Date:2024-04-08 14:58:22Functions:1425.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14isqrt_helper__IlLb1EE5isqrtEl0
_ZN7healpix5ilog2IiEEiT_0
_ZN7healpix5ilog2IlEEiT_0
_ZN7healpix7fmoduloEdd24585
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html new file mode 100644 index 000000000..badf8789f --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html @@ -0,0 +1,259 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/math_utils.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - math_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:72330.4 %
Date:2024-04-08 14:58:22Functions:1425.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*! \file math_utils.h
+      26             :  *  Various convenience mathematical functions.
+      27             :  *
+      28             :  *  Copyright (C) 2002-2012 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #ifndef PLANCK_MATH_UTILS_H
+      33             : #define PLANCK_MATH_UTILS_H
+      34             : 
+      35             : #include <cmath>
+      36             : #include <algorithm>
+      37             : #include "healpix_base/datatypes.h"
+      38             : 
+      39             : namespace healpix{
+      40             : 
+      41             : /*! \defgroup mathutilsgroup Mathematical helper functions */
+      42             : /*! \{ */
+      43             : 
+      44             : /*! Returns \e true if | \a a-b | <= \a epsilon * | \a b |, else \e false. */
+      45             : template<typename F> inline bool approx (F a, F b, F epsilon=1e-5)
+      46             :   {
+      47             :   using namespace std;
+      48             :   return abs(a-b) <= (epsilon*abs(b));
+      49             :   }
+      50             : 
+      51             : /*! Returns \e true if | \a a-b | <= \a epsilon, else \e false. */
+      52             : template<typename F> inline bool abs_approx (F a, F b, F epsilon=1e-5)
+      53             :   {
+      54             :   using namespace std;
+      55             :   return abs(a-b) <= epsilon;
+      56             :   }
+      57             : 
+      58             : /*! Returns the largest integer which is smaller than (or equal to) \a arg. */
+      59             : template<typename I, typename F> inline I ifloor (F arg)
+      60             :   {
+      61             :   using namespace std;
+      62           0 :   return I(floor(arg));
+      63             :   }
+      64             : 
+      65             : /*! Returns the integer which is nearest to \a arg. */
+      66             : template<typename I, typename F> inline I nearest (F arg)
+      67             :   { return ifloor<I>(arg+0.5); }
+      68             : 
+      69             : /*! Returns the remainder of the division \a v1/v2.
+      70             :     The result is non-negative.
+      71             :     \a v1 can be positive or negative; \a v2 must be positive. */
+      72       24585 : inline double fmodulo (double v1, double v2)
+      73             :   {
+      74             :   using namespace std;
+      75       24585 :   if (v1>=0)
+      76       12356 :     return (v1<v2) ? v1 : fmod(v1,v2);
+      77       12229 :   double tmp=fmod(v1,v2)+v2;
+      78       12229 :   return (tmp==v2) ? 0. : tmp;
+      79             : //  return (v1>=0) ? ((v1<v2) ? v1 : fmod(v1,v2)) : (fmod(v1,v2)+v2);
+      80             :   }
+      81             : 
+      82             : /*! Returns the remainder of the division \a v1/v2.
+      83             :     The result is non-negative.
+      84             :     \a v1 can be positive or negative; \a v2 must be positive. */
+      85             : template<typename I> inline I imodulo (I v1, I v2)
+      86             :   { I v=v1%v2; return (v>=0) ? v : v+v2; }
+      87             : 
+      88             : /*! Returns -1 if \a signvalue is negative, else +1. */
+      89             : template<typename T> inline T sign (const T& signvalue)
+      90             :   { return (signvalue>=0) ? 1 : -1; }
+      91             : 
+      92             : /*! Returns \a val*pow(-1,m) */
+      93             : template<typename T, typename I> inline T xpow (I m, T val)
+      94             :   { return (m&1) ? -val : val; }
+      95             : 
+      96             : template<typename I, bool g4> struct isqrt_helper__
+      97             :   {};
+      98             : template<typename I> struct isqrt_helper__ <I, false>
+      99             :   {
+     100             :   static uint32 isqrt (I arg)
+     101             :     {
+     102             :     using namespace std;
+     103       44162 :     return uint32 (sqrt(arg+0.5));
+     104             :     }
+     105             :   };
+     106             : template<typename I> struct isqrt_helper__ <I, true>
+     107             :   {
+     108           0 :   static uint32 isqrt (I arg)
+     109             :     {
+     110             :     using namespace std;
+     111           0 :     I res = sqrt(double(arg)+0.5);
+     112           0 :     if (arg<(int64(1)<<50)) return uint32(res);
+     113           0 :     if (res*res>arg)
+     114           0 :       --res;
+     115           0 :     else if ((res+1)*(res+1)<=arg)
+     116             :       ++res;
+     117           0 :     return uint32(res);
+     118             :     }
+     119             :   };
+     120             : 
+     121             : /*! Returns the integer \a n, which fulfills \a n*n<=arg<(n+1)*(n+1). */
+     122             : template<typename I> inline uint32 isqrt (I arg)
+     123           0 :   { return isqrt_helper__<I,(sizeof(I)>4)>::isqrt(arg); }
+     124             : 
+     125             : /*! Returns the largest integer \a n that fulfills \a 2^n<=arg. */
+     126           0 : template<typename I> inline int ilog2 (I arg)
+     127             :   {
+     128             :   int res=0;
+     129           0 :   while (arg > 0x0000FFFF) { res+=16; arg>>=16; }
+     130           0 :   if (arg > 0x000000FF) { res|=8; arg>>=8; }
+     131           0 :   if (arg > 0x0000000F) { res|=4; arg>>=4; }
+     132           0 :   if (arg > 0x00000003) { res|=2; arg>>=2; }
+     133           0 :   if (arg > 0x00000001) { res|=1; }
+     134           0 :   return res;
+     135             :   }
+     136             : 
+     137             : /*! Returns \a atan2(y,x) if \a x!=0 or \a y!=0; else returns 0. */
+     138             : inline double safe_atan2 (double y, double x)
+     139             :   {
+     140             :   using namespace std;
+     141       61874 :   return ((x==0.) && (y==0.)) ? 0.0 : atan2(y,x);
+     142             :   }
+     143             : 
+     144             : /*! Helper function for linear interpolation (or extrapolation).
+     145             :     The array must be ordered in ascending order; no two values may be equal. */
+     146             : template<typename T, typename Iter, typename Comp> inline void interpol_helper
+     147             :   (const Iter &begin, const Iter &end, const T &val, Comp comp, tsize &idx,
+     148             :   T &frac)
+     149             :   {
+     150             :   using namespace std;
+     151             :   planck_assert((end-begin)>1,"sequence too small for interpolation");
+     152             :   idx = lower_bound(begin,end,val,comp)-begin;
+     153             :   if (idx>0) --idx;
+     154             :   idx = min(tsize(end-begin-2),idx);
+     155             :   frac = (val-begin[idx])/(begin[idx+1]-begin[idx]);
+     156             :   }
+     157             : 
+     158             : /*! Helper function for linear interpolation (or extrapolation).
+     159             :     The array must be ordered in ascending order; no two values may be equal. */
+     160             : template<typename T, typename Iter> inline void interpol_helper
+     161             :   (const Iter &begin, const Iter &end, const T &val, tsize &idx, T &frac)
+     162             :   { interpol_helper (begin,end,val,std::less<T>(),idx,frac); }
+     163             : 
+     164             : /*! \} */
+     165             : 
+     166             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c)
+     167             :   { return (a==b) && (a==c); }
+     168             : 
+     169             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c,
+     170             :   const T &d)
+     171             :   { return (a==b) && (a==c) && (a==d); }
+     172             : 
+     173             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c,
+     174             :   const T &d, const T &e)
+     175             :   { return (a==b) && (a==c) && (a==d) && (a==e); }
+     176             : 
+     177             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c,
+     178             :   const T &d, const T &e, const T &f)
+     179             :   { return (a==b) && (a==c) && (a==d) && (a==e) && (a==f); }
+     180             : 
+     181             : } // namespace healpix
+     182             : #endif
+     183             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html new file mode 100644 index 000000000..bd57abfaa --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/pointing.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - pointing.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html new file mode 100644 index 000000000..1bde73dd1 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html @@ -0,0 +1,72 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/pointing.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - pointing.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ +
+ + + + + + +

Function Name Sort by function nameHit count Sort by hit count
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html new file mode 100644 index 000000000..59e765ab6 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html @@ -0,0 +1,161 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/pointing.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - pointing.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:00-
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*! \file pointing.h
+      26             :  *  Class representing a direction in 3D space
+      27             :  *
+      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #ifndef PLANCK_POINTING_H
+      33             : #define PLANCK_POINTING_H
+      34             : 
+      35             : #include <cmath>
+      36             : #include "healpix_base/vec3.h"
+      37             : 
+      38             : namespace healpix{
+      39             : 
+      40             : /*! \defgroup pointinggroup Pointings */
+      41             : /*! \{ */
+      42             : 
+      43             : /*! Class representing a direction in 3D space or a location on the
+      44             :     unit sphere. All angles in radians. */
+      45             : class pointing
+      46             :   {
+      47             :   public:
+      48             :     /*! Colatitude of the pointing (i.e. the North pole is at \a theta=0). */
+      49             :     double theta;
+      50             :     /*! Longitude of the pointing. */
+      51             :     double phi;
+      52             : 
+      53             :     /*! Default constructor. \a theta and \a phi are not initialized. */
+      54           0 :     pointing() {}
+      55             :     /*! Creates a pointing with \a Theta and \a Phi. */
+      56           0 :     pointing (double Theta, double Phi) : theta(Theta), phi(Phi) {}
+      57             : 
+      58             : // FIXME: should become "explicit" some time
+      59             :     /*! Creates a pointing from the vector \a inp. \a inp need not be
+      60             :         normalized. */
+      61             :     pointing (const vec3 &inp)
+      62           0 :       { from_vec3(inp); }
+      63             : // FIXME: should be removed some time
+      64             :     /*! Returns a normalized vector pointing in the same direction. */
+      65             :     operator vec3() const
+      66           0 :       { return to_vec3(); }
+      67             :     /*! Returns a normalized vector pointing in the same direction. */
+      68             :     vec3 to_vec3() const;
+      69             :     /*! Converts \a inp to \a ptg. \a inp need not be normalized. */
+      70             :     void from_vec3 (const vec3 &inp);
+      71             :     /*! Changes the angles so that \a 0<=theta<=pi. */
+      72             :     void normalize_theta();
+      73             :     /*! Changes the angles so that \a 0<=theta<=pi and \a 0<=phi<2*pi. */
+      74             :     void normalize();
+      75             :   };
+      76             : 
+      77             : /*! Writes \a p to \a os.
+      78             :     \relates pointing */
+      79             : std::ostream &operator<< (std::ostream &os, const pointing &p);
+      80             : 
+      81             : /*! \} */
+      82             : 
+      83             : } // namespace healpix
+      84             : #endif
+      85             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html new file mode 100644 index 000000000..9daab7962 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html @@ -0,0 +1,120 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/rangeset.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - rangeset.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0510.0 %
Date:2024-04-08 14:58:22Functions:0120.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8rangesetIiE6appendERKS1_0
_ZN7healpix8rangesetIiE6appendERKiS3_0
_ZN7healpix8rangesetIiE9addRemoveEiil0
_ZN7healpix8rangesetIiE9intersectERKiS3_0
_ZN7healpix8rangesetIlE6appendERKS1_0
_ZN7healpix8rangesetIlE6appendERKlS3_0
_ZN7healpix8rangesetIlE9addRemoveElll0
_ZN7healpix8rangesetIlE9intersectERKlS3_0
_ZNK7healpix8rangesetIiE3iivERKi0
_ZNK7healpix8rangesetIiE8toVectorERSt6vectorIiSaIiEE0
_ZNK7healpix8rangesetIlE3iivERKl0
_ZNK7healpix8rangesetIlE8toVectorERSt6vectorIlSaIlEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html new file mode 100644 index 000000000..8a90294c3 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html @@ -0,0 +1,120 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/rangeset.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - rangeset.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0510.0 %
Date:2024-04-08 14:58:22Functions:0120.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8rangesetIiE6appendERKS1_0
_ZN7healpix8rangesetIiE6appendERKiS3_0
_ZN7healpix8rangesetIiE9addRemoveEiil0
_ZN7healpix8rangesetIiE9intersectERKiS3_0
_ZN7healpix8rangesetIlE6appendERKS1_0
_ZN7healpix8rangesetIlE6appendERKlS3_0
_ZN7healpix8rangesetIlE9addRemoveElll0
_ZN7healpix8rangesetIlE9intersectERKlS3_0
_ZNK7healpix8rangesetIiE3iivERKi0
_ZNK7healpix8rangesetIiE8toVectorERSt6vectorIiSaIiEE0
_ZNK7healpix8rangesetIlE3iivERKl0
_ZNK7healpix8rangesetIlE8toVectorERSt6vectorIlSaIlEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html new file mode 100644 index 000000000..177519f90 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html @@ -0,0 +1,363 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/rangeset.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - rangeset.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0510.0 %
Date:2024-04-08 14:58:22Functions:0120.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*! \file rangeset.h
+      26             :  *  Class for storing sets of ranges of integer numbers
+      27             :  *
+      28             :  *  Copyright (C) 2011, 2012 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #ifndef PLANCK_RANGESET_H
+      33             : #define PLANCK_RANGESET_H
+      34             : 
+      35             : #include <algorithm>
+      36             : #include <vector>
+      37             : #include <utility>
+      38             : #include <iostream>
+      39             : #include "healpix_base/datatypes.h"
+      40             : #include "healpix_base/error_handling.h"
+      41             : 
+      42             : namespace healpix{
+      43             : 
+      44             : /*! Class for storing sets of ranges of integer numbers */
+      45           0 : template<typename T> class rangeset
+      46             :   {
+      47             :   private:
+      48             :     typedef std::vector<T> rtype;
+      49             :     typedef typename rtype::iterator iterator;
+      50             :     typedef typename rtype::const_iterator c_iterator;
+      51             :     rtype r;
+      52             : 
+      53           0 :     tdiff iiv (const T &val) const
+      54           0 :       { return tdiff(std::upper_bound(r.begin(),r.end(),val)-r.begin())-1; }
+      55             : 
+      56           0 :     void addRemove (T a, T b, tdiff v)
+      57             :       {
+      58           0 :       tdiff pos1=iiv(a), pos2=iiv(b);
+      59           0 :       if ((pos1>=0) && (r[pos1]==a)) --pos1;
+      60             :       // first to delete is at pos1+1; last is at pos2
+      61           0 :       bool insert_a = (pos1&1)==v;
+      62           0 :       bool insert_b = (pos2&1)==v;
+      63           0 :       int rmstart=pos1+1+(insert_a ? 1 : 0);
+      64           0 :       int rmend  =pos2-(insert_b?1:0);
+      65             : 
+      66           0 :       planck_assert((rmend-rmstart)&1,"cannot happen");
+      67             : 
+      68           0 :       if (insert_a && insert_b && (pos1+1>pos2)) // insert
+      69             :         {
+      70           0 :         r.insert(r.begin()+pos1+1,2,a);
+      71           0 :         r[pos1+2]=b;
+      72             :         }
+      73             :       else
+      74             :         {
+      75           0 :         if (insert_a) r[pos1+1]=a;
+      76           0 :         if (insert_b) r[pos2]=b;
+      77           0 :         r.erase(r.begin()+rmstart,r.begin()+rmend+1);
+      78             :         }
+      79           0 :       }
+      80             : 
+      81             :     static void generalUnion (const rtype &a, const rtype &b,
+      82             :       bool flip_a, bool flip_b, rtype &c)
+      83             :       {
+      84             :       planck_assert((&c!=&a)&&(&c!=&b), "cannot overwrite the rangeset");
+      85             :       c.clear();
+      86             :       bool state_a=flip_a, state_b=flip_b, state_res=state_a||state_b;
+      87             :       tsize ia=0, ea=a.size(), ib=0, eb=b.size();
+      88             :       bool runa = ia!=ea, runb = ib!=eb;
+      89             :       while(runa||runb)
+      90             :         {
+      91             :         bool adv_a=false, adv_b=false;
+      92             :         T val,va=T(),vb=T();
+      93             :         if (runa) va = a[ia];
+      94             :         if (runb) vb = b[ib];
+      95             :         if (runa && (!runb || (va<=vb))) { adv_a=true; val=va; }
+      96             :         if (runb && (!runa || (vb<=va))) { adv_b=true; val=vb; }
+      97             :         if (adv_a) { state_a=!state_a; ++ia; runa = ia!=ea; }
+      98             :         if (adv_b) { state_b=!state_b; ++ib; runb = ib!=eb; }
+      99             :         if ((state_a||state_b)!=state_res)
+     100             :           { c.push_back(val); state_res = !state_res; }
+     101             :         }
+     102             :       }
+     103             : 
+     104             :   public:
+     105             :     /*! Removes all rangeset entries. */
+     106             :     void clear() { r.clear(); }
+     107             :     /*! Reserves space for \a n ranges. */
+     108             :     void reserve(tsize n) { r.reserve(2*n); }
+     109             :     /*! Returns the current number of ranges. */
+     110           0 :     tsize size() const { return r.size()>>1; }
+     111             :     /*! Returns the current vector of ranges. */
+     112             :     const rtype &data() const { return r; }
+     113             : 
+     114             :     /*! Returns the first value of range \a i. */
+     115           0 :     const T &ivbegin (tdiff i) const { return r[2*i]; }
+     116             :     /*! Returns the one-past-last value of range \a i. */
+     117           0 :     const T &ivend (tdiff i) const { return r[2*i+1]; }
+     118             :     /*! Returns the length of range \a i. */
+     119             :     T ivlen (tdiff i) const { return r[2*i+1]-r[2*i]; }
+     120             : 
+     121             :     /*! Appends \a [v1;v2[ to the rangeset. \a v1 must be larger
+     122             :         than the minimum of the last range in the rangeset. */
+     123           0 :     void append(const T &v1, const T &v2)
+     124             :       {
+     125           0 :       if (v2<=v1) return;
+     126           0 :       if ((!r.empty()) && (v1<=r.back()))
+     127             :         {
+     128           0 :         planck_assert (v1>=r[r.size()-2],"bad append operation");
+     129           0 :         if (v2>r.back()) r.back()=v2;
+     130             :         }
+     131             :       else
+     132           0 :         { r.push_back(v1); r.push_back(v2); }
+     133             :       }
+     134             :     /*! Appends \a [v;v+1[ to the rangeset. \a v must be larger
+     135             :         than the minimum of the last range in the rangeset. */
+     136             :     void append(const T &v)
+     137           0 :       { append(v,v+1); }
+     138             : 
+     139             :     /*! Appends \a other to the rangeset. All values in \a other must be larger
+     140             :         than the minimum of the last range in the rangeset. */
+     141           0 :     void append (const rangeset &other)
+     142             :       {
+     143           0 :       for (tsize j=0; j<other.size(); ++j)
+     144           0 :         append(other.ivbegin(j),other.ivend(j));
+     145           0 :       }
+     146             : 
+     147             :     /*! After this operation, the rangeset contains the union of itself
+     148             :         with \a [v1;v2[. */
+     149             :     void add(const T &v1, const T &v2) { addRemove(v1,v2,1); }
+     150             :     /*! After this operation, the rangeset contains the union of itself
+     151             :         with \a [v;v+1[. */
+     152             :     void add(const T &v) { addRemove(v,v+1,1); }
+     153             : 
+     154             :     /*! Removes all values within \a [v1;v2[ from the rangeset. */
+     155           0 :     void remove(const T &v1, const T &v2) { addRemove(v1,v2,0); }
+     156             :     /*! Removes the value \a v from the rangeset. */
+     157             :     void remove(const T &v) { addRemove(v,v+1,0); }
+     158             : 
+     159             :     /*! Removes all values not within \a [v1;v2[ from the rangeset. */
+     160           0 :     void intersect (const T &a, const T &b)
+     161             :       {
+     162           0 :       tdiff pos1=iiv(a), pos2=iiv(b);
+     163           0 :       if ((pos2>=0) && (r[pos2]==b)) --pos2;
+     164             :       // delete all up to pos1 (inclusive); and starting from pos2+1
+     165           0 :       bool insert_a = (pos1&1)==0;
+     166           0 :       bool insert_b = (pos2&1)==0;
+     167             : 
+     168             :       // cut off end
+     169           0 :       r.erase(r.begin()+pos2+1,r.end());
+     170           0 :       if (insert_b) r.push_back(b);
+     171             : 
+     172             :       // erase start
+     173           0 :       if (insert_a) r[pos1--]=a;
+     174           0 :       if (pos1>=0)
+     175             :         r.erase(r.begin(),r.begin()+pos1+1);
+     176           0 :       }
+     177             : 
+     178             :     /*! Returns the total number of elements in the rangeset. */
+     179             :     T nval() const
+     180             :       {
+     181             :       T result=T(0);
+     182           0 :       for (tsize i=0; i<r.size(); i+=2)
+     183           0 :         result+=r[i+1]-r[i];
+     184             :       return result;
+     185             :       }
+     186             : 
+     187             :     /*! After this opration, \a res contains all elements of the rangeset
+     188             :         in ascending order. */
+     189           0 :     void toVector (std::vector<T> &res) const
+     190             :       {
+     191             :       res.clear();
+     192           0 :       res.reserve(nval());
+     193           0 :       for (tsize i=0; i<r.size(); i+=2)
+     194           0 :         for (T m(r[i]); m<r[i+1]; ++m)
+     195           0 :           res.push_back(m);
+     196           0 :       }
+     197             : 
+     198             :     /*! After this operation, the rangeset contains the union of itself
+     199             :         and \a other. */
+     200             :     void unite (const rangeset &other)
+     201             :       {
+     202             :       rtype tmp;
+     203             :       generalUnion (r,other.r,false,false,tmp);
+     204             :       std::swap(r,tmp);
+     205             :       }
+     206             :     /*! After this operation, the rangeset contains the intersection of itself
+     207             :         and \a other. */
+     208             :     void intersect (const rangeset &other)
+     209             :       {
+     210             :       rtype tmp;
+     211             :       generalUnion (r,other.r,true,true,tmp);
+     212             :       std::swap(r,tmp);
+     213             :       }
+     214             :     /*! After this operation, the rangeset contains the union of itself
+     215             :         with the inverse of \a other. */
+     216             :     void subtract (const rangeset &other)
+     217             :       {
+     218             :       rtype tmp;
+     219             :       generalUnion (r,other.r,true,false,tmp);
+     220             :       std::swap(r,tmp);
+     221             :       }
+     222             :     /*! After this operation, the rangeset contains the union of \a a
+     223             :         and \a b. */
+     224             :     void setToUnion (const rangeset &a, const rangeset &b)
+     225             :       { generalUnion (a.r,b.r,false,false,r); }
+     226             :     /*! After this operation, the rangeset contains the intersection of \a a
+     227             :         and \a b. */
+     228             :     void setToIntersection (const rangeset &a, const rangeset &b)
+     229             :       { generalUnion (a.r,b.r,true,true,r); }
+     230             :     /*! After this operation, the rangeset contains the union of \a a
+     231             :         with the inverse of \a b. */
+     232             :     void setToDifference (const rangeset &a, const rangeset &b)
+     233             :       { generalUnion (a.r,b.r,true,false,r); }
+     234             : 
+     235             :     /*! Returns the index of the interval containing \a v; if no such interval
+     236             :         exists, -1 is returned. */
+     237             :     tdiff findInterval (const T &v) const
+     238             :       {
+     239             :       tdiff res = iiv(v);
+     240             :       return (res&1) ? -1 : res>>1;
+     241             :       }
+     242             : 
+     243             :     /*! Returns \a true if the rangeset is identical to \a other, else \a false.
+     244             :         */
+     245             :     bool equals (const rangeset &other) const
+     246             :       { return r==other.data(); }
+     247             : 
+     248             :     /*! Returns \a true if the rangeset contains all values in the range
+     249             :         \a [a;b[, else \a false. */
+     250             :     bool containsAll (T a,T b) const
+     251             :       {
+     252             :       tdiff res=iiv(a);
+     253             :       if (res&1) return false;
+     254             :       return (b<=r[res+1]);
+     255             :       }
+     256             :     /*! Returns \a true if the rangeset contains the value \a v,
+     257             :         else \a false. */
+     258             :     bool contains (T v) const
+     259             :       { return !(iiv(v)&1); }
+     260             :     /*! Returns \a true if the rangeset contains all values stored in \a other,
+     261             :         else \a false. */
+     262             :     bool contains (const rangeset &other) const
+     263             :       {
+     264             :       tsize im=0, em=r.size();
+     265             :       for (tsize i=0; i<other.r.size(); i+=2)
+     266             :         {
+     267             :         T a=other.r[i], b=other.r[i+1];
+     268             :         while ((im!=em) && (r[im+1] < a)) im+=2;
+     269             :         if (im==em) return false;
+     270             :         if ((r[im]>a) || (r[im+1]<b)) return false;
+     271             :         }
+     272             :       return true;
+     273             :       }
+     274             :   };
+     275             : 
+     276             : template<typename T> inline std::ostream &operator<< (std::ostream &os,
+     277             :   const rangeset<T> &rs)
+     278             :   {
+     279             :   os << "{ ";
+     280             :   for (tsize i=0; i<rs.size(); ++i)
+     281             :     os << "["<<rs.ivbegin(i)<<";"<<rs.ivend(i)<<"[ ";
+     282             :   return os << "}";
+     283             :   }
+     284             : 
+     285             : } // namespace healpix
+     286             : #endif
+     287             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html new file mode 100644 index 000000000..50398e10d --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/vec3.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - vec3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:102245.5 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix6vec3_tIdE9NormalizeEv0
_ZN7healpix6vec3_tIdE9set_z_phiEdd134176
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html new file mode 100644 index 000000000..633dc74e4 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/vec3.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - vec3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:102245.5 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix6vec3_tIdE9NormalizeEv0
_ZN7healpix6vec3_tIdE9set_z_phiEdd134176
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html new file mode 100644 index 000000000..78b942fb1 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html @@ -0,0 +1,229 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/vec3.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base/include/healpix_base - vec3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:102245.5 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*! \file vec3.h
+      26             :  *  Class representing 3D cartesian vectors
+      27             :  *
+      28             :  *  Copyright (C) 2003, 2006 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #ifndef PLANCK_VEC3_H
+      33             : #define PLANCK_VEC3_H
+      34             : 
+      35             : #include <cmath>
+      36             : #include <iostream>
+      37             : #include "healpix_base/datatypes.h"
+      38             : 
+      39             : namespace healpix{
+      40             : 
+      41             : /*! \defgroup vec3group 3D vectors */
+      42             : /*! \{ */
+      43             : 
+      44             : /*! Class representing a 3D cartesian vector. */
+      45             : template<typename T>class vec3_t
+      46             :   {
+      47             :   public:
+      48             :     T x, /*!< x-coordinate */
+      49             :       y, /*!< y-coordinate */
+      50             :       z; /*!< z-coordinate */
+      51             : 
+      52             :     /*! Default constructor. Does not initialize \a x, \a y, and \a z. */
+      53      244781 :     vec3_t () {}
+      54             :     /*! Creates a vector with the coordinates \a xc, \a yc, and \a zc. */
+      55        1417 :     vec3_t (T xc, T yc, T zc)
+      56        1417 :       : x(xc), y(yc), z(zc) {}
+      57             :     template<typename T2> explicit vec3_t (const vec3_t<T2> &orig)
+      58             :       : x(orig.x), y(orig.y), z(orig.z) {}
+      59             : 
+      60             :     /*! Sets the vector components to \a xc, \a yc, and \a zc. */
+      61             :     void Set (T xc, T yc, T zc)
+      62             :       { x=xc; y=yc; z=zc; }
+      63             :     /*! Creates a unit vector from a z coordinate and an azimuthal angle. */
+      64      134176 :     void set_z_phi (T z_, T phi)
+      65             :       {
+      66             :       using namespace std;
+      67      134176 :       T sintheta = sqrt((T(1)-z_)*(T(1)+z_));
+      68      134176 :       x = sintheta*cos(phi);
+      69      134176 :       y = sintheta*sin(phi);
+      70      134176 :       z = z_;
+      71      134176 :       }
+      72             : 
+      73             :     /*! Normalizes the vector to length 1. */
+      74           0 :     void Normalize ()
+      75             :       {
+      76             :       using namespace std;
+      77           0 :       T l = T(1)/sqrt (x*x + y*y + z*z);
+      78           0 :       x*=l; y*=l; z*=l;
+      79           0 :       }
+      80             : 
+      81             :     vec3_t Norm() const
+      82             :       {
+      83           0 :       vec3_t res(*this);
+      84           0 :       res.Normalize();
+      85             :       return res;
+      86             :       }
+      87             : 
+      88             :     /*! Returns the length of the vector. */
+      89             :     T Length () const
+      90       24585 :       { return sqrt (x*x + y*y + z*z); }
+      91             : 
+      92             :     /*! Returns the squared length of the vector. */
+      93             :     T SquaredLength () const
+      94             :       { return (x*x + y*y + z*z); }
+      95             :     /*! Returns the vector with the signs of all coordinates flipped. */
+      96             :     const vec3_t operator- () const
+      97             :       { return vec3_t (-x, -y, -z); }
+      98             :     /*! Flips the signs of all coordinates. */
+      99             :     void Flip ()
+     100           0 :       { x=-x; y=-y; z=-z; }
+     101             :     /*! Returns (\a *this + \a vec). */
+     102             :     const vec3_t operator+ (const vec3_t &vec) const
+     103           0 :       { return vec3_t (x+vec.x, y+vec.y, z+vec.z); }
+     104             :     /*! Adds \a vec to \a *this. */
+     105             :     vec3_t &operator+= (const vec3_t &vec)
+     106             :       { x+=vec.x; y+=vec.y; z+=vec.z; return *this; }
+     107             :     /*! Returns (\a *this - \a vec). */
+     108             :     const vec3_t operator- (const vec3_t &vec) const
+     109           0 :       { return vec3_t (x-vec.x, y-vec.y, z-vec.z); }
+     110             :     /*! Subtracts \a vec from \a *this. */
+     111             :     vec3_t &operator-= (const vec3_t &vec)
+     112             :       { x-=vec.x; y-=vec.y; z-=vec.z; return *this; }
+     113             :     /*! Returns the vector scaled by \a fact. */
+     114             :     const vec3_t operator* (T fact) const
+     115             :       { return vec3_t (x*fact, y*fact, z*fact); }
+     116             :     /*! Returns the vector scaled by \a 1/fact. */
+     117             :     const vec3_t operator/ (T fact) const
+     118             :       { T xfact = T(1)/fact; return vec3_t (x*xfact, y*xfact, z*xfact); }
+     119             :     /*! Scales the vector by \a fact. */
+     120             :     vec3_t &operator*= (T fact)
+     121           0 :       { x*=fact; y*=fact; z*=fact; return *this; }
+     122             :   };
+     123             : 
+     124             : /*! Returns the dot product of \a v1 and \a v2.
+     125             :     \relates vec3_t */
+     126             : template<typename T> inline T dotprod(const vec3_t<T> &v1, const vec3_t<T> &v2)
+     127           0 :   { return v1.x*v2.x + v1.y*v2.y + v1.z*v2.z; }
+     128             : 
+     129             : /*! Returns the cross product of \a a and \a b.
+     130             :     \relates vec3_t */
+     131             : template<typename T> inline vec3_t<T> crossprod
+     132             :   (const vec3_t<T> &a, const vec3_t<T> &b)
+     133           0 :   { return vec3_t<T>(a.y*b.z - a.z*b.y, a.z*b.x - a.x*b.z, a.x*b.y - a.y*b.x); }
+     134             : 
+     135             : /*! Writes \a v to \a os.
+     136             :     \relates vec3_t */
+     137             : template<typename T> inline std::ostream &operator<<
+     138             :   (std::ostream &os, const vec3_t<T> &v)
+     139             :   {
+     140             :   os << v.x << ", " << v.y << ", " << v.z << std::endl;
+     141             :   return os;
+     142             :   }
+     143             : 
+     144             : /*! Specialisation of vec3_t for 64-bit floating point components */
+     145             : typedef vec3_t<float64> vec3;
+     146             : /*! Specialisation of vec3_t for 32-bit floating point components */
+     147             : typedef vec3_t<float32> vec3f;
+     148             : 
+     149             : /*! \} */
+     150             : 
+     151             : } // namespace healpix
+     152             : #endif
+     153             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/index-sort-f.html b/doc/coverageReport/libs/healpix_base/index-sort-f.html new file mode 100644 index 000000000..90582d17c --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/index-sort-f.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:11279214.1 %
Date:2024-04-08 14:58:22Functions:101069.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
geom_utils.cc +
0.0%
+
0.0 %0 / 250.0 %0 / 3
pointing.cc +
0.0%
+
0.0 %0 / 210.0 %0 / 5
error_handling.cc +
0.0%
+
0.0 %0 / 120.0 %0 / 7
healpix_base.cc +
15.3%15.3%
+
15.3 %112 / 73411.0 %10 / 91
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/index-sort-l.html b/doc/coverageReport/libs/healpix_base/index-sort-l.html new file mode 100644 index 000000000..51b835471 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/index-sort-l.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:11279214.1 %
Date:2024-04-08 14:58:22Functions:101069.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.cc +
0.0%
+
0.0 %0 / 120.0 %0 / 7
pointing.cc +
0.0%
+
0.0 %0 / 210.0 %0 / 5
geom_utils.cc +
0.0%
+
0.0 %0 / 250.0 %0 / 3
healpix_base.cc +
15.3%15.3%
+
15.3 %112 / 73411.0 %10 / 91
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/index.html b/doc/coverageReport/libs/healpix_base/index.html new file mode 100644 index 000000000..5078da2bf --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/index.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:11279214.1 %
Date:2024-04-08 14:58:22Functions:101069.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.cc +
0.0%
+
0.0 %0 / 120.0 %0 / 7
geom_utils.cc +
0.0%
+
0.0 %0 / 250.0 %0 / 3
healpix_base.cc +
15.3%15.3%
+
15.3 %112 / 73411.0 %10 / 91
pointing.cc +
0.0%
+
0.0 %0 / 210.0 %0 / 5
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html new file mode 100644 index 000000000..4499d9636 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/pointing.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - pointing.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:050.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8pointing15normalize_thetaEv0
_ZN7healpix8pointing9from_vec3ERKNS_6vec3_tIdEE0
_ZN7healpix8pointing9normalizeEv0
_ZN7healpixlsERSoRKNS_8pointingE0
_ZNK7healpix8pointing7to_vec3Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/pointing.cc.func.html b/doc/coverageReport/libs/healpix_base/pointing.cc.func.html new file mode 100644 index 000000000..473f90349 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/pointing.cc.func.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/pointing.cc - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - pointing.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:050.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8pointing15normalize_thetaEv0
_ZN7healpix8pointing9from_vec3ERKNS_6vec3_tIdEE0
_ZN7healpix8pointing9normalizeEv0
_ZN7healpixlsERSoRKNS_8pointingE0
_ZNK7healpix8pointing7to_vec3Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html b/doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html new file mode 100644 index 000000000..678a7db26 --- /dev/null +++ b/doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/healpix_base/pointing.cc + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/healpix_base - pointing.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:050.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /*
+       2             :  *  This file is part of libcxxsupport.
+       3             :  *
+       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
+       5             :  *  it under the terms of the GNU General Public License as published by
+       6             :  *  the Free Software Foundation; either version 2 of the License, or
+       7             :  *  (at your option) any later version.
+       8             :  *
+       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
+      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      12             :  *  GNU General Public License for more details.
+      13             :  *
+      14             :  *  You should have received a copy of the GNU General Public License
+      15             :  *  along with libcxxsupport; if not, write to the Free Software
+      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
+      17             :  */
+      18             : 
+      19             : /*
+      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
+      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
+      22             :  *  (DLR).
+      23             :  */
+      24             : 
+      25             : /*! \file pointing.cc
+      26             :  *  Class representing a direction in 3D space
+      27             :  *
+      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
+      29             :  *  \author Martin Reinecke
+      30             :  */
+      31             : 
+      32             : #include "healpix_base/pointing.h"
+      33             : #include "healpix_base/lsconstants.h"
+      34             : #include "healpix_base/math_utils.h"
+      35             : 
+      36             : namespace healpix{
+      37             : 
+      38             : using namespace std;
+      39             : 
+      40           0 : vec3 pointing::to_vec3() const
+      41             :   {
+      42           0 :   double st=sin(theta);
+      43           0 :   return vec3 (st*cos(phi), st*sin(phi), cos(theta));
+      44             :   }
+      45           0 : void pointing::from_vec3 (const vec3 &inp)
+      46             :   {
+      47           0 :   theta = atan2(sqrt(inp.x*inp.x+inp.y*inp.y),inp.z);
+      48           0 :   phi = safe_atan2 (inp.y,inp.x);
+      49           0 :   if (phi<0.) phi += twopi;
+      50           0 :   }
+      51           0 : void pointing::normalize_theta()
+      52             :   {
+      53           0 :   theta=fmodulo(theta,twopi);
+      54           0 :   if (theta>pi)
+      55             :     {
+      56           0 :     phi+=pi;
+      57           0 :     theta=twopi-theta;
+      58             :     }
+      59           0 :   }
+      60           0 : void pointing::normalize()
+      61             :   {
+      62           0 :   normalize_theta();
+      63           0 :   phi=fmodulo(phi,twopi);
+      64           0 :   }
+      65             : 
+      66           0 : ostream &operator<< (ostream &os, const pointing &p)
+      67             :   {
+      68           0 :   os << p.theta << ", " << p.phi << std::endl;
+      69           0 :   return os;
+      70             :   }
+      71             : } // namespace healpix
+      72             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html b/doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html new file mode 100644 index 000000000..3091b54e8 --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss/convert.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kiss - convert.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:71070.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss3strIiEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKT_2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html b/doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html new file mode 100644 index 000000000..df4061a5f --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html @@ -0,0 +1,76 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss/convert.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kiss - convert.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:71070.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ +
+ + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss3strIiEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKT_2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html b/doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html new file mode 100644 index 000000000..6a912c12a --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html @@ -0,0 +1,150 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss/convert.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kiss - convert.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:71070.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef KISS_CONVERT_H
+       2             : #define KISS_CONVERT_H
+       3             : 
+       4             : #include <iostream>
+       5             : #include <sstream>
+       6             : #include <string>
+       7             : #include <typeinfo>
+       8             : #include <stdexcept>
+       9             : 
+      10             : namespace kiss {
+      11             : 
+      12             : class bad_conversion: public std::runtime_error {
+      13             : public:
+      14           0 :         bad_conversion(std::string const& s) :
+      15           0 :                         std::runtime_error(s) {
+      16             :         }
+      17             : };
+      18             : 
+      19             : template<typename T>
+      20           2 : inline std::string str(T const& x) {
+      21           2 :         std::ostringstream o;
+      22           2 :         o.imbue(std::locale("C"));
+      23           2 :         o << x;
+      24           2 :         if (!o) {
+      25             : #ifdef DEBUG
+      26             :                 std::cerr << "bad_conversion: str(" << typeid(x).name() << ")";
+      27             : #endif
+      28           0 :                 throw bad_conversion(std::string("str(") + typeid(x).name() + ")");
+      29             :         }
+      30           2 :         return o.str();
+      31           2 : }
+      32             : 
+      33             : template<typename T>
+      34             : inline void convert(const char *s, T& x) {
+      35             :         if (s == 0) {
+      36             : #ifdef DEBUG
+      37             :                 std::cerr << "bad_conversion: convert, null pointer";
+      38             : #endif
+      39             :                 throw bad_conversion("null pointer");
+      40             :         }
+      41             :         std::istringstream i(s);
+      42             :         i.imbue(std::locale("C"));
+      43             :         i >> x;
+      44             :         if (!i) {
+      45             : #ifdef DEBUG
+      46             :                 std::cerr << "bad_conversion: convert (" << s << ")";
+      47             : #endif
+      48             :                 throw bad_conversion(std::string(s) + " to " + typeid(x).name());
+      49             :         }
+      50             : }
+      51             : 
+      52             : template<typename T>
+      53             : inline void convert(std::string const& s, T& x) {
+      54             :         std::istringstream i(s);
+      55             :         i.imbue(std::locale("C"));
+      56             :         i >> x;
+      57             :         if (!i) {
+      58             : #ifdef DEBUG
+      59             :                 std::cerr << "bad_conversion: convert (" << s << ")";
+      60             : #endif
+      61             :                 throw bad_conversion(s + " to " + typeid(x).name());
+      62             :         }
+      63             : }
+      64             : 
+      65             : template<typename T>
+      66             : inline T convertTo(std::string const& s, bool failIfLeftoverChars = true) {
+      67             :         T x;
+      68             :         convert(s, x, failIfLeftoverChars);
+      69             :         return x;
+      70             : }
+      71             : 
+      72             : } // namespace kiss
+      73             : 
+      74             : #endif /* KISSCONVERT_H */
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html b/doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html new file mode 100644 index 000000000..bb06075e7 --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html @@ -0,0 +1,103 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kissHitTotalCoverage
Test:coverage.info.cleanedLines:111957.9 %
Date:2024-04-08 14:58:22Functions:146720.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
logger.h +
44.4%44.4%
+
44.4 %4 / 919.7 %13 / 66
convert.h +
70.0%70.0%
+
70.0 %7 / 10100.0 %1 / 1
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html b/doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html new file mode 100644 index 000000000..b047c279f --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html @@ -0,0 +1,103 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kissHitTotalCoverage
Test:coverage.info.cleanedLines:111957.9 %
Date:2024-04-08 14:58:22Functions:146720.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
logger.h +
44.4%44.4%
+
44.4 %4 / 919.7 %13 / 66
convert.h +
70.0%70.0%
+
70.0 %7 / 10100.0 %1 / 1
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/index.html b/doc/coverageReport/libs/kiss/include/kiss/index.html new file mode 100644 index 000000000..c4b160333 --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/index.html @@ -0,0 +1,103 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kissHitTotalCoverage
Test:coverage.info.cleanedLines:111957.9 %
Date:2024-04-08 14:58:22Functions:146720.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
convert.h +
70.0%70.0%
+
70.0 %7 / 10100.0 %1 / 1
logger.h +
44.4%44.4%
+
44.4 %4 / 919.7 %13 / 66
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html b/doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html new file mode 100644 index 000000000..35772c48a --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html @@ -0,0 +1,336 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss/logger.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kiss - logger.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4944.4 %
Date:2024-04-08 14:58:22Functions:136619.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6LoggerlsEPFRSoS1_E0
_ZN4kiss6LoggerlsIA11_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA12_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA135_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA14_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA156_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA15_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA16_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA18_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA197_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA231_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA23_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA256_cEERS0_RT_0
_ZN4kiss6LoggerlsIA25_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA26_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA27_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA33_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA34_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA35_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA39_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA40_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA41_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA42_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA46_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA47_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA49_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA53_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA54_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA55_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA69_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA6_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA70_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA71_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA72_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA73_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA74_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA75_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA81_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA82_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA83_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA8_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA93_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA9_KcEERS0_RT_0
_ZN4kiss6LoggerlsIKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIKbEERS0_RT_0
_ZN4kiss6LoggerlsIKiEERS0_RT_0
_ZN4kiss6LoggerlsIKmEERS0_RT_0
_ZN4kiss6LoggerlsIN7crpropa7Vector3IdEEEERS0_RT_0
_ZN4kiss6LoggerlsINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIbEERS0_RT_0
_ZN4kiss6LoggerlsIdEERS0_RT_0
_ZN4kiss6LoggerlsImEERS0_RT_0
_ZN4kiss6LoggerlsIyEERS0_RT_0
_ZN4kiss6LoggerlsIA166_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA3_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA59_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA5_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA7_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA2_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA58_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA64_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA67_KcEERS0_RT_2
_ZN4kiss6LoggerlsIiEERS0_RT_2
_ZN4kiss6LoggerlsIA51_KcEERS0_RT_3
_ZN4kiss6LoggerlsIA131_KcEERS0_RT_4
_ZN4kiss6LoggerlsIA50_KcEERS0_RT_4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html b/doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html new file mode 100644 index 000000000..1f4061bc2 --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html @@ -0,0 +1,336 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss/logger.h - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kiss - logger.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4944.4 %
Date:2024-04-08 14:58:22Functions:136619.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6LoggerlsEPFRSoS1_E0
_ZN4kiss6LoggerlsIA11_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA12_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA131_KcEERS0_RT_4
_ZN4kiss6LoggerlsIA135_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA14_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA156_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA15_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA166_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA16_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA18_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA197_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA231_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA23_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA256_cEERS0_RT_0
_ZN4kiss6LoggerlsIA25_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA26_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA27_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA2_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA33_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA34_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA35_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA39_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA3_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA40_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA41_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA42_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA46_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA47_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA49_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA50_KcEERS0_RT_4
_ZN4kiss6LoggerlsIA51_KcEERS0_RT_3
_ZN4kiss6LoggerlsIA53_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA54_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA55_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA58_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA59_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA5_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA64_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA67_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA69_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA6_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA70_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA71_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA72_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA73_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA74_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA75_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA7_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA81_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA82_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA83_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA8_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA93_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA9_KcEERS0_RT_0
_ZN4kiss6LoggerlsIKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIKbEERS0_RT_0
_ZN4kiss6LoggerlsIKiEERS0_RT_0
_ZN4kiss6LoggerlsIKmEERS0_RT_0
_ZN4kiss6LoggerlsIN7crpropa7Vector3IdEEEERS0_RT_0
_ZN4kiss6LoggerlsINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIbEERS0_RT_0
_ZN4kiss6LoggerlsIdEERS0_RT_0
_ZN4kiss6LoggerlsIiEERS0_RT_2
_ZN4kiss6LoggerlsImEERS0_RT_0
_ZN4kiss6LoggerlsIyEERS0_RT_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html b/doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html new file mode 100644 index 000000000..a7402eee3 --- /dev/null +++ b/doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html @@ -0,0 +1,131 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/include/kiss/logger.h + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/include/kiss - logger.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4944.4 %
Date:2024-04-08 14:58:22Functions:136619.7 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifndef KISS_LOG_H
+       2             : #define KISS_LOG_H
+       3             : 
+       4             : #include <iostream>
+       5             : 
+       6             : namespace kiss {
+       7             : 
+       8             : enum eLogLevel {
+       9             :         LOG_LEVEL_ERROR, LOG_LEVEL_WARNING, LOG_LEVEL_INFO, LOG_LEVEL_DEBUG
+      10             : };
+      11             : 
+      12             : class Logger {
+      13             :         static std::ostream *stream;
+      14             :         static eLogLevel level;
+      15             : public:
+      16             :         Logger(eLogLevel level);
+      17             :         ~Logger();
+      18             :         static std::ostream &getLogStream();
+      19             :         static void setLogStream(std::ostream *s);
+      20             :         static void setLogStream(std::ostream &s);
+      21             : 
+      22             :         static void setLogLevel(eLogLevel level);
+      23             :         static eLogLevel getLogLevel();
+      24             : 
+      25             :         static void loadEnvLogLevel();
+      26             : 
+      27             :         operator std::ostream &() {
+      28           0 :                 return getLogStream();
+      29             :         }
+      30             : 
+      31          26 :         template<typename T> inline Logger& operator<<(T& data) {
+      32          52 :                 #pragma omp critical (KISS_LOGGER)
+      33             :                 {
+      34          26 :                 getLogStream() << data;
+      35             :                 }
+      36          26 :                 return *this;
+      37             :         }
+      38             : 
+      39           0 :         inline Logger& operator<<(std::ostream& (*func)(std::ostream&)) {
+      40           0 :                 #pragma omp critical (KISS_LOGGER)
+      41             :                 {
+      42           0 :                 getLogStream() << func;
+      43             :                 }
+      44           0 :                 return *this;
+      45             :         }
+      46             : };
+      47             : 
+      48             : } // namespace kiss
+      49             : 
+      50             : #define KISS_LOG_ERROR if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_ERROR) {} else kiss::Logger(kiss::LOG_LEVEL_ERROR)
+      51             : #define KISS_LOG_WARNING if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_WARNING) {} else kiss::Logger(kiss::LOG_LEVEL_WARNING)
+      52             : #define KISS_LOG_INFO if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_INFO) {} else kiss::Logger(kiss::LOG_LEVEL_INFO)
+      53             : #define KISS_LOG_DEBUG if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_DEBUG) {} else kiss::Logger(kiss::LOG_LEVEL_DEBUG)
+      54             : 
+      55             : #endif /* KISSLOG_H */
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/index-sort-f.html b/doc/coverageReport/libs/kiss/src/index-sort-f.html new file mode 100644 index 000000000..ec409f400 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/index-sort-f.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/srcHitTotalCoverage
Test:coverage.info.cleanedLines:3412128.1 %
Date:2024-04-08 14:58:22Functions:92339.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
string.cpp +
14.8%14.8%
+
14.8 %4 / 2714.3 %1 / 7
path.cpp +
24.5%24.5%
+
24.5 %13 / 5337.5 %3 / 8
logger.cpp +
41.5%41.5%
+
41.5 %17 / 4162.5 %5 / 8
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/index-sort-l.html b/doc/coverageReport/libs/kiss/src/index-sort-l.html new file mode 100644 index 000000000..4cac3f96c --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/index-sort-l.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/srcHitTotalCoverage
Test:coverage.info.cleanedLines:3412128.1 %
Date:2024-04-08 14:58:22Functions:92339.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
string.cpp +
14.8%14.8%
+
14.8 %4 / 2714.3 %1 / 7
path.cpp +
24.5%24.5%
+
24.5 %13 / 5337.5 %3 / 8
logger.cpp +
41.5%41.5%
+
41.5 %17 / 4162.5 %5 / 8
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/index.html b/doc/coverageReport/libs/kiss/src/index.html new file mode 100644 index 000000000..d44e18167 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/index.html @@ -0,0 +1,113 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/srcHitTotalCoverage
Test:coverage.info.cleanedLines:3412128.1 %
Date:2024-04-08 14:58:22Functions:92339.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
logger.cpp +
41.5%41.5%
+
41.5 %17 / 4162.5 %5 / 8
path.cpp +
24.5%24.5%
+
24.5 %13 / 5337.5 %3 / 8
string.cpp +
14.8%14.8%
+
14.8 %4 / 2714.3 %1 / 7
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html b/doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html new file mode 100644 index 000000000..a72ea02f2 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/logger.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - logger.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:174141.5 %
Date:2024-04-08 14:58:22Functions:5862.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6Logger11setLogLevelENS_9eLogLevelE0
_ZN4kiss6Logger12setLogStreamEPSo0
_ZN4kiss6Logger12setLogStreamERSo0
_ZN4kiss6LoggerC2ENS_9eLogLevelE12
_ZN4kiss6LoggerD2Ev12
_ZN4kiss6Logger15loadEnvLogLevelEv19
_ZN4kiss6Logger12getLogStreamEv26
_ZN4kiss6Logger11getLogLevelEv290
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/logger.cpp.func.html b/doc/coverageReport/libs/kiss/src/logger.cpp.func.html new file mode 100644 index 000000000..c740d5ca4 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/logger.cpp.func.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/logger.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - logger.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:174141.5 %
Date:2024-04-08 14:58:22Functions:5862.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6Logger11getLogLevelEv290
_ZN4kiss6Logger11setLogLevelENS_9eLogLevelE0
_ZN4kiss6Logger12getLogStreamEv26
_ZN4kiss6Logger12setLogStreamEPSo0
_ZN4kiss6Logger12setLogStreamERSo0
_ZN4kiss6Logger15loadEnvLogLevelEv19
_ZN4kiss6LoggerC2ENS_9eLogLevelE12
_ZN4kiss6LoggerD2Ev12
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html b/doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html new file mode 100644 index 000000000..212278290 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html @@ -0,0 +1,161 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/logger.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - logger.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:174141.5 %
Date:2024-04-08 14:58:22Functions:5862.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "kiss/logger.h"
+       2             : 
+       3             : #include <stdlib.h>
+       4             : #include <iostream>
+       5             : 
+       6             : namespace kiss {
+       7             : 
+       8             : std::ostream *Logger::stream = &std::cerr;
+       9             : eLogLevel Logger::level = LOG_LEVEL_WARNING;
+      10             : const char* sLoggerLevel[] = { " ERROR ", "WARNING", " INFO  ", " DEBUG " };
+      11             : 
+      12             : class EnvLogger {
+      13             : public:
+      14             :         EnvLogger() {
+      15             :                 Logger::loadEnvLogLevel();
+      16             :         }
+      17             : };
+      18             : static EnvLogger _env_log_;
+      19             : 
+      20          12 : Logger::Logger(eLogLevel level) {
+      21             :         time_t rawtime;
+      22             :         struct tm * timeinfo;
+      23             :         char buffer[80];
+      24             : 
+      25          12 :         time(&rawtime);
+      26          12 :         timeinfo = localtime(&rawtime);
+      27             : 
+      28          12 :         strftime(buffer, 80, "%Y-%m-%d %H:%M:%S ", timeinfo);
+      29          12 :         *stream << buffer;
+      30          12 :         *stream << "[" << sLoggerLevel[level] << "] ";
+      31          12 : }
+      32             : 
+      33          12 : Logger::~Logger() {
+      34          12 :         *stream << std::endl;
+      35          12 : }
+      36             : 
+      37          26 : std::ostream &Logger::getLogStream() {
+      38          26 :         return (*stream);
+      39             : }
+      40             : 
+      41           0 : void Logger::setLogStream(std::ostream *s) {
+      42           0 :         stream = s;
+      43           0 : }
+      44             : 
+      45           0 : void Logger::setLogStream(std::ostream &s) {
+      46           0 :         stream = &s;
+      47           0 : }
+      48             : 
+      49           0 : void Logger::setLogLevel(eLogLevel l) {
+      50           0 :         level = l;
+      51           0 : }
+      52         290 : eLogLevel Logger::getLogLevel() {
+      53         290 :         return (level);
+      54             : }
+      55             : 
+      56             : 
+      57             : 
+      58             : 
+      59          19 : void Logger::loadEnvLogLevel() {
+      60          19 :         if (::getenv("KISS_LOG_LEVEL")) {
+      61             :                 
+      62           0 :                 int level = atoi(::getenv("KISS_LOG_LEVEL"));
+      63           0 :                 switch (level) {
+      64           0 :                 case LOG_LEVEL_ERROR:
+      65           0 :                         Logger::setLogLevel(LOG_LEVEL_ERROR);
+      66           0 :                         break;
+      67           0 :                 case LOG_LEVEL_WARNING:
+      68           0 :                         Logger::setLogLevel(LOG_LEVEL_WARNING);
+      69           0 :                         break;
+      70           0 :                 case LOG_LEVEL_INFO:
+      71           0 :                         Logger::setLogLevel(LOG_LEVEL_INFO);
+      72           0 :                         break;
+      73           0 :                 case LOG_LEVEL_DEBUG:
+      74           0 :                         Logger::setLogLevel(LOG_LEVEL_DEBUG);
+      75           0 :                         break;
+      76             :                 default:
+      77             :                         std::cerr << "kiss::Logger: unknown log level in KISS_LOG_LEVEL '"
+      78           0 :                                         << level << " values from 0-3 expected." << std::endl;
+      79             :                         break;
+      80             :                 }
+      81             :         }
+      82          19 : }
+      83             : 
+      84             : } // namespace kiss
+      85             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html b/doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html new file mode 100644 index 000000000..496484b29 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/path.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - path.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:135324.5 %
Date:2024-04-08 14:58:22Functions:3837.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_Z11append_fileRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_b0
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_S6_0
_Z14list_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS4_SaIS4_EE0
_Z16create_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
_Z26create_directory_recursiveRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
_Z15executable_pathB5cxx11v13
_Z12is_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE26
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_547
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/path.cpp.func.html b/doc/coverageReport/libs/kiss/src/path.cpp.func.html new file mode 100644 index 000000000..e354ac988 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/path.cpp.func.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/path.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - path.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:135324.5 %
Date:2024-04-08 14:58:22Functions:3837.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_Z11append_fileRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_b0
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_547
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_S6_0
_Z12is_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE26
_Z14list_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS4_SaIS4_EE0
_Z15executable_pathB5cxx11v13
_Z16create_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
_Z26create_directory_recursiveRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/path.cpp.gcov.html b/doc/coverageReport/libs/kiss/src/path.cpp.gcov.html new file mode 100644 index 000000000..7cc7b933a --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/path.cpp.gcov.html @@ -0,0 +1,245 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/path.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - path.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:135324.5 %
Date:2024-04-08 14:58:22Functions:3837.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "kiss/path.h"
+       2             : 
+       3             : #ifdef WIN32
+       4             : #  include "windows.h"
+       5             : #  ifndef S_ISREG
+       6             : #    define S_ISREG(x) (((x) & S_IFMT) == S_IFREG)
+       7             : #  endif
+       8             : #  ifndef S_ISDIR
+       9             : #    define S_ISDIR(x) (((x) & S_IFMT) == S_IFDIR)
+      10             : #  endif
+      11             : #  include "sys/stat.h"
+      12             : #else
+      13             : #include <sys/types.h>
+      14             : #include <fcntl.h>
+      15             : #include <unistd.h>
+      16             : #include <dirent.h>
+      17             : #include "sys/stat.h"
+      18             : #endif
+      19             : 
+      20             : #include <stdexcept>
+      21             : #include <cstdio>
+      22             : 
+      23           0 : bool create_directory(const std::string &path, size_t user_permission,
+      24             :                 size_t group_permission, size_t other_permission) {
+      25             : #ifdef WIN32
+      26             :         BOOL result = ::CreateDirectoryA(path.c_str(), 0);
+      27             :         return result == TRUE;
+      28             : #else
+      29             :         mode_t m = 0;
+      30           0 :         m |= (user_permission << 6);
+      31           0 :         m |= (group_permission << 3);
+      32           0 :         m |= (other_permission << 0);
+      33           0 :         int result = mkdir(path.c_str(), m);
+      34           0 :         return (result == 0);
+      35             : #endif
+      36             : }
+      37             : 
+      38          26 : bool is_directory(const std::string &path) {
+      39             : #ifdef WIN32
+      40             :         struct _stat buf;
+      41             :         int result = _stat(path.c_str(), &buf);
+      42             :         if (result == 0 && S_ISDIR(buf.st_mode))
+      43             :                 return true;
+      44             :         else
+      45             :                 return false;
+      46             : #else
+      47             :         struct stat buf;
+      48          26 :         int result = stat(path.c_str(), &buf);
+      49          26 :         if (result == 0 && S_ISDIR(buf.st_mode))
+      50             :         return true;
+      51             :         else
+      52          26 :         return false;
+      53             : #endif
+      54             : }
+      55             : 
+      56           0 : bool list_directory(const std::string &directory,
+      57             :                 std::vector<std::string> &elements) {
+      58             : #ifdef WIN32
+      59             :         WIN32_FIND_DATA findData;
+      60             :         HANDLE hFind = FindFirstFileA((directory + "\\*.*").c_str(), &findData);
+      61             :         if (hFind == INVALID_HANDLE_VALUE)
+      62             :                 throw std::runtime_error("Failed to get directory list");
+      63             :         for (;;) {
+      64             :                 if (findData.cFileName[0] != '.') {
+      65             :                         elements.push_back(findData.cFileName);
+      66             :                 }
+      67             :                 if (FindNextFileA(hFind, &findData) == 0)
+      68             :                         break;
+      69             :         }
+      70             :         FindClose(hFind);
+      71             : #else
+      72           0 :         DIR* dir = opendir(directory.c_str());
+      73           0 :         if (dir == NULL)
+      74             :         return false;
+      75             :         dirent* entry;
+      76           0 :         while ((entry = readdir(dir)) != NULL) {
+      77           0 :                 if (entry->d_name[0] != '.') {
+      78           0 :                         elements.push_back(entry->d_name);
+      79             :                 }
+      80             :         }
+      81           0 :         closedir(dir);
+      82             : #endif
+      83           0 :         return true;
+      84             : }
+      85             : 
+      86           0 : bool create_directory_recursive(const std::string &dir, size_t user_permission,
+      87             :                 size_t group_permission, size_t other_permission) {
+      88             :         // split path
+      89           0 :         const char seperators[] = "\\/";
+      90             :         std::vector<std::string> elements;
+      91             :         std::string::size_type a, b;
+      92             :         a = dir.find_first_not_of(seperators), b = dir.find_first_of(seperators, a);
+      93           0 :         while (a != std::string::npos) {
+      94           0 :                 elements.push_back(dir.substr(a, b - a));
+      95             :                 a = dir.find_first_not_of(seperators, b), b = dir.find_first_of(
+      96             :                                 seperators, a);
+      97             :         }
+      98             : 
+      99             :         // create all non existing parts
+     100             :         std::string path;
+     101           0 :         for (size_t i = 0; i < elements.size(); i++) {
+     102             :                 path += elements[i];
+     103             :                 path += path_seperator;
+     104           0 :                 if (is_directory(path) == false)
+     105           0 :                         create_directory(path);
+     106             :         }
+     107             : 
+     108           0 :         return is_directory(dir);
+     109           0 : }
+     110             : 
+     111         547 : std::string concat_path(const std::string &a, const std::string &b) {
+     112         547 :         char last = *a.rbegin();
+     113         547 :         if (last == '\\' || last == '/')
+     114           0 :                 return a + b;
+     115             :         else
+     116        1094 :                 return a + path_seperator + b;
+     117             : 
+     118             : }
+     119             : 
+     120           0 : std::string concat_path(const std::string &a, const std::string &b,
+     121             :                 const std::string &c) {
+     122             :         std::string p = a;
+     123           0 :         if (*p.rbegin() != '\\' && *p.rbegin() != '/')
+     124             :                 p += path_seperator;
+     125             :         p += b;
+     126           0 :         if (*p.rbegin() != '\\' && *p.rbegin() != '/')
+     127             :                 p += path_seperator;
+     128             :         p += c;
+     129           0 :         return p;
+     130             : }
+     131             : 
+     132           0 : void append_file(const std::string &target, const std::string &source,
+     133             :                 bool binary) {
+     134           0 :         FILE *t = fopen(target.c_str(), binary ? "wb+" : "w+");
+     135           0 :         if (t == NULL)
+     136           0 :                 return;
+     137             : 
+     138           0 :         FILE *s = fopen(source.c_str(), binary ? "rb" : "r");
+     139           0 :         if (s == NULL) {
+     140           0 :                 fclose(t);
+     141           0 :                 return;
+     142             :         }
+     143             : 
+     144             :         size_t size = 0;
+     145             :         char buffer[1 << 20];
+     146           0 :         while ((size = fread(buffer, 1, sizeof(buffer), s)) > 0) {
+     147           0 :                 fwrite(buffer, 1, size, t);
+     148             :         }
+     149             : 
+     150           0 :         fclose(t);
+     151           0 :         fclose(s);
+     152             : }
+     153             : 
+     154          13 : std::string executable_path() {
+     155             :         char buf[1024];
+     156             : 
+     157             : //#if linux
+     158          13 :         size_t len = readlink("/proc/self/exe", buf, sizeof(buf)-1);
+     159             : //#else
+     160             : //      size_t len = ::GetModuleFileName(NULL, buf, sizeof(buf)-1 );
+     161             : //#endif
+     162         192 :         for (size_t i = 1; i < len; i++) {
+     163         189 :                 if (buf[len - 1] == path_seperator)
+     164             :                         break;
+     165             :                 else
+     166             :                         len --;
+     167             :         }
+     168          13 :         return std::string(buf, len);
+     169             : }
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html b/doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html new file mode 100644 index 000000000..43fcf0d21 --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/string.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - string.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:42714.8 %
Date:2024-04-08 14:58:22Functions:1714.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss10trim_rightERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss11starts_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss4trimERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss7explodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS5_SaIS5_EEbS7_0
_ZN4kiss7implodeERKSt6vectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESaIS6_EERKS6_0
_ZN4kiss9trim_leftERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss9ends_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/string.cpp.func.html b/doc/coverageReport/libs/kiss/src/string.cpp.func.html new file mode 100644 index 000000000..a35b5f6ae --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/string.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/string.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - string.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:42714.8 %
Date:2024-04-08 14:58:22Functions:1714.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss10trim_rightERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss11starts_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss4trimERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss7explodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS5_SaIS5_EEbS7_0
_ZN4kiss7implodeERKSt6vectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESaIS6_EERKS6_0
_ZN4kiss9ends_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_3
_ZN4kiss9trim_leftERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/libs/kiss/src/string.cpp.gcov.html b/doc/coverageReport/libs/kiss/src/string.cpp.gcov.html new file mode 100644 index 000000000..af1671ddc --- /dev/null +++ b/doc/coverageReport/libs/kiss/src/string.cpp.gcov.html @@ -0,0 +1,165 @@ + + + + + + + LCOV - coverage.info.cleaned - libs/kiss/src/string.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - libs/kiss/src - string.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:42714.8 %
Date:2024-04-08 14:58:22Functions:1714.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "kiss/string.h"
+       2             : 
+       3             : #include <iostream>
+       4             : #include <string>
+       5             : #include <vector>
+       6             : 
+       7             : namespace kiss {
+       8             : 
+       9           0 : std::string trim_right(const std::string &s, const std::string &t) {
+      10             :         std::string::size_type i(s.find_last_not_of(t));
+      11             : 
+      12           0 :         if (i == std::string::npos)
+      13           0 :                 return "";
+      14             :         else
+      15           0 :                 return std::string(s, 0, i);
+      16             : }
+      17             : 
+      18           0 : std::string trim_left(const std::string &s, const std::string &t) {
+      19           0 :         return std::string(s, s.find_first_not_of(t));
+      20             : }
+      21             : 
+      22           0 : std::string trim(const std::string &s, const std::string &t) {
+      23             :         std::string::size_type a = s.find_first_not_of(t);
+      24             :         std::string::size_type b = s.find_last_not_of(t);
+      25             : 
+      26           0 :         if (a == std::string::npos || b == std::string::npos)
+      27           0 :                 return "";
+      28             : 
+      29           0 :         return std::string(s, a, b - a + 1);
+      30             : }
+      31             : 
+      32           0 : void explode(const std::string &s, std::vector<std::string> &v,
+      33             :                 const bool trim_spaces, const std::string &t) {
+      34             :         std::string::size_type a, b;
+      35             : 
+      36             :         a = s.find_first_not_of(t), b = s.find_first_of(t, a);
+      37             : 
+      38           0 :         while (a != std::string::npos) {
+      39           0 :                 if (trim_spaces)
+      40           0 :                         v.push_back(trim(s.substr(a, b - a)));
+      41             :                 else
+      42           0 :                         v.push_back(s.substr(a, b - a));
+      43             : 
+      44             :                 a = s.find_first_not_of(t, b), b = s.find_first_of(t, a);
+      45             :         }
+      46           0 : }
+      47             : 
+      48           0 : std::string implode(const std::vector<std::string> &v, const std::string &t) {
+      49             :         unsigned int i;
+      50             :         std::string s;
+      51             : 
+      52           0 :         for (i = 0; i < (v.size() - 1); i++) {
+      53             :                 s.append(v[i]);
+      54             :                 s.append(t);
+      55             :         }
+      56             : 
+      57           0 :         return s + v[i];
+      58             : }
+      59             : 
+      60           3 : bool ends_with(const std::string &s, const std::string &w) {
+      61           3 :         if (s.size() < w.size())
+      62             :                 return false;
+      63             :         std::string::const_reverse_iterator si = s.rbegin();
+      64             :         std::string::const_reverse_iterator wi = w.rbegin();
+      65           3 :         while (wi != w.rend()) {
+      66           3 :                 if (*wi != *si)
+      67             :                         return false;
+      68             :                 wi++;
+      69             :                 si++;
+      70             :         }
+      71             : 
+      72             :         return true;
+      73             : }
+      74             : 
+      75           0 : bool starts_with(const std::string &s, const std::string &w) {
+      76           0 :         if (s.size() < w.size())
+      77             :                 return false;
+      78             :         std::string::const_iterator si = s.begin();
+      79             :         std::string::const_iterator wi = w.begin();
+      80           0 :         while (wi != w.end()) {
+      81           0 :                 if (*wi != *si)
+      82             :                         return false;
+      83             :                 wi++;
+      84             :                 si++;
+      85             :         }
+      86             :         return true;
+      87             : }
+      88             : 
+      89             : } // namespace kiss
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/ruby.png b/doc/coverageReport/ruby.png new file mode 100644 index 0000000000000000000000000000000000000000..991b6d4ec9e78be165e3ef757eed1aada287364d GIT binary patch literal 141 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)ga>?NMQuI!iC1^FceV#7`HfI^%F z9+AZi4BSE>%y{W;-5;PJOS+@4BLl<6e(pbstUx|nfKQ0)e^Y%R^MdiLxj>4`)5S5Q b;#P73kj=!v_*DHKNFRfztDnm{r-UW|iOwIS literal 0 HcmV?d00001 diff --git a/doc/coverageReport/snow.png b/doc/coverageReport/snow.png new file mode 100644 index 0000000000000000000000000000000000000000..2cdae107fceec6e7f02ac7acb4a34a82a540caa5 GIT binary patch literal 141 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)ga>?NMQuI!iC1^MM!lvI6;R0X`wF|Ns97GD8ntt^-nBo-U3d c6}OTTfNUlP#;5A{K>8RwUHx3vIVCg!071?oo&W#< literal 0 HcmV?d00001 diff --git a/doc/coverageReport/src/Candidate.cpp.func-sort-c.html b/doc/coverageReport/src/Candidate.cpp.func-sort-c.html new file mode 100644 index 000000000..b34d8b8c1 --- /dev/null +++ b/doc/coverageReport/src/Candidate.cpp.func-sort-c.html @@ -0,0 +1,212 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Candidate.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Candidate.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12914787.8 %
Date:2024-04-08 14:58:22Functions:333594.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Candidate16clearSecondariesEv0
_ZNK7crpropa9Candidate14getDescriptionB5cxx11Ev0
_ZN7crpropa9Candidate19setNextSerialNumberEm1
_ZN7crpropa9Candidate7restartEv1
_ZN7crpropa9Candidate12addSecondaryEiddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa9Candidate12addSecondaryEPS0_4
_ZN7crpropa9Candidate12updateWeightEd5
_ZN7crpropa9Candidate14removePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE5
_ZN7crpropa9Candidate19getNextSerialNumberEv6
_ZN7crpropa9Candidate15setSerialNumberEm11
_ZNK7crpropa9Candidate11getPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE11
_ZN7crpropa9CandidateC2ERKNS_13ParticleStateE20
_ZNK7crpropa9Candidate11hasPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE30
_ZNK7crpropa9Candidate5cloneEb30
_ZNK7crpropa9Candidate22getCreatedSerialNumberEv48
_ZNK7crpropa9Candidate21getSourceSerialNumberEv49
_ZNK7crpropa9Candidate12getTagOriginB5cxx11Ev61
_ZNK7crpropa9Candidate15getSerialNumberEv84
_ZNK7crpropa9Candidate9getWeightEv1064
_ZN7crpropa9Candidate11setPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantE1143
_ZN7crpropa9Candidate9setActiveEb1742
_ZNK7crpropa9Candidate8isActiveEv21336
_ZNK7crpropa9Candidate14getCurrentStepEv63001
_ZNK7crpropa9Candidate11getNextStepEv499385
_ZN7crpropa9Candidate11setNextStepEd499400
_ZN7crpropa9Candidate14setCurrentStepEd501076
_ZNK7crpropa9Candidate11getRedshiftEv529541
_ZN7crpropa9Candidate13limitNextStepEd530052
_ZNK7crpropa9Candidate19getTrajectoryLengthEv1011718
_ZN7crpropa9Candidate12addSecondaryEidNS_7Vector3IdEEdNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324908
_ZN7crpropa9Candidate12setTagOriginENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324912
_ZN7crpropa9Candidate19setTrajectoryLengthEd3324939
_ZN7crpropa9Candidate9setWeightEd3325923
_ZN7crpropa9Candidate11setRedshiftEd3332752
_ZN7crpropa9CandidateC2EidNS_7Vector3IdEES2_ddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3368851
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Candidate.cpp.func.html b/doc/coverageReport/src/Candidate.cpp.func.html new file mode 100644 index 000000000..4a0c5e726 --- /dev/null +++ b/doc/coverageReport/src/Candidate.cpp.func.html @@ -0,0 +1,212 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Candidate.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Candidate.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12914787.8 %
Date:2024-04-08 14:58:22Functions:333594.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Candidate11setNextStepEd499400
_ZN7crpropa9Candidate11setPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantE1143
_ZN7crpropa9Candidate11setRedshiftEd3332752
_ZN7crpropa9Candidate12addSecondaryEPS0_4
_ZN7crpropa9Candidate12addSecondaryEidNS_7Vector3IdEEdNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324908
_ZN7crpropa9Candidate12addSecondaryEiddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa9Candidate12setTagOriginENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324912
_ZN7crpropa9Candidate12updateWeightEd5
_ZN7crpropa9Candidate13limitNextStepEd530052
_ZN7crpropa9Candidate14removePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE5
_ZN7crpropa9Candidate14setCurrentStepEd501076
_ZN7crpropa9Candidate15setSerialNumberEm11
_ZN7crpropa9Candidate16clearSecondariesEv0
_ZN7crpropa9Candidate19getNextSerialNumberEv6
_ZN7crpropa9Candidate19setNextSerialNumberEm1
_ZN7crpropa9Candidate19setTrajectoryLengthEd3324939
_ZN7crpropa9Candidate7restartEv1
_ZN7crpropa9Candidate9setActiveEb1742
_ZN7crpropa9Candidate9setWeightEd3325923
_ZN7crpropa9CandidateC2ERKNS_13ParticleStateE20
_ZN7crpropa9CandidateC2EidNS_7Vector3IdEES2_ddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3368851
_ZNK7crpropa9Candidate11getNextStepEv499385
_ZNK7crpropa9Candidate11getPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE11
_ZNK7crpropa9Candidate11getRedshiftEv529541
_ZNK7crpropa9Candidate11hasPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE30
_ZNK7crpropa9Candidate12getTagOriginB5cxx11Ev61
_ZNK7crpropa9Candidate14getCurrentStepEv63001
_ZNK7crpropa9Candidate14getDescriptionB5cxx11Ev0
_ZNK7crpropa9Candidate15getSerialNumberEv84
_ZNK7crpropa9Candidate19getTrajectoryLengthEv1011718
_ZNK7crpropa9Candidate21getSourceSerialNumberEv49
_ZNK7crpropa9Candidate22getCreatedSerialNumberEv48
_ZNK7crpropa9Candidate5cloneEb30
_ZNK7crpropa9Candidate8isActiveEv21336
_ZNK7crpropa9Candidate9getWeightEv1064
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Candidate.cpp.gcov.html b/doc/coverageReport/src/Candidate.cpp.gcov.html new file mode 100644 index 000000000..07a4b2a2a --- /dev/null +++ b/doc/coverageReport/src/Candidate.cpp.gcov.html @@ -0,0 +1,331 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Candidate.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Candidate.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12914787.8 %
Date:2024-04-08 14:58:22Functions:333594.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Candidate.h"
+       2             : #include "crpropa/ParticleID.h"
+       3             : #include "crpropa/Units.h"
+       4             : 
+       5             : #include <stdexcept>
+       6             : 
+       7             : namespace crpropa {
+       8             : 
+       9     3368851 : Candidate::Candidate(int id, double E, Vector3d pos, Vector3d dir, double z, double weight, std::string tagOrigin) :
+      10     3368851 :   redshift(z), trajectoryLength(0), weight(weight), currentStep(0), nextStep(0), active(true), parent(0), tagOrigin(tagOrigin) {
+      11     3368851 :         ParticleState state(id, E, pos, dir);
+      12             :         source = state;
+      13             :         created = state;
+      14             :         previous = state;
+      15             :         current = state;
+      16             : 
+      17             : #if defined(OPENMP_3_1)
+      18             :                 #pragma omp atomic capture
+      19             :                 {serialNumber = nextSerialNumber++;}
+      20             : #elif defined(__GNUC__)
+      21     3368851 :                 {serialNumber = __sync_add_and_fetch(&nextSerialNumber, 1);}
+      22             : #else
+      23             :                 #pragma omp critical
+      24             :                 {serialNumber = nextSerialNumber++;}
+      25             : #endif
+      26             : 
+      27     3368851 : }
+      28             : 
+      29          20 : Candidate::Candidate(const ParticleState &state) :
+      30          20 :                 source(state), created(state), current(state), previous(state), redshift(0), trajectoryLength(0), currentStep(0), nextStep(0), active(true), parent(0), tagOrigin ("PRIM") {
+      31             : 
+      32             : #if defined(OPENMP_3_1)
+      33             :                 #pragma omp atomic capture
+      34             :                 {serialNumber = nextSerialNumber++;}
+      35             : #elif defined(__GNUC__)
+      36          20 :                 {serialNumber = __sync_add_and_fetch(&nextSerialNumber, 1);}
+      37             : #else
+      38             :                 #pragma omp critical
+      39             :                 {serialNumber = nextSerialNumber++;}
+      40             : #endif
+      41             : 
+      42          20 : }
+      43             : 
+      44       21336 : bool Candidate::isActive() const {
+      45       21336 :         return active;
+      46             : }
+      47             : 
+      48        1742 : void Candidate::setActive(bool b) {
+      49        1742 :         active = b;
+      50        1742 : }
+      51             : 
+      52      529541 : double Candidate::getRedshift() const {
+      53      529541 :         return redshift;
+      54             : }
+      55             : 
+      56     1011718 : double Candidate::getTrajectoryLength() const {
+      57     1011718 :         return trajectoryLength;
+      58             : }
+      59             : 
+      60        1064 : double Candidate::getWeight() const {
+      61        1064 :         return weight;
+      62             : }
+      63             : 
+      64       63001 : double Candidate::getCurrentStep() const {
+      65       63001 :         return currentStep;
+      66             : }
+      67             : 
+      68      499385 : double Candidate::getNextStep() const {
+      69      499385 :         return nextStep;
+      70             : }
+      71             : 
+      72     3332752 : void Candidate::setRedshift(double z) {
+      73     3332752 :         redshift = z;
+      74     3332752 : }
+      75             : 
+      76     3324939 : void Candidate::setTrajectoryLength(double a) {
+      77     3324939 :         trajectoryLength = a;
+      78     3324939 : }
+      79             : 
+      80     3325923 : void Candidate::setWeight(double w) {
+      81     3325923 :         weight = w;
+      82     3325923 : }
+      83             : 
+      84           5 : void Candidate::updateWeight(double w) {
+      85           5 :   weight *= w;
+      86           5 : }
+      87             : 
+      88      501076 : void Candidate::setCurrentStep(double lstep) {
+      89      501076 :         currentStep = lstep;
+      90      501076 :         trajectoryLength += lstep;
+      91      501076 : }
+      92             : 
+      93      499400 : void Candidate::setNextStep(double step) {
+      94      499400 :         nextStep = step;
+      95      499400 : }
+      96             : 
+      97      530052 : void Candidate::limitNextStep(double step) {
+      98      530052 :         nextStep = std::min(nextStep, step);
+      99      530052 : }
+     100             : 
+     101        1143 : void Candidate::setProperty(const std::string &name, const Variant &value) {
+     102        1143 :         properties[name] = value;
+     103        1143 : }
+     104             : 
+     105     3324912 : void Candidate::setTagOrigin (std::string tagOrigin) {
+     106     3324912 :         this->tagOrigin = tagOrigin;
+     107     3324912 : }
+     108             : 
+     109          61 : std::string Candidate::getTagOrigin () const {
+     110          61 :         return tagOrigin;
+     111             : }
+     112             : 
+     113          11 : const Variant &Candidate::getProperty(const std::string &name) const {
+     114          11 :         PropertyMap::const_iterator i = properties.find(name);
+     115          11 :         if (i == properties.end())
+     116           0 :                 throw std::runtime_error("Unknown candidate property: " + name);
+     117          11 :         return i->second;
+     118             : }
+     119             : 
+     120           5 : bool Candidate::removeProperty(const std::string& name) {
+     121           5 :         PropertyMap::iterator i = properties.find(name);
+     122           5 :         if (i == properties.end())
+     123             :                 return false;
+     124             :         properties.erase(i);
+     125             :         return true;
+     126             : }
+     127             : 
+     128          30 : bool Candidate::hasProperty(const std::string &name) const {
+     129          30 :         PropertyMap::const_iterator i = properties.find(name);
+     130          30 :         if (i == properties.end())
+     131          10 :                 return false;
+     132             :         return true;
+     133             : }
+     134             : 
+     135           4 : void Candidate::addSecondary(Candidate *c) {
+     136           4 :         secondaries.push_back(c);
+     137           4 : }
+     138             : 
+     139           2 : void Candidate::addSecondary(int id, double energy, double w, std::string tagOrigin) {
+     140           4 :         ref_ptr<Candidate> secondary = new Candidate;
+     141           2 :         secondary->setRedshift(redshift);
+     142           2 :         secondary->setTrajectoryLength(trajectoryLength);
+     143           2 :         secondary->setWeight(weight * w);
+     144           4 :         secondary->setTagOrigin(tagOrigin);
+     145           2 :         for (PropertyMap::const_iterator it = properties.begin(); it != properties.end(); ++it) {
+     146           0 :                 secondary->setProperty(it->first, it->second);         
+     147             :         }
+     148             :         secondary->source = source;
+     149             :         secondary->previous = previous;
+     150             :         secondary->created = previous;
+     151           2 :         secondary->current = current;
+     152           2 :         secondary->current.setId(id);
+     153           2 :         secondary->current.setEnergy(energy);
+     154           2 :         secondary->parent = this;
+     155           2 :         secondaries.push_back(secondary);
+     156           2 : }
+     157             : 
+     158     3324908 : void Candidate::addSecondary(int id, double energy, Vector3d position, double w, std::string tagOrigin) {
+     159     6649816 :         ref_ptr<Candidate> secondary = new Candidate;
+     160     3324908 :         secondary->setRedshift(redshift);
+     161     3324908 :         secondary->setTrajectoryLength(trajectoryLength - (current.getPosition() - position).getR());
+     162     3324908 :         secondary->setWeight(weight * w);
+     163     6649816 :         secondary->setTagOrigin(tagOrigin);
+     164     3324908 :         for (PropertyMap::const_iterator it = properties.begin(); it != properties.end(); ++it) {
+     165           0 :                 secondary->setProperty(it->first, it->second);         
+     166             :         }
+     167             :         secondary->source = source;
+     168             :         secondary->previous = previous;
+     169     3324908 :         secondary->created = previous;
+     170     3324908 :         secondary->current = current;
+     171     3324908 :         secondary->current.setId(id);
+     172     3324908 :         secondary->current.setEnergy(energy);
+     173     3324908 :         secondary->current.setPosition(position);
+     174     3324908 :         secondary->created.setPosition(position);
+     175     3324908 :         secondary->parent = this;
+     176     3324908 :         secondaries.push_back(secondary);
+     177     3324908 : }
+     178             : 
+     179           0 : void Candidate::clearSecondaries() {
+     180           0 :         secondaries.clear();
+     181           0 : }
+     182             : 
+     183           0 : std::string Candidate::getDescription() const {
+     184           0 :         std::stringstream ss;
+     185           0 :         ss << "CosmicRay at z = " << getRedshift() << "\n";
+     186           0 :         ss << "  source:  " << source.getDescription() << "\n";
+     187           0 :         ss << "  current: " << current.getDescription();
+     188           0 :         return ss.str();
+     189           0 : }
+     190             : 
+     191          30 : ref_ptr<Candidate> Candidate::clone(bool recursive) const {
+     192          60 :         ref_ptr<Candidate> cloned = new Candidate;
+     193             :         cloned->source = source;
+     194             :         cloned->created = created;
+     195             :         cloned->current = current;
+     196             :         cloned->previous = previous;
+     197             : 
+     198          30 :         cloned->properties = properties;
+     199          30 :         cloned->active = active;
+     200          30 :         cloned->redshift = redshift;
+     201          30 :         cloned->weight = weight;
+     202          30 :         cloned->trajectoryLength = trajectoryLength;
+     203          30 :         cloned->currentStep = currentStep;
+     204          30 :         cloned->nextStep = nextStep;
+     205          30 :         if (recursive) {
+     206           0 :                 cloned->secondaries.reserve(secondaries.size());
+     207           0 :                 for (size_t i = 0; i < secondaries.size(); i++) {
+     208           0 :                         ref_ptr<Candidate> s = secondaries[i]->clone(recursive);
+     209           0 :                         s->parent = cloned;
+     210           0 :                         cloned->secondaries.push_back(s);
+     211             :                 }
+     212             :         }
+     213          30 :         return cloned;
+     214             : }
+     215             : 
+     216          84 : uint64_t Candidate::getSerialNumber() const {
+     217          84 :         return serialNumber;
+     218             : }
+     219             : 
+     220          11 : void Candidate::setSerialNumber(const uint64_t snr) {
+     221          11 :         serialNumber = snr;
+     222          11 : }
+     223             : 
+     224          49 : uint64_t Candidate::getSourceSerialNumber() const {
+     225          84 :         if (parent)
+     226             :                 return parent->getSourceSerialNumber();
+     227             :         else
+     228          49 :                 return serialNumber;
+     229             : }
+     230             : 
+     231          48 : uint64_t Candidate::getCreatedSerialNumber() const {
+     232          48 :         if (parent)
+     233          35 :                 return parent->getSerialNumber();
+     234             :         else
+     235          13 :                 return serialNumber;
+     236             : }
+     237             : 
+     238           1 : void Candidate::setNextSerialNumber(uint64_t snr) {
+     239           1 :         nextSerialNumber = snr;
+     240           1 : }
+     241             : 
+     242           6 : uint64_t Candidate::getNextSerialNumber() {
+     243           6 :         return nextSerialNumber;
+     244             : }
+     245             : 
+     246             : uint64_t Candidate::nextSerialNumber = 0;
+     247             : 
+     248           1 : void Candidate::restart() {
+     249           1 :         setActive(true);
+     250           1 :         setTrajectoryLength(0);
+     251             :         previous = source;
+     252             :         current = source;
+     253           1 : }
+     254             : 
+     255             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Clock.cpp.func-sort-c.html b/doc/coverageReport/src/Clock.cpp.func-sort-c.html new file mode 100644 index 000000000..3a192f2e6 --- /dev/null +++ b/doc/coverageReport/src/Clock.cpp.func-sort-c.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Clock.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Clock.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:080.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa5Clock11getInstanceEv0
_ZN7crpropa5Clock14getMillisecondEv0
_ZN7crpropa5Clock4Impl7getTimeEv0
_ZN7crpropa5Clock5resetEv0
_ZN7crpropa5Clock9getSecondEv0
_ZN7crpropa5ClockC2Ev0
_ZN7crpropa5ClockD0Ev0
_ZN7crpropa5ClockD2Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Clock.cpp.func.html b/doc/coverageReport/src/Clock.cpp.func.html new file mode 100644 index 000000000..5e2c004bd --- /dev/null +++ b/doc/coverageReport/src/Clock.cpp.func.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Clock.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Clock.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:080.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa5Clock11getInstanceEv0
_ZN7crpropa5Clock14getMillisecondEv0
_ZN7crpropa5Clock4Impl7getTimeEv0
_ZN7crpropa5Clock5resetEv0
_ZN7crpropa5Clock9getSecondEv0
_ZN7crpropa5ClockC2Ev0
_ZN7crpropa5ClockD0Ev0
_ZN7crpropa5ClockD2Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Clock.cpp.gcov.html b/doc/coverageReport/src/Clock.cpp.gcov.html new file mode 100644 index 000000000..1175dfb35 --- /dev/null +++ b/doc/coverageReport/src/Clock.cpp.gcov.html @@ -0,0 +1,231 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Clock.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Clock.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:080.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Clock.h"
+       2             : 
+       3             : #if defined(WIN32) || defined(_WIN32)
+       4             : 
+       5             : #define USE_WINDOWS_TIMERS
+       6             : #define WIN32_LEAN_AND_MEAN
+       7             : #define NOWINRES
+       8             : #define NOMCX
+       9             : #define NOIME
+      10             : #ifdef _XBOX
+      11             : #include <Xtl.h>
+      12             : #else
+      13             : #include <windows.h>
+      14             : #endif
+      15             : #include <ctime>
+      16             : 
+      17             : #else
+      18             : #include <sys/time.h>
+      19             : #endif
+      20             : 
+      21             : #include <algorithm>
+      22             : #ifdef _OPENMP
+      23             : #include <omp.h>
+      24             : #include <stdexcept>
+      25             : #endif
+      26             : 
+      27             : namespace crpropa {
+      28             : 
+      29             : #ifdef WIN32
+      30             : class Clock::Impl {
+      31             :         LARGE_INTEGER clockFrequency;
+      32             :         DWORD startTick;
+      33             :         LONGLONG prevElapsedTime;
+      34             :         LARGE_INTEGER startTime;
+      35             : public:
+      36             :         Impl() {
+      37             :                 QueryPerformanceFrequency(&clockFrequency);
+      38             :                 reset();
+      39             :         }
+      40             : 
+      41             :         void reset() {
+      42             :                 QueryPerformanceCounter(&startTime);
+      43             :                 startTick = GetTickCount();
+      44             :                 prevElapsedTime = 0;
+      45             :         }
+      46             : 
+      47             :         /// Returns the time in ms since the last call to reset or since
+      48             :         /// the btClock was created.
+      49             :         double getSecond() {
+      50             :                 LARGE_INTEGER currentTime;
+      51             :                 QueryPerformanceCounter(&currentTime);
+      52             :                 LONGLONG elapsedTime = currentTime.QuadPart - startTime.QuadPart;
+      53             : 
+      54             :                 // Compute the number of millisecond ticks elapsed.
+      55             :                 unsigned long msecTicks = (unsigned long) (1000 * elapsedTime
+      56             :                                 / clockFrequency.QuadPart);
+      57             : 
+      58             :                 // Check for unexpected leaps in the Win32 performance counter.
+      59             :                 // (This is caused by unexpected data across the PCI to ISA
+      60             :                 // bridge, aka south bridge.  See Microsoft KB274323.)
+      61             :                 unsigned long elapsedTicks = GetTickCount() - startTick;
+      62             :                 signed long msecOff = (signed long) (msecTicks - elapsedTicks);
+      63             :                 if (msecOff < -100 || msecOff > 100) {
+      64             :                         // Adjust the starting time forwards.
+      65             :                         LONGLONG msecAdjustment = std::min(
+      66             :                                         msecOff * clockFrequency.QuadPart / 1000,
+      67             :                                         elapsedTime - prevElapsedTime);
+      68             :                         startTime.QuadPart += msecAdjustment;
+      69             :                         elapsedTime -= msecAdjustment;
+      70             :                 }
+      71             : 
+      72             :                 // Store the current elapsed time for adjustments next time.
+      73             :                 prevElapsedTime = elapsedTime;
+      74             : 
+      75             :                 // Convert to microseconds.
+      76             :                 unsigned long usecTicks = (unsigned long) (1000000 * elapsedTime
+      77             :                                 / clockFrequency.QuadPart);
+      78             : 
+      79             :                 return double(usecTicks) / 1000000;
+      80             :         }
+      81             : };
+      82             : #else
+      83             : 
+      84             : class Clock::Impl {
+      85             :         struct timeval startTime;
+      86             : public:
+      87           0 :         Impl() {
+      88             :                 reset();
+      89             :         }
+      90             : 
+      91             :         void reset() {
+      92           0 :                 gettimeofday(&startTime, 0);
+      93             :         }
+      94             : 
+      95             :         /// Returns the time in since the last call to reset or since
+      96             :         /// the btClock was created.
+      97           0 :         double getTime() {
+      98             :                 struct timeval currentTime;
+      99           0 :                 gettimeofday(&currentTime, 0);
+     100           0 :                 double t = double(currentTime.tv_sec - startTime.tv_sec);
+     101           0 :                 t += double(currentTime.tv_usec - startTime.tv_usec) / 1000000.;
+     102           0 :                 return t;
+     103             :         }
+     104             : };
+     105             : #endif
+     106             : 
+     107           0 : Clock::Clock() {
+     108           0 :         impl = new Impl;
+     109           0 : }
+     110             : 
+     111           0 : Clock::~Clock() {
+     112           0 :         delete impl;
+     113           0 : }
+     114             : 
+     115           0 : void Clock::reset() {
+     116           0 :         impl->reset();
+     117           0 : }
+     118             : 
+     119           0 : double Clock::getSecond() {
+     120           0 :         return impl->getTime();
+     121             : }
+     122             : 
+     123           0 : double Clock::getMillisecond() {
+     124           0 :         return impl->getTime() * 1000;
+     125             : }
+     126             : 
+     127             : #ifdef _OPENMP
+     128             : 
+     129             : // see http://stackoverflow.com/questions/8051108/using-the-openmp-threadprivate-directive-on-static-instances-of-c-stl-types
+     130             : const static int MAX_THREAD = 256;
+     131             : 
+     132           0 : struct CLOCK_TLS_ITEM {
+     133             :         Clock r;
+     134             :         char padding[(sizeof(Clock) / 64 + 1) * 64 - sizeof(Clock)];
+     135             : };
+     136             : 
+     137           0 : Clock &Clock::getInstance() {
+     138             : #ifdef _MSC_VER
+     139             :         __declspec(align(64)) static CLOCK_TLS_ITEM tls[MAX_THREAD];
+     140             : #else
+     141           0 :         __attribute__ ((aligned(64))) static CLOCK_TLS_ITEM tls[MAX_THREAD];
+     142             : #endif
+     143           0 :         int i = omp_get_thread_num();
+     144           0 :         if (i >= MAX_THREAD)
+     145           0 :         throw std::runtime_error("crpropa::Clock: more than MAX_THREAD threads!");
+     146           0 :         return tls[i].r;
+     147             : }
+     148             : #else
+     149             : Clock &Clock::getInstance() {
+     150             :         static Clock r;
+     151             :         return r;
+     152             : }
+     153             : #endif
+     154             : 
+     155             : } /* namespace scs */
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Common.cpp.func-sort-c.html b/doc/coverageReport/src/Common.cpp.func-sort-c.html new file mode 100644 index 000000000..8b8e54c80 --- /dev/null +++ b/doc/coverageReport/src/Common.cpp.func-sort-c.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Common.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Common.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486277.4 %
Date:2024-04-08 14:58:22Functions:5683.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16getInstallPrefixB5cxx11Ev0
_ZN7crpropa11getDataPathENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE547
_ZN7crpropa12closestIndexEdRKSt6vectorIdSaIdEE565
_ZN7crpropa22interpolateEquidistantEdddRKSt6vectorIdSaIdEE1528
_ZN7crpropa11interpolateEdRKSt6vectorIdSaIdEES4_158374
_ZN7crpropa13interpolate2dEddRKSt6vectorIdSaIdEES4_S4_9536930
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Common.cpp.func.html b/doc/coverageReport/src/Common.cpp.func.html new file mode 100644 index 000000000..b7cf2d004 --- /dev/null +++ b/doc/coverageReport/src/Common.cpp.func.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Common.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Common.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486277.4 %
Date:2024-04-08 14:58:22Functions:5683.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11getDataPathENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE547
_ZN7crpropa11interpolateEdRKSt6vectorIdSaIdEES4_158374
_ZN7crpropa12closestIndexEdRKSt6vectorIdSaIdEE565
_ZN7crpropa13interpolate2dEddRKSt6vectorIdSaIdEES4_S4_9536930
_ZN7crpropa16getInstallPrefixB5cxx11Ev0
_ZN7crpropa22interpolateEquidistantEdddRKSt6vectorIdSaIdEE1528
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Common.cpp.gcov.html b/doc/coverageReport/src/Common.cpp.gcov.html new file mode 100644 index 000000000..485f15540 --- /dev/null +++ b/doc/coverageReport/src/Common.cpp.gcov.html @@ -0,0 +1,212 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Common.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Common.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486277.4 %
Date:2024-04-08 14:58:22Functions:5683.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Common.h"
+       2             : 
+       3             : #include "kiss/path.h"
+       4             : #include "kiss/logger.h"
+       5             : 
+       6             : #include <cstdlib>
+       7             : #include <fstream>
+       8             : #include <string>
+       9             : #include <cmath>
+      10             : #include <algorithm>
+      11             : 
+      12             : #define index(i,j) ((j)+(i)*Y.size())
+      13             : 
+      14             : namespace crpropa {
+      15             : 
+      16         547 : std::string getDataPath(std::string filename) {
+      17         547 :         static std::string dataPath;
+      18         547 :         if (dataPath.size())
+      19         534 :                 return concat_path(dataPath, filename);
+      20             : 
+      21          13 :         const char *env_path = getenv("CRPROPA_DATA_PATH");
+      22          13 :         if (env_path) {
+      23           0 :                 if (is_directory(env_path)) {
+      24             :                         dataPath = env_path;
+      25           0 :                         KISS_LOG_INFO << "getDataPath: use environment variable, "
+      26           0 :                                         << dataPath << std::endl;
+      27           0 :                         return concat_path(dataPath, filename);
+      28             :                 }
+      29             :         }
+      30             : 
+      31             : #ifdef CRPROPA_INSTALL_PREFIX
+      32             :         {
+      33          13 :                 std::string _path = CRPROPA_INSTALL_PREFIX "/share/crpropa";
+      34          13 :                 if (is_directory(_path)) {
+      35             :                         dataPath = _path;
+      36           0 :                         KISS_LOG_INFO
+      37           0 :                         << "getDataPath: use install prefix, " << dataPath << std::endl;
+      38           0 :                         return concat_path(dataPath, filename);
+      39             :                 }
+      40             :         }
+      41             : #endif
+      42             : 
+      43             :         {
+      44          13 :                 std::string _path = executable_path() + "../data";
+      45          13 :                 if (is_directory(_path)) {
+      46             :                         dataPath = _path;
+      47           0 :                         KISS_LOG_INFO << "getDataPath: use executable path, " << dataPath
+      48           0 :                                         << std::endl;
+      49           0 :                         return concat_path(dataPath, filename);
+      50             :                 }
+      51             :         }
+      52             : 
+      53             :         dataPath = "data";
+      54          13 :         KISS_LOG_INFO << "getDataPath: use default, " << dataPath << std::endl;
+      55          13 :         return concat_path(dataPath, filename);
+      56             : }
+      57             : 
+      58             : 
+      59           0 : std::string getInstallPrefix()
+      60             : {
+      61           0 :   std::string _path = "";
+      62             :   #ifdef CRPROPA_INSTALL_PREFIX
+      63             :     _path += CRPROPA_INSTALL_PREFIX;
+      64             :   #endif
+      65           0 :   return _path;
+      66             : };
+      67             : 
+      68      158374 : double interpolate(double x, const std::vector<double> &X,
+      69             :                 const std::vector<double> &Y) {
+      70             :         std::vector<double>::const_iterator it = std::upper_bound(X.begin(),
+      71             :                         X.end(), x);
+      72      158374 :         if (it == X.begin())
+      73           1 :                 return Y.front();
+      74      158373 :         if (it == X.end())
+      75           1 :                 return Y.back();
+      76             : 
+      77             :         size_t i = it - X.begin() - 1;
+      78      158372 :         return Y[i] + (x - X[i]) * (Y[i + 1] - Y[i]) / (X[i + 1] - X[i]);
+      79             : }
+      80             : 
+      81     9536930 : double interpolate2d(double x, double y, const std::vector<double> &X,
+      82             :                 const std::vector<double> &Y, const std::vector<double> &Z) {
+      83             : 
+      84             :         std::vector<double>::const_iterator itx = std::upper_bound(X.begin(), X.end(), x);
+      85             :         std::vector<double>::const_iterator ity = std::upper_bound(Y.begin(), Y.end(), y);
+      86             : 
+      87     9536930 :         if (x > X.back() || x < X.front())
+      88             :                 return 0;
+      89     9536930 :         if (y > Y.back() || y < Y.front())
+      90             :                 return 0;
+      91             : 
+      92     9536930 :         if (itx == X.begin() && ity == Y.begin())
+      93           0 :                 return Z.front();
+      94     9536930 :         if (itx == X.end() && ity == Y.end())
+      95          73 :                 return Z.back();
+      96             : 
+      97     9536857 :         size_t i = itx - X.begin() - 1;
+      98     9536857 :         size_t j = ity - Y.begin() - 1;
+      99             : 
+     100     9536857 :         double Q11 = Z[index(i,j)];
+     101     9536857 :         double Q12 = Z[index(i,j+1)];
+     102     9536857 :         double Q21 = Z[index(i+1,j)];
+     103     9536857 :         double Q22 = Z[index(i+1,j+1)];
+     104             : 
+     105     9536857 :         double R1 = ((X[i+1]-x)/(X[i+1]-X[i]))*Q11+((x-X[i])/(X[i+1]-X[i]))*Q21;
+     106     9536857 :         double R2 = ((X[i+1]-x)/(X[i+1]-X[i]))*Q12+((x-X[i])/(X[i+1]-X[i]))*Q22;
+     107             : 
+     108     9536857 :         return ((Y[j+1]-y)/(Y[j+1]-Y[j]))*R1+((y-Y[j])/(Y[j+1]-Y[j]))*R2;
+     109             : }
+     110             : 
+     111        1528 : double interpolateEquidistant(double x, double lo, double hi,
+     112             :                 const std::vector<double> &Y) {
+     113        1528 :         if (x <= lo)
+     114           1 :                 return Y.front();
+     115        1527 :         if (x >= hi)
+     116           1 :                 return Y.back();
+     117             : 
+     118        1526 :         double dx = (hi - lo) / (Y.size() - 1);
+     119        1526 :         double p = (x - lo) / dx;
+     120        1526 :         size_t i = floor(p);
+     121        1526 :         return Y[i] + (p - i) * (Y[i + 1] - Y[i]);
+     122             : }
+     123             : 
+     124         565 : size_t closestIndex(double x, const std::vector<double> &X) {
+     125         565 :         size_t i1 = std::lower_bound(X.begin(), X.end(), x) - X.begin();
+     126         565 :         if (i1 == 0)
+     127             :                 return i1;
+     128         565 :         size_t i0 = i1 - 1;
+     129         565 :         if (std::fabs(X[i0] - x) < std::fabs(X[i1] - x))
+     130             :                 return i0;
+     131             :         else
+     132         308 :                 return i1;
+     133             : }
+     134             : 
+     135             : } // namespace crpropa
+     136             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Cosmology.cpp.func-sort-c.html b/doc/coverageReport/src/Cosmology.cpp.func-sort-c.html new file mode 100644 index 000000000..5faf01e27 --- /dev/null +++ b/doc/coverageReport/src/Cosmology.cpp.func-sort-c.html @@ -0,0 +1,132 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Cosmology.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Cosmology.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:449247.8 %
Date:2024-04-08 14:58:22Functions:61540.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22setCosmologyParametersEdd0
_ZN7crpropa25redshift2ComovingDistanceEd0
_ZN7crpropa27luminosityDistance2RedshiftEd0
_ZN7crpropa27redshift2LuminosityDistanceEd0
_ZN7crpropa28lightTravelDistance2RedshiftEd0
_ZN7crpropa28redshift2LightTravelDistanceEd0
_ZN7crpropa2H0Ev0
_ZN7crpropa6omegaLEv0
_ZN7crpropa6omegaMEv0
_ZN7crpropa25comovingDistance2RedshiftEd1
_ZN7crpropa28lightTravel2ComovingDistanceEd1
_ZN7crpropa28comoving2LightTravelDistanceEd2
_ZN7crpropa9Cosmology6updateEv19
_ZN7crpropa9CosmologyC2Ev19
_ZN7crpropa10hubbleRateEd7623
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Cosmology.cpp.func.html b/doc/coverageReport/src/Cosmology.cpp.func.html new file mode 100644 index 000000000..ea101710d --- /dev/null +++ b/doc/coverageReport/src/Cosmology.cpp.func.html @@ -0,0 +1,132 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Cosmology.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Cosmology.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:449247.8 %
Date:2024-04-08 14:58:22Functions:61540.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10hubbleRateEd7623
_ZN7crpropa22setCosmologyParametersEdd0
_ZN7crpropa25comovingDistance2RedshiftEd1
_ZN7crpropa25redshift2ComovingDistanceEd0
_ZN7crpropa27luminosityDistance2RedshiftEd0
_ZN7crpropa27redshift2LuminosityDistanceEd0
_ZN7crpropa28comoving2LightTravelDistanceEd2
_ZN7crpropa28lightTravel2ComovingDistanceEd1
_ZN7crpropa28lightTravelDistance2RedshiftEd0
_ZN7crpropa28redshift2LightTravelDistanceEd0
_ZN7crpropa2H0Ev0
_ZN7crpropa6omegaLEv0
_ZN7crpropa6omegaMEv0
_ZN7crpropa9Cosmology6updateEv19
_ZN7crpropa9CosmologyC2Ev19
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Cosmology.cpp.gcov.html b/doc/coverageReport/src/Cosmology.cpp.gcov.html new file mode 100644 index 000000000..f85d7609e --- /dev/null +++ b/doc/coverageReport/src/Cosmology.cpp.gcov.html @@ -0,0 +1,245 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Cosmology.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Cosmology.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:449247.8 %
Date:2024-04-08 14:58:22Functions:61540.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Cosmology.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Common.h"
+       4             : 
+       5             : #include <vector>
+       6             : #include <cmath>
+       7             : #include <stdexcept>
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11             : /**
+      12             :  @class Cosmology
+      13             :  @brief Cosmology calculations
+      14             :  */
+      15             : struct Cosmology {
+      16             :         double H0; // Hubble parameter at z=0
+      17             :         double omegaM; // matter density parameter
+      18             :         double omegaL; // vacuum energy parameter
+      19             : 
+      20             :         static const int n;
+      21             :         static const double zmin;
+      22             :         static const double zmax;
+      23             : 
+      24             :         std::vector<double> Z;  // redshift
+      25             :         std::vector<double> Dc; // comoving distance [m]
+      26             :         std::vector<double> Dl; // luminosity distance [m]
+      27             :         std::vector<double> Dt; // light travel distance [m]
+      28             : 
+      29          19 :         void update() {
+      30          19 :                 double dH = c_light / H0; // Hubble distance
+      31             : 
+      32          19 :                 std::vector<double> E(n);
+      33          19 :                 E[0] = 1;
+      34             : 
+      35             :                 // Relation between comoving distance r and redshift z (cf. J.A. Peacock, Cosmological physics, p. 89 eq. 3.76)
+      36             :                 // dr = c / H(z) dz, integration using midpoint rule
+      37             :                 double dlz = log10(zmax) - log10(zmin);
+      38       19000 :                 for (int i = 1; i < n; i++) {
+      39       18981 :                         Z[i] = zmin * pow(10, i * dlz / (n - 1)); // logarithmic even spacing
+      40       18981 :                         double dz = (Z[i] - Z[i - 1]); // redshift step
+      41       18981 :                         E[i] = sqrt(omegaL + omegaM * pow_integer<3>(1 + Z[i]));
+      42       18981 :                         Dc[i] = Dc[i - 1] + dH * dz * (1 / E[i] + 1 / E[i - 1]) / 2;
+      43       18981 :                         Dl[i] = (1 + Z[i]) * Dc[i];
+      44       18981 :                         Dt[i] = Dt[i - 1]
+      45       18981 :                                         + dH * dz
+      46       18981 :                                                         * (1 / ((1 + Z[i]) * E[i])
+      47       18981 :                                                                         + 1 / ((1 + Z[i - 1]) * E[i - 1])) / 2;
+      48             :                 }
+      49          19 :         }
+      50             : 
+      51          19 :         Cosmology() {
+      52             :         // Cosmological parameters (K.A. Olive et al. (Particle Data Group), Chin. Phys. C, 38, 090001 (2014))
+      53          19 :                 H0 = 67.3 * 1000 * meter / second / Mpc; // default values
+      54          19 :                 omegaM = 0.315;
+      55          19 :                 omegaL = 1 - omegaM;
+      56             : 
+      57          19 :                 Z.resize(n);
+      58          19 :                 Dc.resize(n);
+      59          19 :                 Dl.resize(n);
+      60          19 :                 Dt.resize(n);
+      61             : 
+      62          19 :                 Z[0] = 0;
+      63          19 :                 Dc[0] = 0;
+      64          19 :                 Dl[0] = 0;
+      65          19 :                 Dt[0] = 0;
+      66             : 
+      67          19 :                 update();
+      68          19 :         }
+      69             : 
+      70             :         void setParameters(double h, double oM) {
+      71           0 :                 H0 = h * 1e5 / Mpc;
+      72           0 :                 omegaM = oM;
+      73           0 :                 omegaL = 1 - oM;
+      74           0 :                 update();
+      75             :         }
+      76             : };
+      77             : 
+      78             : const int Cosmology::n = 1000;
+      79             : const double Cosmology::zmin = 0.0001;
+      80             : const double Cosmology::zmax = 100;
+      81             : 
+      82             : static Cosmology cosmology; // instance is created at runtime
+      83             : 
+      84           0 : void setCosmologyParameters(double h, double oM) {
+      85             :         cosmology.setParameters(h, oM);
+      86           0 : }
+      87             : 
+      88        7623 : double hubbleRate(double z) {
+      89        7623 :         return cosmology.H0
+      90        7623 :                         * sqrt(cosmology.omegaL + cosmology.omegaM * pow(1 + z, 3));
+      91             : }
+      92             : 
+      93           0 : double omegaL() {
+      94           0 :         return cosmology.omegaL;
+      95             : }
+      96             : 
+      97           0 : double omegaM() {
+      98           0 :         return cosmology.omegaM;
+      99             : }
+     100             : 
+     101           0 : double H0() {
+     102           0 :         return cosmology.H0;
+     103             : }
+     104             : 
+     105           1 : double comovingDistance2Redshift(double d) {
+     106           1 :         if (d < 0)
+     107           0 :                 throw std::runtime_error("Cosmology: d < 0");
+     108           1 :         if (d > cosmology.Dc.back())
+     109           0 :                 throw std::runtime_error("Cosmology: d > dmax");
+     110           1 :         return interpolate(d, cosmology.Dc, cosmology.Z);
+     111             : }
+     112             : 
+     113           0 : double redshift2ComovingDistance(double z) {
+     114           0 :         if (z < 0)
+     115           0 :                 throw std::runtime_error("Cosmology: z < 0");
+     116           0 :         if (z > cosmology.zmax)
+     117           0 :                 throw std::runtime_error("Cosmology: z > zmax");
+     118           0 :         return interpolate(z, cosmology.Z, cosmology.Dc);
+     119             : }
+     120             : 
+     121           0 : double luminosityDistance2Redshift(double d) {
+     122           0 :         if (d < 0)
+     123           0 :                 throw std::runtime_error("Cosmology: d < 0");
+     124           0 :         if (d > cosmology.Dl.back())
+     125           0 :                 throw std::runtime_error("Cosmology: d > dmax");
+     126           0 :         return interpolate(d, cosmology.Dl, cosmology.Z);
+     127             : }
+     128             : 
+     129           0 : double redshift2LuminosityDistance(double z) {
+     130           0 :         if (z < 0)
+     131           0 :                 throw std::runtime_error("Cosmology: z < 0");
+     132           0 :         if (z > cosmology.zmax)
+     133           0 :                 throw std::runtime_error("Cosmology: z > zmax");
+     134           0 :         return interpolate(z, cosmology.Z, cosmology.Dl);
+     135             : }
+     136             : 
+     137           0 : double lightTravelDistance2Redshift(double d) {
+     138           0 :         if (d < 0)
+     139           0 :                 throw std::runtime_error("Cosmology: d < 0");
+     140           0 :         if (d > cosmology.Dt.back())
+     141           0 :                 throw std::runtime_error("Cosmology: d > dmax");
+     142           0 :         return interpolate(d, cosmology.Dt, cosmology.Z);
+     143             : }
+     144             : 
+     145           0 : double redshift2LightTravelDistance(double z) {
+     146           0 :         if (z < 0)
+     147           0 :                 throw std::runtime_error("Cosmology: z < 0");
+     148           0 :         if (z > cosmology.zmax)
+     149           0 :                 throw std::runtime_error("Cosmology: z > zmax");
+     150           0 :         return interpolate(z, cosmology.Z, cosmology.Dt);
+     151             : }
+     152             : 
+     153           2 : double comoving2LightTravelDistance(double d) {
+     154           2 :         if (d < 0)
+     155           0 :                 throw std::runtime_error("Cosmology: d < 0");
+     156           2 :         if (d > cosmology.Dc.back())
+     157           0 :                 throw std::runtime_error("Cosmology: d > dmax");
+     158           2 :         return interpolate(d, cosmology.Dc, cosmology.Dt);
+     159             : }
+     160             : 
+     161           1 : double lightTravel2ComovingDistance(double d) {
+     162           1 :         if (d < 0)
+     163           0 :                 throw std::runtime_error("Cosmology: d < 0");
+     164           1 :         if (d > cosmology.Dt.back())
+     165           0 :                 throw std::runtime_error("Cosmology: d > dmax");
+     166           1 :         return interpolate(d, cosmology.Dt, cosmology.Dc);
+     167             : }
+     168             : 
+     169             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html b/doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html new file mode 100644 index 000000000..08e7db8aa --- /dev/null +++ b/doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html @@ -0,0 +1,204 @@ + + + + + + + LCOV - coverage.info.cleaned - src/EmissionMap.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - EmissionMap.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8315653.2 %
Date:2024-04-08 14:58:22Functions:183354.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11EmissionMap4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap4saveERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap5mergeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap6hasMapEid0
_ZN7crpropa11EmissionMap7fillMapERKNS_13ParticleStateEd0
_ZN7crpropa11EmissionMapC2Emmm0
_ZN7crpropa24CylindricalProjectionMap7getNPhiEv0
_ZN7crpropa24CylindricalProjectionMap9getNThetaEv0
_ZN7crpropa24CylindricalProjectionMapC2Ev0
_ZNK7crpropa11EmissionMap13drawDirectionERKNS_13ParticleStateERNS_7Vector3IdEE0
_ZNK7crpropa11EmissionMap14checkDirectionERKNS_13ParticleStateE0
_ZNK7crpropa11EmissionMap14checkDirectionEidRKNS_7Vector3IdEE0
_ZNK7crpropa24CylindricalProjectionMap14checkDirectionERKNS_7Vector3IdEE0
_ZNK7crpropa24CylindricalProjectionMap6getCdfEv0
_ZNK7crpropa24CylindricalProjectionMap6getPdfEv0
_ZN7crpropa11EmissionMap5mergeEPKS0_1
_ZN7crpropa11EmissionMap7getMapsEv1
_ZN7crpropa11EmissionMapC2Emmmdd1
_ZNK7crpropa11EmissionMap13energyFromBinEm1
_ZNK7crpropa24CylindricalProjectionMap13drawDirectionEv1
_ZNK7crpropa24CylindricalProjectionMap9updateCdfEv1
_ZN7crpropa11EmissionMapC2Ev2
_ZNK7crpropa11EmissionMap7getMapsEv2
_ZNK7crpropa24CylindricalProjectionMap16directionFromBinEm2
_ZNK7crpropa11EmissionMap13drawDirectionEidRNS_7Vector3IdEE3
_ZN7crpropa11EmissionMap7fillMapEidRKNS_7Vector3IdEEd4
_ZN7crpropa24CylindricalProjectionMap7fillBinERKNS_7Vector3IdEEd4
_ZN7crpropa24CylindricalProjectionMap6getPdfEv5
_ZN7crpropa24CylindricalProjectionMapC2Emm6
_ZNK7crpropa24CylindricalProjectionMap16binFromDirectionERKNS_7Vector3IdEE6
_ZN7crpropa11EmissionMap6getMapEid7
_ZNK7crpropa11EmissionMap13binFromEnergyEd11
_ZN7crpropa24CylindricalProjectionMap7fillBinEmd129604
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/EmissionMap.cpp.func.html b/doc/coverageReport/src/EmissionMap.cpp.func.html new file mode 100644 index 000000000..ca8986910 --- /dev/null +++ b/doc/coverageReport/src/EmissionMap.cpp.func.html @@ -0,0 +1,204 @@ + + + + + + + LCOV - coverage.info.cleaned - src/EmissionMap.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - EmissionMap.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8315653.2 %
Date:2024-04-08 14:58:22Functions:183354.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11EmissionMap4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap4saveERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap5mergeEPKS0_1
_ZN7crpropa11EmissionMap5mergeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap6getMapEid7
_ZN7crpropa11EmissionMap6hasMapEid0
_ZN7crpropa11EmissionMap7fillMapERKNS_13ParticleStateEd0
_ZN7crpropa11EmissionMap7fillMapEidRKNS_7Vector3IdEEd4
_ZN7crpropa11EmissionMap7getMapsEv1
_ZN7crpropa11EmissionMapC2Emmm0
_ZN7crpropa11EmissionMapC2Emmmdd1
_ZN7crpropa11EmissionMapC2Ev2
_ZN7crpropa24CylindricalProjectionMap6getPdfEv5
_ZN7crpropa24CylindricalProjectionMap7fillBinERKNS_7Vector3IdEEd4
_ZN7crpropa24CylindricalProjectionMap7fillBinEmd129604
_ZN7crpropa24CylindricalProjectionMap7getNPhiEv0
_ZN7crpropa24CylindricalProjectionMap9getNThetaEv0
_ZN7crpropa24CylindricalProjectionMapC2Emm6
_ZN7crpropa24CylindricalProjectionMapC2Ev0
_ZNK7crpropa11EmissionMap13binFromEnergyEd11
_ZNK7crpropa11EmissionMap13drawDirectionERKNS_13ParticleStateERNS_7Vector3IdEE0
_ZNK7crpropa11EmissionMap13drawDirectionEidRNS_7Vector3IdEE3
_ZNK7crpropa11EmissionMap13energyFromBinEm1
_ZNK7crpropa11EmissionMap14checkDirectionERKNS_13ParticleStateE0
_ZNK7crpropa11EmissionMap14checkDirectionEidRKNS_7Vector3IdEE0
_ZNK7crpropa11EmissionMap7getMapsEv2
_ZNK7crpropa24CylindricalProjectionMap13drawDirectionEv1
_ZNK7crpropa24CylindricalProjectionMap14checkDirectionERKNS_7Vector3IdEE0
_ZNK7crpropa24CylindricalProjectionMap16binFromDirectionERKNS_7Vector3IdEE6
_ZNK7crpropa24CylindricalProjectionMap16directionFromBinEm2
_ZNK7crpropa24CylindricalProjectionMap6getCdfEv0
_ZNK7crpropa24CylindricalProjectionMap6getPdfEv0
_ZNK7crpropa24CylindricalProjectionMap9updateCdfEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/EmissionMap.cpp.gcov.html b/doc/coverageReport/src/EmissionMap.cpp.gcov.html new file mode 100644 index 000000000..59cbfc778 --- /dev/null +++ b/doc/coverageReport/src/EmissionMap.cpp.gcov.html @@ -0,0 +1,370 @@ + + + + + + + LCOV - coverage.info.cleaned - src/EmissionMap.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - EmissionMap.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8315653.2 %
Date:2024-04-08 14:58:22Functions:183354.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/EmissionMap.h"
+       2             : #include "crpropa/Random.h"
+       3             : #include "crpropa/Units.h"
+       4             : 
+       5             : #include "kiss/logger.h"
+       6             : 
+       7             : #include <fstream>
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11           0 : CylindricalProjectionMap::CylindricalProjectionMap() : nPhi(360), nTheta(180), dirty(false), pdf(nPhi* nTheta, 0), cdf(nPhi* nTheta, 0) {
+      12           0 :         sPhi = 2. * M_PI / nPhi;
+      13           0 :         sTheta = 2. / nTheta;
+      14           0 : }
+      15             : 
+      16           6 : CylindricalProjectionMap::CylindricalProjectionMap(size_t nPhi, size_t nTheta) : nPhi(nPhi), nTheta(nTheta), dirty(false), pdf(nPhi* nTheta, 0), cdf(nPhi* nTheta, 0) {
+      17           6 :         sPhi = 2 * M_PI / nPhi;
+      18           6 :         sTheta = 2. / nTheta;
+      19           6 : }
+      20             : 
+      21           4 : void CylindricalProjectionMap::fillBin(const Vector3d& direction, double weight) {
+      22           4 :         size_t bin = binFromDirection(direction);
+      23           4 :         fillBin(bin, weight);
+      24           4 : }
+      25             : 
+      26      129604 : void CylindricalProjectionMap::fillBin(size_t bin, double weight) {
+      27      129604 :         pdf[bin] += weight;
+      28      129604 :         dirty = true;
+      29      129604 : }
+      30             : 
+      31           1 : Vector3d CylindricalProjectionMap::drawDirection() const {
+      32           1 :         if (dirty)
+      33           1 :                 updateCdf();
+      34             : 
+      35           1 :         size_t bin = Random::instance().randBin(cdf);
+      36             : 
+      37           1 :         return directionFromBin(bin);
+      38             : }
+      39             : 
+      40           0 : bool CylindricalProjectionMap::checkDirection(const Vector3d &direction) const {
+      41           0 :         size_t bin = binFromDirection(direction);
+      42           0 :         return pdf[bin];
+      43             : }
+      44             : 
+      45             : 
+      46           0 : const std::vector<double>& CylindricalProjectionMap::getPdf() const {
+      47           0 :         return pdf;
+      48             : }
+      49             : 
+      50           5 : std::vector<double>& CylindricalProjectionMap::getPdf() {
+      51           5 :         return pdf;
+      52             : }
+      53             : 
+      54           0 : const std::vector<double>& CylindricalProjectionMap::getCdf() const {
+      55           0 :         return cdf;
+      56             : }
+      57             : 
+      58           0 : size_t CylindricalProjectionMap::getNPhi() {
+      59           0 :         return nPhi;
+      60             : }
+      61             : 
+      62           0 : size_t CylindricalProjectionMap::getNTheta() {
+      63           0 :         return nTheta;
+      64             : }
+      65             : 
+      66             : /*
+      67             :  * Cylindrical Coordinates
+      68             :  * iPhi -> [0, 2*pi]
+      69             :  * iTheta -> [0, 2]
+      70             :  *
+      71             :  * Spherical Coordinates
+      72             :  * phi -> [-pi, pi]
+      73             :  * theta -> [0, pi]
+      74             :  */
+      75           6 : size_t CylindricalProjectionMap::binFromDirection(const Vector3d& direction) const {
+      76             :         // convert to cylindrical
+      77           6 :         double phi = direction.getPhi() + M_PI;
+      78           6 :         double theta = sin(M_PI_2 - direction.getTheta()) + 1;
+      79             : 
+      80             :         // to indices
+      81           6 :         size_t iPhi = phi / sPhi;
+      82           6 :         size_t iTheta = theta / sTheta;
+      83             : 
+      84             :         // interleave
+      85           6 :         size_t bin =  iTheta * nPhi + iPhi;
+      86           6 :         return bin;
+      87             : }
+      88             : 
+      89           2 : Vector3d CylindricalProjectionMap::directionFromBin(size_t bin) const {
+      90             :         // deinterleave
+      91           2 :         double iPhi = bin % nPhi;
+      92           2 :         double iTheta = bin / nPhi;
+      93             : 
+      94             :         // any where in the bin
+      95           2 :         iPhi += Random::instance().rand();
+      96           2 :         iTheta += Random::instance().rand();
+      97             : 
+      98             :         // cylindrical Coordinates
+      99           2 :         double phi = iPhi * sPhi;
+     100           2 :         double theta = iTheta * sTheta;
+     101             : 
+     102             :         // sphericala Coordinates
+     103           2 :         phi = phi - M_PI;
+     104           2 :         theta = M_PI_2 - asin(theta - 1);
+     105             : 
+     106             :         Vector3d v;
+     107           2 :         v.setRThetaPhi(1.0, theta, phi);
+     108           2 :         return v;
+     109             : }
+     110             : 
+     111           1 : void CylindricalProjectionMap::updateCdf() const {
+     112           1 :         if (dirty) {
+     113           1 :                 cdf[0] = pdf[0];
+     114       64800 :                 for (size_t i = 1; i < pdf.size(); i++) {
+     115       64799 :                         cdf[i] = cdf[i-1] + pdf[i];
+     116             :                 }
+     117           1 :                 dirty = false;
+     118             :         }
+     119           1 : }
+     120             : 
+     121           2 : EmissionMap::EmissionMap() : minEnergy(0.0001 * EeV), maxEnergy(10000 * EeV),
+     122           2 :         nEnergy(8*2), nPhi(360), nTheta(180) {
+     123           2 :         logStep = log10(maxEnergy / minEnergy) / nEnergy;
+     124           2 : }
+     125             : 
+     126           0 : EmissionMap::EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy) : minEnergy(0.0001 * EeV), maxEnergy(10000 * EeV),
+     127           0 :         nEnergy(nEnergy), nPhi(nPhi), nTheta(nTheta) {
+     128           0 :         logStep = log10(maxEnergy / minEnergy) / nEnergy;
+     129           0 : }
+     130             : 
+     131           1 : EmissionMap::EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy, double minEnergy, double maxEnergy) : minEnergy(minEnergy), maxEnergy(maxEnergy), nEnergy(nEnergy), nPhi(nPhi), nTheta(nTheta) {
+     132           1 :         logStep = log10(maxEnergy / minEnergy) / nEnergy;
+     133           1 : }
+     134             : 
+     135           1 : double EmissionMap::energyFromBin(size_t bin) const {
+     136           1 :         return pow(10, log10(minEnergy) + logStep * bin);
+     137             : }
+     138             : 
+     139          11 : size_t EmissionMap::binFromEnergy(double energy) const {
+     140          11 :         return log10(energy / minEnergy) / logStep;
+     141             : }
+     142             : 
+     143           4 : void EmissionMap::fillMap(int pid, double energy, const Vector3d& direction, double weight) {
+     144           4 :         getMap(pid, energy)->fillBin(direction, weight);
+     145           4 : }
+     146             : 
+     147           0 : void EmissionMap::fillMap(const ParticleState& state, double weight) {
+     148           0 :         fillMap(state.getId(), state.getEnergy(), state.getDirection(), weight);
+     149           0 : }
+     150             : 
+     151           1 : EmissionMap::map_t &EmissionMap::getMaps() {
+     152           1 :         return maps;
+     153             : }
+     154             : 
+     155           2 : const EmissionMap::map_t &EmissionMap::getMaps() const {
+     156           2 :         return maps;
+     157             : }
+     158             : 
+     159           3 : bool EmissionMap::drawDirection(int pid, double energy, Vector3d& direction) const {
+     160           3 :         key_t key(pid, binFromEnergy(energy));
+     161             :         map_t::const_iterator i = maps.find(key);
+     162             : 
+     163           3 :         if (i == maps.end() || !i->second.valid()) {
+     164             :                 return false;
+     165             :         } else {
+     166           1 :                 direction = i->second->drawDirection();
+     167           1 :                 return true;
+     168             :         }
+     169             : }
+     170             : 
+     171           0 : bool EmissionMap::drawDirection(const ParticleState& state, Vector3d& direction) const {
+     172           0 :         return drawDirection(state.getId(), state.getEnergy(), direction);
+     173             : }
+     174             : 
+     175           0 : bool EmissionMap::checkDirection(int pid, double energy, const Vector3d& direction) const {
+     176           0 :         key_t key(pid, binFromEnergy(energy));
+     177             :         map_t::const_iterator i = maps.find(key);
+     178             : 
+     179           0 :         if (i == maps.end() || !i->second.valid()) {
+     180             :                 return false;
+     181             :         } else {
+     182           0 :                 return i->second->checkDirection(direction);
+     183             :         }
+     184             : }
+     185             : 
+     186           0 : bool EmissionMap::checkDirection(const ParticleState& state) const {
+     187           0 :         return checkDirection(state.getId(), state.getEnergy(), state.getDirection());
+     188             : }
+     189             : 
+     190           0 : bool EmissionMap::hasMap(int pid, double energy) {
+     191           0 :     key_t key(pid, binFromEnergy(energy));
+     192             :     map_t::iterator i = maps.find(key);
+     193           0 :     if (i == maps.end() || !i->second.valid())
+     194             :                 return false;
+     195             :         else
+     196           0 :                 return true;
+     197             : }
+     198             : 
+     199           7 : ref_ptr<CylindricalProjectionMap> EmissionMap::getMap(int pid, double energy) {
+     200           7 :         key_t key(pid, binFromEnergy(energy));
+     201             :         map_t::iterator i = maps.find(key);
+     202           7 :         if (i == maps.end() || !i->second.valid()) {
+     203           5 :                 ref_ptr<CylindricalProjectionMap> cpm = new CylindricalProjectionMap(nPhi, nTheta);
+     204           5 :                 maps[key] = cpm;
+     205             :                 return cpm;
+     206             :         } else {
+     207             :                 return i->second;
+     208             :         }
+     209             : }
+     210             : 
+     211           0 : void EmissionMap::save(const std::string &filename) {
+     212           0 :         std::ofstream out(filename.c_str());
+     213           0 :         out.imbue(std::locale("C"));
+     214             : 
+     215           0 :         for (map_t::iterator i = maps.begin(); i != maps.end(); i++) {
+     216           0 :                 if (!i->second.valid())
+     217           0 :                         continue;
+     218           0 :                 out << i->first.first << " " << i->first.second << " " << energyFromBin(i->first.second) << " ";
+     219           0 :                 out << i->second->getNPhi() << " " << i->second->getNTheta();
+     220           0 :                 const std::vector<double> &pdf = i->second->getPdf();
+     221           0 :                 for (size_t i = 0; i < pdf.size(); i++)
+     222           0 :                         out << " " << pdf[i];
+     223             :                 out << std::endl;
+     224             :         }
+     225           0 : }
+     226             : 
+     227           1 : void EmissionMap::merge(const EmissionMap *other) {
+     228           1 :         if (other == 0)
+     229             :                 return;
+     230           1 :         map_t::const_iterator i = other->getMaps().begin();
+     231           1 :         map_t::const_iterator end = other->getMaps().end();
+     232           3 :         for(;i != end; i++) {
+     233           2 :                 if (!i->second.valid())
+     234           0 :                         continue;
+     235             : 
+     236           2 :                 std::vector<double> &otherpdf = i->second->getPdf();
+     237           2 :                 ref_ptr<CylindricalProjectionMap> cpm = getMap(i->first.first, i->first.second);
+     238             : 
+     239           2 :                 if (otherpdf.size() != cpm->getPdf().size()) {
+     240           0 :                         throw std::runtime_error("PDF size mismatch!");
+     241             :                         break;
+     242             :                 }
+     243             : 
+     244      129602 :                 for (size_t k = 0; k < otherpdf.size(); k++) {
+     245      129600 :                         cpm->fillBin(k, otherpdf[k]);
+     246             :                 }
+     247             :         }
+     248             : }
+     249             : 
+     250           0 : void EmissionMap::merge(const std::string &filename) {
+     251           0 :         EmissionMap em;
+     252           0 :         em.load(filename);
+     253           0 :         merge(&em);
+     254           0 : }
+     255             : 
+     256           0 : void EmissionMap::load(const std::string &filename) {
+     257           0 :         std::ifstream in(filename.c_str());
+     258           0 :         in.imbue(std::locale("C"));
+     259             : 
+     260           0 :         while(in.good()) {
+     261           0 :                 key_t key;
+     262             :                 double tmp;
+     263             :                 size_t nPhi_, nTheta_;
+     264           0 :                 in >> key.first >> key.second >> tmp;
+     265             :                 in >> nPhi_ >> nTheta_;
+     266             : 
+     267           0 :                 if (!in.good()) {
+     268           0 :                         KISS_LOG_ERROR << "Invalid line: " << key.first << " " << key.second << " " << nPhi_ << " " << nTheta_;
+     269           0 :                         break;
+     270             :                 }
+     271             : 
+     272           0 :                 if (nPhi != nPhi_) {
+     273           0 :                         KISS_LOG_WARNING << "nPhi mismatch: " << nPhi << " " << nPhi_;
+     274             :                 }
+     275           0 :                 if (nTheta != nTheta_) {
+     276           0 :                         KISS_LOG_WARNING << "nTheta mismatch: " << nTheta << " " << nTheta_;
+     277             :                 }
+     278             : 
+     279           0 :                 ref_ptr<CylindricalProjectionMap> cpm = new CylindricalProjectionMap(nPhi_, nTheta_);
+     280           0 :                 std::vector<double> &pdf = cpm->getPdf();
+     281           0 :                 for (size_t i = 0; i < pdf.size(); i++)
+     282             :                         in >> pdf[i];
+     283             : 
+     284           0 :                 if (in.good()) {
+     285           0 :                         maps[key] = cpm;
+     286             :                         // std::cout << "added " << key.first << " " << key.second << std::endl;
+     287             :                 } else {
+     288           0 :                         KISS_LOG_WARNING << "Invalid data in line: " << key.first << " " << key.second << " " << nPhi_ << " " << nTheta_ << "\n";
+     289             :                 }
+     290             :         }
+     291             : 
+     292           0 : }
+     293             : 
+     294             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Geometry.cpp.func-sort-c.html b/doc/coverageReport/src/Geometry.cpp.func-sort-c.html new file mode 100644 index 000000000..14ddef6d4 --- /dev/null +++ b/doc/coverageReport/src/Geometry.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Geometry.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Geometry.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:185036.0 %
Date:2024-04-08 14:58:22Functions:61346.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_S4_0
_ZNK7crpropa11ParaxialBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ParaxialBox6normalERKNS_7Vector3IdEE0
_ZNK7crpropa5Plane14getDescriptionB5cxx11Ev0
_ZNK7crpropa5Plane6normalERKNS_7Vector3IdEE0
_ZNK7crpropa6Sphere14getDescriptionB5cxx11Ev0
_ZNK7crpropa6Sphere6normalERKNS_7Vector3IdEE0
_ZN7crpropa11ParaxialBoxC2ERKNS_7Vector3IdEES4_1
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_1
_ZNK7crpropa5Plane8distanceERKNS_7Vector3IdEE2
_ZN7crpropa6SphereC2ERKNS_7Vector3IdEEd4
_ZNK7crpropa11ParaxialBox8distanceERKNS_7Vector3IdEE6
_ZNK7crpropa6Sphere8distanceERKNS_7Vector3IdEE12
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Geometry.cpp.func.html b/doc/coverageReport/src/Geometry.cpp.func.html new file mode 100644 index 000000000..ced667ab2 --- /dev/null +++ b/doc/coverageReport/src/Geometry.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Geometry.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Geometry.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:185036.0 %
Date:2024-04-08 14:58:22Functions:61346.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11ParaxialBoxC2ERKNS_7Vector3IdEES4_1
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_1
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_S4_0
_ZN7crpropa6SphereC2ERKNS_7Vector3IdEEd4
_ZNK7crpropa11ParaxialBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ParaxialBox6normalERKNS_7Vector3IdEE0
_ZNK7crpropa11ParaxialBox8distanceERKNS_7Vector3IdEE6
_ZNK7crpropa5Plane14getDescriptionB5cxx11Ev0
_ZNK7crpropa5Plane6normalERKNS_7Vector3IdEE0
_ZNK7crpropa5Plane8distanceERKNS_7Vector3IdEE2
_ZNK7crpropa6Sphere14getDescriptionB5cxx11Ev0
_ZNK7crpropa6Sphere6normalERKNS_7Vector3IdEE0
_ZNK7crpropa6Sphere8distanceERKNS_7Vector3IdEE12
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Geometry.cpp.gcov.html b/doc/coverageReport/src/Geometry.cpp.gcov.html new file mode 100644 index 000000000..23f52e359 --- /dev/null +++ b/doc/coverageReport/src/Geometry.cpp.gcov.html @@ -0,0 +1,200 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Geometry.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Geometry.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:185036.0 %
Date:2024-04-08 14:58:22Functions:61346.2 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include <limits>
+       2             : #include <cmath>
+       3             : #include "kiss/logger.h"
+       4             : #include "crpropa/Geometry.h"
+       5             : 
+       6             : #include <iostream>
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10             : // Plane ------------------------------------------------------------------
+      11           1 : Plane::Plane(const Vector3d& _x0, const Vector3d& _n) : x0(_x0), n(_n) {
+      12           1 : };
+      13             : 
+      14           0 : Plane::Plane(const Vector3d& _x0, const Vector3d& v1,const Vector3d& v2) : x0(_x0), n(0,0,0) {
+      15             :         n = v1.cross(v2);
+      16             :         n /= n.getR();
+      17           0 : };
+      18             : 
+      19           2 : double Plane::distance(const Vector3d &x) const {
+      20             :         Vector3d dX = x - x0;
+      21           2 :         return n.dot(dX);
+      22             : };
+      23             : 
+      24           0 : std::string Plane::getDescription() const {
+      25           0 :         std::stringstream ss;
+      26             :         ss << "Plane: " << std::endl
+      27           0 :            << "   x0: " << x0 << std::endl
+      28           0 :            << "    n: " << n << std::endl;
+      29           0 :         return ss.str();
+      30           0 : };
+      31             : 
+      32           0 : Vector3d Plane::normal(const Vector3d& point) const {
+      33           0 :         return n;
+      34             : }
+      35             : 
+      36             : 
+      37             : // Sphere ------------------------------------------------------------------
+      38           4 : Sphere::Sphere(const Vector3d& _center, double _radius) : center(_center), radius(_radius) {
+      39           4 : };
+      40             : 
+      41          12 : double Sphere::distance(const Vector3d &point) const {
+      42             :         Vector3d dR = point - center;
+      43          12 :         return dR.getR() - radius;
+      44             : }
+      45             : 
+      46           0 : Vector3d Sphere::normal(const Vector3d& point) const {
+      47             :         Vector3d d = point - center;
+      48           0 :         return d.getUnitVector();
+      49             : }
+      50             : 
+      51           0 : std::string Sphere::getDescription() const {
+      52           0 :         std::stringstream ss;
+      53             :         ss << "Sphere: " << std::endl
+      54           0 :                         << "   Center: " << center << std::endl
+      55           0 :                         << "   Radius: " << radius << std::endl;
+      56           0 :         return ss.str();
+      57           0 : };
+      58             : 
+      59             : 
+      60             : // ParaxialBox -------------------------------------------------------------
+      61           1 : ParaxialBox::ParaxialBox(const Vector3d& _corner, const Vector3d& _size) : corner(_corner), size(_size) {
+      62           1 : };
+      63             : 
+      64           6 : double ParaxialBox::distance(const Vector3d &point) const {
+      65             :         Vector3d X = point - corner - size/2.;
+      66             : 
+      67             :         // inside the cube
+      68           6 :         if ((fabs(X.x) <= size.x/2.) and (fabs(X.y) <= size.y/2.) and (fabs(X.z) <= size.z/2.)) { 
+      69             :                 Vector3d Xp = size/2. - X.abs();
+      70           3 :                 double d = std::min(Xp.x, std::min(Xp.y, Xp.z));
+      71             : 
+      72           3 :                 return -1. * d;
+      73             :         }
+      74             : 
+      75           3 :         double a = std::max(0., fabs(X.x) - size.x/2.);
+      76           3 :         double b = std::max(0., fabs(X.y) - size.y/2.);
+      77           3 :         double c = std::max(0., fabs(X.z) - size.z/2.);
+      78             : 
+      79           3 :         return sqrt(a*a + b*b +c*c);
+      80             : }
+      81             : 
+      82           0 : Vector3d ParaxialBox::normal(const Vector3d& point) const {
+      83             :         Vector3d d = (point - corner).abs();
+      84             :         Vector3d d2 = d + size;
+      85             :         Vector3d n;
+      86             :         double dmin = std::numeric_limits<double>::infinity();
+      87           0 :         if (d.x < dmin) {
+      88             :                 dmin = d.x;
+      89             :                 n = Vector3d(-1, 0, 0);
+      90             :         }
+      91           0 :         if (d.y < dmin) {
+      92             :                 dmin = d.y;
+      93             :                 n = Vector3d(0, -1, 0);
+      94             :         }
+      95           0 :         if (d.z < dmin) {
+      96             :                 dmin = d.z;
+      97             :                 n = Vector3d(0, 0, -1);
+      98             :         }
+      99           0 :         if (d2.x < dmin) {
+     100             :                 dmin = d2.x;
+     101             :                 n = Vector3d(1, 0, 0);
+     102             :         }
+     103           0 :         if (d2.y < dmin) {
+     104             :                 dmin = d2.y;
+     105             :                 n = Vector3d(0, 1, 0);
+     106             :         }
+     107           0 :         if (d2.z < dmin) {
+     108             :                 // dmin = d2.z;
+     109             :                 n = Vector3d(0, 0, 1);
+     110             :         }
+     111             : 
+     112           0 :         return n;
+     113             : }
+     114             : 
+     115           0 : std::string ParaxialBox::getDescription() const {
+     116           0 :         std::stringstream ss;
+     117             :         ss << "ParaxialBox: " << std::endl
+     118           0 :                  << "   corner: " << corner << std::endl
+     119           0 :                  << "     size: " << size << std::endl;
+     120           0 :         return ss.str();
+     121           0 : };
+     122             : 
+     123             : 
+     124             : } // namespace
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/GridTools.cpp.func-sort-c.html b/doc/coverageReport/src/GridTools.cpp.func-sort-c.html new file mode 100644 index 000000000..14424d83d --- /dev/null +++ b/doc/coverageReport/src/GridTools.cpp.func-sort-c.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - src/GridTools.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - GridTools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6724527.3 %
Date:2024-04-08 14:58:22Functions:71936.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa17fromMagneticFieldENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa17gridPowerSpectrumENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa23rmsFieldStrengthPerAxisENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa25fromMagneticFieldStrengthENS_7ref_ptrINS_4GridIfEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridIfEEEEd0
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa15meanFieldVectorENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE1
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE11
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEd11
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/GridTools.cpp.func.html b/doc/coverageReport/src/GridTools.cpp.func.html new file mode 100644 index 000000000..0781b93b7 --- /dev/null +++ b/doc/coverageReport/src/GridTools.cpp.func.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - src/GridTools.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - GridTools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6724527.3 %
Date:2024-04-08 14:58:22Functions:71936.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa15meanFieldVectorENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE1
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE11
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa17fromMagneticFieldENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa17gridPowerSpectrumENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa23rmsFieldStrengthPerAxisENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa25fromMagneticFieldStrengthENS_7ref_ptrINS_4GridIfEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEd11
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridIfEEEEd0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/GridTools.cpp.gcov.html b/doc/coverageReport/src/GridTools.cpp.gcov.html new file mode 100644 index 000000000..20f0163b7 --- /dev/null +++ b/doc/coverageReport/src/GridTools.cpp.gcov.html @@ -0,0 +1,491 @@ + + + + + + + LCOV - coverage.info.cleaned - src/GridTools.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - GridTools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6724527.3 %
Date:2024-04-08 14:58:22Functions:71936.8 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/GridTools.h"
+       2             : #include "crpropa/magneticField/MagneticField.h"
+       3             : 
+       4             : #include <fstream>
+       5             : #include <sstream>
+       6             : 
+       7             : namespace crpropa {
+       8             : 
+       9           0 : void scaleGrid(ref_ptr<Grid1f> grid, double a) {
+      10           0 :         for (int ix = 0; ix < grid->getNx(); ix++)
+      11           0 :                 for (int iy = 0; iy < grid->getNy(); iy++)
+      12           0 :                         for (int iz = 0; iz < grid->getNz(); iz++)
+      13           0 :                                 grid->get(ix, iy, iz) *= a;
+      14           0 : }
+      15             : 
+      16          11 : void scaleGrid(ref_ptr<Grid3f> grid, double a) {
+      17         654 :         for (int ix = 0; ix < grid->getNx(); ix++)
+      18       41612 :                 for (int iy = 0; iy < grid->getNy(); iy++)
+      19     2662436 :                         for (int iz = 0; iz < grid->getNz(); iz++)
+      20     2621467 :                                 grid->get(ix, iy, iz) *= a;
+      21          11 : }
+      22             : 
+      23           1 : Vector3f meanFieldVector(ref_ptr<Grid3f> grid) {
+      24             :         size_t Nx = grid->getNx();
+      25             :         size_t Ny = grid->getNy();
+      26             :         size_t Nz = grid->getNz();
+      27             :         Vector3f mean(0.);
+      28          65 :         for (int ix = 0; ix < Nx; ix++)
+      29        4160 :                 for (int iy = 0; iy < Ny; iy++)
+      30      266240 :                         for (int iz = 0; iz < Nz; iz++)
+      31             :                                 mean += grid->get(ix, iy, iz);
+      32           1 :         return mean / Nx / Ny / Nz;
+      33             : }
+      34             : 
+      35           0 : double meanFieldStrength(ref_ptr<Grid3f> grid) {
+      36             :         size_t Nx = grid->getNx();
+      37             :         size_t Ny = grid->getNy();
+      38             :         size_t Nz = grid->getNz();
+      39             :         double mean = 0;
+      40           0 :         for (int ix = 0; ix < Nx; ix++)
+      41           0 :                 for (int iy = 0; iy < Ny; iy++)
+      42           0 :                         for (int iz = 0; iz < Nz; iz++)
+      43           0 :                                 mean += grid->get(ix, iy, iz).getR();
+      44           0 :         return mean / Nx / Ny / Nz;
+      45             : }
+      46             : 
+      47           0 : double meanFieldStrength(ref_ptr<Grid1f> grid) {
+      48             :         size_t Nx = grid->getNx();
+      49             :         size_t Ny = grid->getNy();
+      50             :         size_t Nz = grid->getNz();
+      51             :         double mean = 0;
+      52           0 :         for (int ix = 0; ix < Nx; ix++)
+      53           0 :                 for (int iy = 0; iy < Ny; iy++)
+      54           0 :                         for (int iz = 0; iz < Nz; iz++)
+      55           0 :                                 mean += grid->get(ix, iy, iz);
+      56           0 :         return mean / Nx / Ny / Nz;
+      57             : }
+      58             : 
+      59          11 : double rmsFieldStrength(ref_ptr<Grid3f> grid) {
+      60             :         size_t Nx = grid->getNx();
+      61             :         size_t Ny = grid->getNy();
+      62             :         size_t Nz = grid->getNz();
+      63             :         double sumV2 = 0;
+      64         715 :         for (int ix = 0; ix < Nx; ix++)
+      65       45760 :                 for (int iy = 0; iy < Ny; iy++)
+      66     2928640 :                         for (int iz = 0; iz < Nz; iz++)
+      67     2883584 :                                 sumV2 += grid->get(ix, iy, iz).getR2();
+      68          11 :         return std::sqrt(sumV2 / Nx / Ny / Nz);
+      69             : }
+      70             : 
+      71           0 : double rmsFieldStrength(ref_ptr<Grid1f> grid) {
+      72             :         size_t Nx = grid->getNx();
+      73             :         size_t Ny = grid->getNy();
+      74             :         size_t Nz = grid->getNz();
+      75             :         double sumV2 = 0;
+      76           0 :         for (int ix = 0; ix < Nx; ix++)
+      77           0 :                 for (int iy = 0; iy < Ny; iy++)
+      78           0 :                         for (int iz = 0; iz < Nz; iz++)
+      79           0 :                                 sumV2 += pow(grid->get(ix, iy, iz), 2);
+      80           0 :         return std::sqrt(sumV2 / Nx / Ny / Nz);
+      81             : }
+      82             : 
+      83           0 : std::array<float, 3> rmsFieldStrengthPerAxis(ref_ptr<Grid3f> grid) {
+      84             :     size_t Nx = grid->getNx();
+      85             :     size_t Ny = grid->getNy();
+      86             :     size_t Nz = grid->getNz();
+      87             :     float sumV2_x = 0;
+      88             :     float sumV2_y = 0;
+      89             :     float sumV2_z = 0;
+      90           0 :     for (int ix = 0; ix < Nx; ix++)
+      91           0 :         for (int iy = 0; iy < Ny; iy++)
+      92           0 :             for (int iz = 0; iz < Nz; iz++) {
+      93           0 :                 sumV2_x += pow(grid->get(ix, iy, iz).x, 2);
+      94           0 :                 sumV2_y += pow(grid->get(ix, iy, iz).y, 2);
+      95           0 :                 sumV2_z += pow(grid->get(ix, iy, iz).z, 2);
+      96             :             }
+      97             :     return {
+      98           0 :         std::sqrt(sumV2_x / Nx / Ny / Nz),
+      99           0 :         std::sqrt(sumV2_y / Nx / Ny / Nz),
+     100           0 :         std::sqrt(sumV2_z / Nx / Ny / Nz)
+     101           0 :     };
+     102             : }
+     103             : 
+     104           0 : void fromMagneticField(ref_ptr<Grid3f> grid, ref_ptr<MagneticField> field) {
+     105             :         Vector3d origin = grid->getOrigin();
+     106             :         Vector3d spacing = grid->getSpacing();
+     107             :         size_t Nx = grid->getNx();
+     108             :         size_t Ny = grid->getNy();
+     109             :         size_t Nz = grid->getNz();
+     110           0 :         for (size_t ix = 0; ix < Nx; ix++)
+     111           0 :                 for (size_t iy = 0; iy < Ny; iy++)
+     112           0 :                         for (size_t iz = 0; iz < Nz; iz++) {
+     113           0 :                                 Vector3d pos = Vector3d(double(ix) + 0.5, double(iy) + 0.5, double(iz) + 0.5) * spacing + origin;
+     114           0 :                                 Vector3d B = field->getField(pos);
+     115             :                                 grid->get(ix, iy, iz) = B;
+     116             :         }
+     117           0 : }
+     118             : 
+     119           0 : void fromMagneticFieldStrength(ref_ptr<Grid1f> grid, ref_ptr<MagneticField> field) {
+     120             :         Vector3d origin = grid->getOrigin();
+     121             :         Vector3d spacing = grid->getSpacing();
+     122             :         size_t Nx = grid->getNx();
+     123             :         size_t Ny = grid->getNy();
+     124             :         size_t Nz = grid->getNz();
+     125           0 :         for (size_t ix = 0; ix < Nx; ix++)
+     126           0 :                 for (size_t iy = 0; iy < Ny; iy++)
+     127           0 :                         for (size_t iz = 0; iz < Nz; iz++) {
+     128           0 :                                 Vector3d pos = Vector3d(double(ix) + 0.5, double(iy) + 0.5, double(iz) + 0.5) * spacing + origin;
+     129           0 :                                 double s = field->getField(pos).getR();
+     130           0 :                                 grid->get(ix, iy, iz) = s;
+     131             :         }
+     132           0 : }
+     133             : 
+     134           1 : void loadGrid(ref_ptr<Grid3f> grid, std::string filename, double c) {
+     135           1 :         std::ifstream fin(filename.c_str(), std::ios::binary);
+     136           1 :         if (!fin) {
+     137           0 :                 std::stringstream ss;
+     138           0 :                 ss << "load Grid3f: " << filename << " not found";
+     139           0 :                 throw std::runtime_error(ss.str());
+     140           0 :         }
+     141             : 
+     142             :         // get length of file and compare to size of grid
+     143           1 :         fin.seekg(0, fin.end);
+     144           1 :         size_t length = fin.tellg() / sizeof(float);
+     145           1 :         fin.seekg (0, fin.beg);
+     146             : 
+     147             :         size_t nx = grid->getNx();
+     148             :         size_t ny = grid->getNy();
+     149             :         size_t nz = grid->getNz();
+     150             : 
+     151           1 :         if (length != (3 * nx * ny * nz))
+     152           0 :                 throw std::runtime_error("loadGrid: file and grid size do not match");
+     153             : 
+     154           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     155          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     156          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     157             :                                 Vector3f &b = grid->get(ix, iy, iz);
+     158          27 :                                 fin.read((char*) &(b.x), sizeof(float));
+     159          27 :                                 fin.read((char*) &(b.y), sizeof(float));
+     160          27 :                                 fin.read((char*) &(b.z), sizeof(float));
+     161          27 :                                 b *= c;
+     162             :                         }
+     163             :                 }
+     164             :         }
+     165           1 :         fin.close();
+     166           1 : }
+     167             : 
+     168           0 : void loadGrid(ref_ptr<Grid1f> grid, std::string filename, double c) {
+     169           0 :         std::ifstream fin(filename.c_str(), std::ios::binary);
+     170           0 :         if (!fin) {
+     171           0 :                 std::stringstream ss;
+     172           0 :                 ss << "load Grid1f: " << filename << " not found";
+     173           0 :                 throw std::runtime_error(ss.str());
+     174           0 :         }
+     175             : 
+     176             :         // get length of file and compare to size of grid
+     177           0 :         fin.seekg(0, fin.end);
+     178           0 :         size_t length = fin.tellg() / sizeof(float);
+     179           0 :         fin.seekg (0, fin.beg);
+     180             : 
+     181             :         size_t nx = grid->getNx();
+     182             :         size_t ny = grid->getNy();
+     183             :         size_t nz = grid->getNz();
+     184             : 
+     185           0 :         if (length != (nx * ny * nz))
+     186           0 :                 throw std::runtime_error("loadGrid: file and grid size do not match");
+     187             : 
+     188           0 :         for (int ix = 0; ix < nx; ix++) {
+     189           0 :                 for (int iy = 0; iy < ny; iy++) {
+     190           0 :                         for (int iz = 0; iz < nz; iz++) {
+     191             :                                 float &b = grid->get(ix, iy, iz);
+     192           0 :                                 fin.read((char*) &b, sizeof(float));
+     193           0 :                                 b *= c;
+     194             :                         }
+     195             :                 }
+     196             :         }
+     197           0 :         fin.close();
+     198           0 : }
+     199             : 
+     200           1 : void dumpGrid(ref_ptr<Grid3f> grid, std::string filename, double c) {
+     201           1 :         std::ofstream fout(filename.c_str(), std::ios::binary);
+     202           1 :         if (!fout) {
+     203           0 :                 std::stringstream ss;
+     204           0 :                 ss << "dump Grid3f: " << filename << " not found";
+     205           0 :                 throw std::runtime_error(ss.str());
+     206           0 :         }
+     207           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     208          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     209          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     210          27 :                                 Vector3f b = grid->get(ix, iy, iz) * c;
+     211          27 :                                 fout.write((char*) &(b.x), sizeof(float));
+     212          27 :                                 fout.write((char*) &(b.y), sizeof(float));
+     213          27 :                                 fout.write((char*) &(b.z), sizeof(float));
+     214             :                         }
+     215             :                 }
+     216             :         }
+     217           1 :         fout.close();
+     218           1 : }
+     219             : 
+     220           0 : void dumpGrid(ref_ptr<Grid1f> grid, std::string filename, double c) {
+     221           0 :         std::ofstream fout(filename.c_str(), std::ios::binary);
+     222           0 :         if (!fout) {
+     223           0 :                 std::stringstream ss;
+     224           0 :                 ss << "dump Grid1f: " << filename << " not found";
+     225           0 :                 throw std::runtime_error(ss.str());
+     226           0 :         }
+     227           0 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     228           0 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     229           0 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     230           0 :                                 float b = grid->get(ix, iy, iz) * c;
+     231           0 :                                 fout.write((char*) &b, sizeof(float));
+     232             :                         }
+     233             :                 }
+     234             :         }
+     235           0 :         fout.close();
+     236           0 : }
+     237             : 
+     238           1 : void loadGridFromTxt(ref_ptr<Grid3f> grid, std::string filename, double c) {
+     239           1 :         std::ifstream fin(filename.c_str());
+     240           1 :         if (!fin) {
+     241           0 :                 std::stringstream ss;
+     242           0 :                 ss << "load Grid3f: " << filename << " not found";
+     243           0 :                 throw std::runtime_error(ss.str());
+     244           0 :         }
+     245             :         // skip header lines
+     246           1 :         while (fin.peek() == '#')
+     247           0 :                 fin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+     248             : 
+     249           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     250          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     251          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     252             :                                 Vector3f &b = grid->get(ix, iy, iz);
+     253          27 :                                 fin >> b.x >> b.y >> b.z;
+     254          27 :                                 b *= c;
+     255          27 :                                 if (fin.eof())
+     256           0 :                                         throw std::runtime_error("load Grid3f: file too short");
+     257             :                         }
+     258             :                 }
+     259             :         }
+     260           1 :         fin.close();
+     261           1 : }
+     262             : 
+     263           0 : void loadGridFromTxt(ref_ptr<Grid1f> grid, std::string filename, double c) {
+     264           0 :         std::ifstream fin(filename.c_str());
+     265           0 :         if (!fin) {
+     266           0 :                 std::stringstream ss;
+     267           0 :                 ss << "load Grid1f: " << filename << " not found";
+     268           0 :                 throw std::runtime_error(ss.str());
+     269           0 :         }
+     270             :         // skip header lines
+     271           0 :         while (fin.peek() == '#')
+     272           0 :                 fin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+     273             : 
+     274           0 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     275           0 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     276           0 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     277             :                                 float &b = grid->get(ix, iy, iz);
+     278             :                                 fin >> b;
+     279           0 :                                 b *= c;
+     280           0 :                                 if (fin.eof())
+     281           0 :                                         throw std::runtime_error("load Grid1f: file too short");
+     282             :                         }
+     283             :                 }
+     284             :         }
+     285           0 :         fin.close();
+     286           0 : }
+     287             : 
+     288           1 : void dumpGridToTxt(ref_ptr<Grid3f> grid, std::string filename, double c) {
+     289           1 :         std::ofstream fout(filename.c_str());
+     290           1 :         if (!fout) {
+     291           0 :                 std::stringstream ss;
+     292           0 :                 ss << "dump Grid3f: " << filename << " not found";
+     293           0 :                 throw std::runtime_error(ss.str());
+     294           0 :         }
+     295           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     296          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     297          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     298          27 :                                 Vector3f b = grid->get(ix, iy, iz) * c;
+     299          27 :                                 fout << b << "\n";
+     300             :                         }
+     301             :                 }
+     302             :         }
+     303           1 :         fout.close();
+     304           1 : }
+     305             : 
+     306           0 : void dumpGridToTxt(ref_ptr<Grid1f> grid, std::string filename, double c) {
+     307           0 :         std::ofstream fout(filename.c_str());
+     308           0 :         if (!fout) {
+     309           0 :                 std::stringstream ss;
+     310           0 :                 ss << "dump Grid1f: " << filename << " not found";
+     311           0 :                 throw std::runtime_error(ss.str());
+     312           0 :         }
+     313           0 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     314           0 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     315           0 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     316           0 :                                 float b = grid->get(ix, iy, iz) * c;
+     317           0 :                                 fout << b << "\n";
+     318             :                         }
+     319             :                 }
+     320             :         }
+     321           0 :         fout.close();
+     322           0 : }
+     323             : 
+     324             : #ifdef CRPROPA_HAVE_FFTW3F
+     325             : 
+     326           0 : std::vector<std::pair<int, float>> gridPowerSpectrum(ref_ptr<Grid3f> grid) {
+     327             : 
+     328           0 :   double rms = rmsFieldStrength(grid);
+     329             :   size_t n = grid->getNx(); // size of array
+     330             : 
+     331             :   // arrays to hold the complex vector components of the B(k)-field
+     332             :   fftwf_complex *Bkx, *Bky, *Bkz;
+     333           0 :   Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n);
+     334           0 :   Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n);
+     335           0 :   Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n);
+     336             : 
+     337             :   fftwf_complex *Bx = (fftwf_complex *)Bkx;
+     338             :   fftwf_complex *By = (fftwf_complex *)Bky;
+     339             :   fftwf_complex *Bz = (fftwf_complex *)Bkz;
+     340             : 
+     341             :   // save to temp
+     342             :   int i;
+     343           0 :   for (size_t ix = 0; ix < n; ix++) {
+     344           0 :     for (size_t iy = 0; iy < n; iy++) {
+     345           0 :       for (size_t iz = 0; iz < n; iz++) {
+     346           0 :         i = ix * n * n + iy * n + iz;
+     347             :         Vector3<float> &b = grid->get(ix, iy, iz);
+     348           0 :         Bx[i][0] = b.x / rms;
+     349           0 :         By[i][0] = b.y / rms;
+     350           0 :         Bz[i][0] = b.z / rms;
+     351             :       }
+     352             :     }
+     353             :   }
+     354             : 
+     355             :   // in-place, real to complex, inverse Fourier transformation on each component
+     356             :   // note that the last elements of B(x) are unused now
+     357             :   fftwf_plan plan_x =
+     358           0 :       fftwf_plan_dft_3d(n, n, n, Bx, Bkx, FFTW_FORWARD, FFTW_ESTIMATE);
+     359           0 :   fftwf_execute(plan_x);
+     360           0 :   fftwf_destroy_plan(plan_x);
+     361             : 
+     362             :   fftwf_plan plan_y =
+     363           0 :       fftwf_plan_dft_3d(n, n, n, By, Bky, FFTW_FORWARD, FFTW_ESTIMATE);
+     364           0 :   fftwf_execute(plan_y);
+     365           0 :   fftwf_destroy_plan(plan_y);
+     366             : 
+     367             :   fftwf_plan plan_z =
+     368           0 :       fftwf_plan_dft_3d(n, n, n, Bz, Bkz, FFTW_FORWARD, FFTW_ESTIMATE);
+     369           0 :   fftwf_execute(plan_z);
+     370           0 :   fftwf_destroy_plan(plan_z);
+     371             : 
+     372             :   float power;
+     373             :   std::map<size_t, std::pair<float, int>> spectrum;
+     374             :   int k;
+     375             : 
+     376           0 :   for (size_t ix = 0; ix < n; ix++) {
+     377           0 :     for (size_t iy = 0; iy < n; iy++) {
+     378           0 :       for (size_t iz = 0; iz < n; iz++) {
+     379           0 :         i = ix * n * n + iy * n + iz;
+     380           0 :         k = static_cast<int>(
+     381           0 :             std::floor(std::sqrt(ix * ix + iy * iy + iz * iz)));
+     382           0 :         if (k > n / 2. || k == 0)
+     383           0 :           continue;
+     384           0 :         power = ((Bkx[i][0] * Bkx[i][0] + Bkx[i][1] * Bkx[i][1]) +
+     385           0 :                  (Bky[i][0] * Bky[i][0] + Bky[i][1] * Bky[i][1]) +
+     386           0 :                  (Bkz[i][0] * Bkz[i][0] + Bkz[i][1] * Bkz[i][1]));
+     387           0 :         if (spectrum.find(k) == spectrum.end()) {
+     388           0 :           spectrum[k].first = power;
+     389           0 :           spectrum[k].second = 1;
+     390             :         } else {
+     391           0 :           spectrum[k].first += power;
+     392           0 :           spectrum[k].second += 1;
+     393             :         }
+     394             :       }
+     395             :     }
+     396             :   }
+     397             : 
+     398           0 :   fftwf_free(Bkx);
+     399           0 :   fftwf_free(Bky);
+     400           0 :   fftwf_free(Bkz);
+     401             : 
+     402             :   std::vector<std::pair<int, float>> points;
+     403           0 :   for (std::map<size_t, std::pair<float, int>>::iterator it = spectrum.begin();
+     404           0 :        it != spectrum.end(); ++it) {
+     405           0 :     points.push_back(
+     406           0 :         std::make_pair(it->first, (it->second).first / (it->second).second));
+     407             :   }
+     408             : 
+     409           0 :   return points;
+     410             : }
+     411             : 
+     412             : #endif // CRPROPA_HAVE_FFTW3F
+     413             : 
+     414             : 
+     415             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Module.cpp.func-sort-c.html b/doc/coverageReport/src/Module.cpp.func-sort-c.html new file mode 100644 index 000000000..16f3b25e6 --- /dev/null +++ b/doc/coverageReport/src/Module.cpp.func-sort-c.html @@ -0,0 +1,120 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Module.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Module.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:374877.1 %
Date:2024-04-08 14:58:22Functions:91275.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17AbstractCondition13setAcceptFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_0
_ZN7crpropa17AbstractCondition23setMakeAcceptedInactiveEb0
_ZNK7crpropa6Module14getDescriptionB5cxx11Ev0
_ZN7crpropa17AbstractCondition13setRejectFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_1
_ZN7crpropa17AbstractCondition23setMakeRejectedInactiveEb1
_ZN7crpropa17AbstractCondition8onAcceptEPNS_6ModuleE1
_ZN7crpropa17AbstractCondition8onRejectEPNS_6ModuleE1
_ZNK7crpropa17AbstractCondition6acceptEPNS_9CandidateE2
_ZN7crpropa17AbstractConditionC2Ev33
_ZN7crpropa6ModuleC2Ev209
_ZN7crpropa6Module14setDescriptionERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE365
_ZNK7crpropa17AbstractCondition6rejectEPNS_9CandidateE1126
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Module.cpp.func.html b/doc/coverageReport/src/Module.cpp.func.html new file mode 100644 index 000000000..b0c8fb43e --- /dev/null +++ b/doc/coverageReport/src/Module.cpp.func.html @@ -0,0 +1,120 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Module.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Module.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:374877.1 %
Date:2024-04-08 14:58:22Functions:91275.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17AbstractCondition13setAcceptFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_0
_ZN7crpropa17AbstractCondition13setRejectFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_1
_ZN7crpropa17AbstractCondition23setMakeAcceptedInactiveEb0
_ZN7crpropa17AbstractCondition23setMakeRejectedInactiveEb1
_ZN7crpropa17AbstractCondition8onAcceptEPNS_6ModuleE1
_ZN7crpropa17AbstractCondition8onRejectEPNS_6ModuleE1
_ZN7crpropa17AbstractConditionC2Ev33
_ZN7crpropa6Module14setDescriptionERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE365
_ZN7crpropa6ModuleC2Ev209
_ZNK7crpropa17AbstractCondition6acceptEPNS_9CandidateE2
_ZNK7crpropa17AbstractCondition6rejectEPNS_9CandidateE1126
_ZNK7crpropa6Module14getDescriptionB5cxx11Ev0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Module.cpp.gcov.html b/doc/coverageReport/src/Module.cpp.gcov.html new file mode 100644 index 000000000..3dc4592a3 --- /dev/null +++ b/doc/coverageReport/src/Module.cpp.gcov.html @@ -0,0 +1,156 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Module.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Module.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:374877.1 %
Date:2024-04-08 14:58:22Functions:91275.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Module.h"
+       2             : 
+       3             : #include <typeinfo>
+       4             : 
+       5             : namespace crpropa {
+       6             : 
+       7         209 : Module::Module() {
+       8             :         const std::type_info &info = typeid(*this);
+       9         209 :         setDescription(info.name());
+      10         209 : }
+      11             : 
+      12           0 : std::string Module::getDescription() const {
+      13           0 :         return description;
+      14             : }
+      15             : 
+      16         365 : void Module::setDescription(const std::string &d) {
+      17         365 :         description = d;
+      18         365 : }
+      19             : 
+      20          33 : AbstractCondition::AbstractCondition() :
+      21          33 :                 makeRejectedInactive(true), makeAcceptedInactive(false), rejectFlagKey(
+      22          33 :                                 "Rejected") {
+      23             : 
+      24          33 : }
+      25             : 
+      26        1126 : void AbstractCondition::reject(Candidate *candidate) const {
+      27        1126 :         if (!candidate)
+      28             :                 return;
+      29             : 
+      30        1126 :         if (rejectAction.valid())
+      31           5 :                 rejectAction->process(candidate);
+      32             : 
+      33        1126 :         if (!rejectFlagKey.empty())
+      34        1126 :                 candidate->setProperty(rejectFlagKey, rejectFlagValue);
+      35             : 
+      36        1126 :         if (makeRejectedInactive)
+      37        1125 :                 candidate->setActive(false);
+      38             : }
+      39             : 
+      40           2 : void AbstractCondition::accept(Candidate *candidate) const {
+      41           2 :         if (!candidate)
+      42             :                 return;
+      43             : 
+      44           2 :         if (acceptAction.valid())
+      45           2 :                 acceptAction->process(candidate);
+      46             : 
+      47           2 :         if (!acceptFlagKey.empty())
+      48           0 :                 candidate->setProperty(acceptFlagKey, acceptFlagValue);
+      49             : 
+      50           2 :         if (makeAcceptedInactive)
+      51           0 :                 candidate->setActive(false);
+      52             : }
+      53             : 
+      54           1 : void AbstractCondition::setMakeRejectedInactive(bool deactivate) {
+      55           1 :         makeRejectedInactive = deactivate;
+      56           1 : }
+      57             : 
+      58           0 : void AbstractCondition::setMakeAcceptedInactive(bool deactivate) {
+      59           0 :         makeAcceptedInactive = deactivate;
+      60           0 : }
+      61             : 
+      62           1 : void AbstractCondition::onReject(Module *action) {
+      63           1 :         rejectAction = action;
+      64           1 : }
+      65             : 
+      66           1 : void AbstractCondition::onAccept(Module *action) {
+      67           1 :         acceptAction = action;
+      68           1 : }
+      69             : 
+      70           1 : void AbstractCondition::setRejectFlag(std::string key, std::string value) {
+      71           1 :         rejectFlagKey = key;
+      72           1 :         rejectFlagValue = value;
+      73           1 : }
+      74             : 
+      75           0 : void AbstractCondition::setAcceptFlag(std::string key, std::string value) {
+      76           0 :         acceptFlagKey = key;
+      77           0 :         acceptFlagValue = value;
+      78           0 : }
+      79             : 
+      80             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleID.cpp.func-sort-c.html b/doc/coverageReport/src/ParticleID.cpp.func-sort-c.html new file mode 100644 index 000000000..02a39f19f --- /dev/null +++ b/doc/coverageReport/src/ParticleID.cpp.func-sort-c.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleID.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleID.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:163053.3 %
Date:2024-04-08 14:58:22Functions:4580.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15convertIdToNameB5cxx11Ei0
_ZN7crpropa9nucleusIdEii45149
_ZN7crpropa10massNumberEi202819
_ZN7crpropa12chargeNumberEi364529
_ZN7crpropa9isNucleusEi20370056
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleID.cpp.func.html b/doc/coverageReport/src/ParticleID.cpp.func.html new file mode 100644 index 000000000..70f77a588 --- /dev/null +++ b/doc/coverageReport/src/ParticleID.cpp.func.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleID.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleID.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:163053.3 %
Date:2024-04-08 14:58:22Functions:4580.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10massNumberEi202819
_ZN7crpropa12chargeNumberEi364529
_ZN7crpropa15convertIdToNameB5cxx11Ei0
_ZN7crpropa9isNucleusEi20370056
_ZN7crpropa9nucleusIdEii45149
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleID.cpp.gcov.html b/doc/coverageReport/src/ParticleID.cpp.gcov.html new file mode 100644 index 000000000..917e4a925 --- /dev/null +++ b/doc/coverageReport/src/ParticleID.cpp.gcov.html @@ -0,0 +1,130 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleID.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleID.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:163053.3 %
Date:2024-04-08 14:58:22Functions:4580.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/ParticleID.h"
+       2             : 
+       3             : #include "HepPID/ParticleIDMethods.hh"
+       4             : #include "HepPID/ParticleName.hh"
+       5             : #include "kiss/convert.h"
+       6             : 
+       7             : #include <string>
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11       45149 : int nucleusId(int a, int z) {
+      12       45149 :         if (z < 0)
+      13           0 :                 throw std::runtime_error(
+      14           0 :                                 "crpropa::Nucleus: no nucleus with Z < 0, A=" + kiss::str(a) + " Z="
+      15           0 :                                                 + kiss::str(z));
+      16       45149 :         if (a < 1)
+      17           0 :                 throw std::runtime_error(
+      18           0 :                                 "crpropa::Nucleus: no nucleus with A < 1, A=" + kiss::str(a) + " Z="
+      19           0 :                                                 + kiss::str(z));
+      20       45149 :         if (a < z)
+      21           1 :                 throw std::runtime_error(
+      22           2 :                                 "crpropa::Nucleus: no nucleus with A < Z, A=" + kiss::str(a) + " Z="
+      23           4 :                                                 + kiss::str(z));
+      24       45148 :         return 1000000000 + z * 10000 + a * 10;
+      25             : }
+      26             : 
+      27      364529 : int chargeNumber(int id) {
+      28      364529 :         return HepPID::Z(id);
+      29             : }
+      30             : 
+      31      202819 : int massNumber(int id) {
+      32      202819 :         if (id == 2112)
+      33             :                 return 1;
+      34      202818 :         return HepPID::A(id);
+      35             : }
+      36             : 
+      37    20370056 : bool isNucleus(int id) {
+      38    20370056 :         if (id == 2112)
+      39             :                 return true; // consider neutron as nucleus
+      40    20370056 :         return HepPID::isNucleus(id);
+      41             : }
+      42             : 
+      43           0 : std::string convertIdToName(int id) {
+      44             :         // handle a few extra cases that HepPID doesn't like
+      45           0 :         if (id == 1000000010) // neutron
+      46           0 :                 id = 2112;
+      47           0 :         if (id == -1000000010) // anti-neutron
+      48           0 :                 id = -2112;
+      49           0 :         if (id == -1000010010) // anti-proton
+      50           0 :                 id = -2212;
+      51           0 :         return HepPID::particleName(id);
+      52             : }
+      53             : 
+      54             : }
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html b/doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html new file mode 100644 index 000000000..684f8b4f6 --- /dev/null +++ b/doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleMass.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleMass.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:303196.8 %
Date:2024-04-08 14:58:22Functions:44100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16NuclearMassTable4initEv12
_ZN7crpropa11nuclearMassEi161184
_ZN7crpropa16NuclearMassTable7getMassEm161208
_ZN7crpropa11nuclearMassEii161209
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleMass.cpp.func.html b/doc/coverageReport/src/ParticleMass.cpp.func.html new file mode 100644 index 000000000..f0fe27c62 --- /dev/null +++ b/doc/coverageReport/src/ParticleMass.cpp.func.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleMass.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleMass.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:303196.8 %
Date:2024-04-08 14:58:22Functions:44100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11nuclearMassEi161184
_ZN7crpropa11nuclearMassEii161209
_ZN7crpropa16NuclearMassTable4initEv12
_ZN7crpropa16NuclearMassTable7getMassEm161208
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleMass.cpp.gcov.html b/doc/coverageReport/src/ParticleMass.cpp.gcov.html new file mode 100644 index 000000000..22315606f --- /dev/null +++ b/doc/coverageReport/src/ParticleMass.cpp.gcov.html @@ -0,0 +1,150 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleMass.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleMass.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:303196.8 %
Date:2024-04-08 14:58:22Functions:44100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/ParticleMass.h"
+       2             : #include "crpropa/ParticleID.h"
+       3             : #include "crpropa/Common.h"
+       4             : #include "crpropa/Units.h"
+       5             : 
+       6             : #include "kiss/convert.h"
+       7             : #include "kiss/logger.h"
+       8             : 
+       9             : #include <vector>
+      10             : #include <fstream>
+      11             : #include <stdexcept>
+      12             : #include <limits>
+      13             : 
+      14             : namespace crpropa {
+      15             : 
+      16             : struct NuclearMassTable {
+      17             :         bool initialized;
+      18             :         std::vector<double> table;
+      19             : 
+      20             :         NuclearMassTable() {
+      21             :                 initialized = false;
+      22             :         }
+      23             : 
+      24          12 :         void init() {
+      25          24 :                 std::string filename = getDataPath("nuclear_mass.txt");
+      26          12 :                 std::ifstream infile(filename.c_str());
+      27             : 
+      28          12 :                 if (!infile.good())
+      29           0 :                         throw std::runtime_error("crpropa: could not open file " + filename);
+      30             : 
+      31             :                 int Z, N;
+      32             :                 double mass;
+      33       10092 :                 while (infile.good()) {
+      34       10080 :                         if (infile.peek() != '#') {
+      35       10056 :                                 infile >> Z >> N >> mass;
+      36       10056 :                                 table.push_back(mass);
+      37             :                         }
+      38       10080 :                         infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+      39             :                 }
+      40             : 
+      41          12 :                 infile.close();
+      42          12 :                 initialized = true;
+      43          24 :         }
+      44             : 
+      45      161208 :         double getMass(std::size_t idx) {
+      46      161208 :                 if (!initialized) {
+      47          12 : #pragma omp critical(init)
+      48          12 :                         init();
+      49             :                 }
+      50      161208 :                 return table[idx];
+      51             :         }
+      52             : };
+      53             : 
+      54             : static NuclearMassTable nuclearMassTable;
+      55             : 
+      56      161184 : double nuclearMass(int id) {
+      57      161184 :         int A = massNumber(id);
+      58      161184 :         int Z = chargeNumber(id);
+      59      161184 :         return nuclearMass(A, Z);
+      60             : }
+      61             : 
+      62      161209 : double nuclearMass(int A, int Z) {
+      63      161209 :         if ((A < 1) or (A > 56) or (Z < 0) or (Z > 26) or (Z > A)) {
+      64           2 :                 KISS_LOG_WARNING <<
+      65           1 :                 "nuclearMass: nuclear mass not found in the mass table for " <<
+      66           1 :                 "A = " << A << ", Z = " << Z << ". " <<
+      67           1 :                 "Approximated value used A * amu - Z * m_e instead.";
+      68           1 :                 return A * amu - Z * mass_electron;
+      69             :         }
+      70      161208 :         int N = A - Z;
+      71      161208 :         return nuclearMassTable.getMass(Z * 31 + N);
+      72             : }
+      73             : 
+      74             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleState.cpp.func-sort-c.html b/doc/coverageReport/src/ParticleState.cpp.func-sort-c.html new file mode 100644 index 000000000..c6897830a --- /dev/null +++ b/doc/coverageReport/src/ParticleState.cpp.func-sort-c.html @@ -0,0 +1,140 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleState.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleState.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:485685.7 %
Date:2024-04-08 14:58:22Functions:161794.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13ParticleState14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ParticleState11getRigidityEv1
_ZNK7crpropa13ParticleState11getVelocityEv1
_ZNK7crpropa13ParticleState11getMomentumEv2
_ZNK7crpropa13ParticleState7getMassEv4
_ZN7crpropa13ParticleState16setLorentzFactorEd15420
_ZNK7crpropa13ParticleState16getLorentzFactorEv33182
_ZNK7crpropa13ParticleState5getIdEv290682
_ZNK7crpropa13ParticleState12getDirectionEv500446
_ZNK7crpropa13ParticleState9getEnergyEv603581
_ZNK7crpropa13ParticleState9getChargeEv960335
_ZNK7crpropa13ParticleState11getPositionEv12488919
_ZN7crpropa13ParticleStateC2EidNS_7Vector3IdEES2_16844401
_ZN7crpropa13ParticleState12setDirectionERKNS_7Vector3IdEE17329639
_ZN7crpropa13ParticleState5setIdEi20314515
_ZN7crpropa13ParticleState9setEnergyEd20322799
_ZN7crpropa13ParticleState11setPositionERKNS_7Vector3IdEE24114998
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleState.cpp.func.html b/doc/coverageReport/src/ParticleState.cpp.func.html new file mode 100644 index 000000000..2ad881fd0 --- /dev/null +++ b/doc/coverageReport/src/ParticleState.cpp.func.html @@ -0,0 +1,140 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleState.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleState.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:485685.7 %
Date:2024-04-08 14:58:22Functions:161794.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13ParticleState11setPositionERKNS_7Vector3IdEE24114998
_ZN7crpropa13ParticleState12setDirectionERKNS_7Vector3IdEE17329639
_ZN7crpropa13ParticleState16setLorentzFactorEd15420
_ZN7crpropa13ParticleState5setIdEi20314515
_ZN7crpropa13ParticleState9setEnergyEd20322799
_ZN7crpropa13ParticleStateC2EidNS_7Vector3IdEES2_16844401
_ZNK7crpropa13ParticleState11getMomentumEv2
_ZNK7crpropa13ParticleState11getPositionEv12488919
_ZNK7crpropa13ParticleState11getRigidityEv1
_ZNK7crpropa13ParticleState11getVelocityEv1
_ZNK7crpropa13ParticleState12getDirectionEv500446
_ZNK7crpropa13ParticleState14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ParticleState16getLorentzFactorEv33182
_ZNK7crpropa13ParticleState5getIdEv290682
_ZNK7crpropa13ParticleState7getMassEv4
_ZNK7crpropa13ParticleState9getChargeEv960335
_ZNK7crpropa13ParticleState9getEnergyEv603581
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ParticleState.cpp.gcov.html b/doc/coverageReport/src/ParticleState.cpp.gcov.html new file mode 100644 index 000000000..34ba83680 --- /dev/null +++ b/doc/coverageReport/src/ParticleState.cpp.gcov.html @@ -0,0 +1,178 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ParticleState.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ParticleState.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:485685.7 %
Date:2024-04-08 14:58:22Functions:161794.1 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/ParticleState.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Common.h"
+       4             : #include "crpropa/ParticleID.h"
+       5             : #include "crpropa/ParticleMass.h"
+       6             : 
+       7             : #include "HepPID/ParticleIDMethods.hh"
+       8             : 
+       9             : #include <cstdlib>
+      10             : #include <sstream>
+      11             : 
+      12             : namespace crpropa {
+      13             : 
+      14    16844401 : ParticleState::ParticleState(int id, double E, Vector3d pos, Vector3d dir): id(0), energy(0.), position(0.), direction(0.), pmass(0.), charge(0.)
+      15             : {
+      16    16844401 :         setId(id);
+      17    16844401 :         setEnergy(E);
+      18    16844401 :         setPosition(pos);
+      19    16844401 :         setDirection(dir);
+      20    16844401 : }
+      21             : 
+      22    24114998 : void ParticleState::setPosition(const Vector3d &pos) {
+      23             :         position = pos;
+      24    24114998 : }
+      25             : 
+      26    12488919 : const Vector3d &ParticleState::getPosition() const {
+      27    12488919 :         return position;
+      28             : }
+      29             : 
+      30    17329639 : void ParticleState::setDirection(const Vector3d &dir) {
+      31             :         direction = dir / dir.getR();
+      32    17329639 : }
+      33             : 
+      34      500446 : const Vector3d &ParticleState::getDirection() const {
+      35      500446 :         return direction;
+      36             : }
+      37             : 
+      38    20322799 : void ParticleState::setEnergy(double newEnergy) {
+      39    20322799 :         energy = std::max(0., newEnergy); // prevent negative energies
+      40    20322799 : }
+      41             : 
+      42      603581 : double ParticleState::getEnergy() const {
+      43      603581 :         return energy;
+      44             : }
+      45             : 
+      46           1 : double ParticleState::getRigidity() const {
+      47           1 :         return fabs(energy / charge);
+      48             : }
+      49             : 
+      50    20314515 : void ParticleState::setId(int newId) {
+      51    20314515 :         id = newId;
+      52    20314515 :         if (isNucleus(id)) {
+      53      146261 :                 pmass = nuclearMass(id);
+      54      146261 :                 charge = chargeNumber(id) * eplus;
+      55      146261 :                 if (id < 0)
+      56           4 :                         charge *= -1; // anti-nucleus
+      57             :         } else {
+      58    20168254 :                 if (abs(id) == 11)
+      59       15064 :                         pmass = mass_electron;
+      60    20168254 :                 charge = HepPID::charge(id) * eplus;
+      61             :         }
+      62    20314515 : }
+      63             : 
+      64      290682 : int ParticleState::getId() const {
+      65      290682 :         return id;
+      66             : }
+      67             : 
+      68           4 : double ParticleState::getMass() const {
+      69           4 :         return pmass;
+      70             : }
+      71             : 
+      72      960335 : double ParticleState::getCharge() const {
+      73      960335 :         return charge;
+      74             : }
+      75             : 
+      76       33182 : double ParticleState::getLorentzFactor() const {
+      77       33182 :         return energy / (pmass * c_squared);
+      78             : }
+      79             : 
+      80       15420 : void ParticleState::setLorentzFactor(double lf) {
+      81       15420 :         lf = std::max(0., lf); // prevent negative Lorentz factors
+      82       15420 :         energy = lf * pmass * c_squared;
+      83       15420 : }
+      84             : 
+      85           1 : Vector3d ParticleState::getVelocity() const {
+      86           1 :         return direction * c_light;
+      87             : }
+      88             : 
+      89           2 : Vector3d ParticleState::getMomentum() const {
+      90           2 :         return direction * (energy / c_light);
+      91             : }
+      92             : 
+      93           0 : std::string ParticleState::getDescription() const {
+      94           0 :         std::stringstream ss;
+      95           0 :         ss << "Particle " << id << ", ";
+      96           0 :         ss << "E = " << energy / EeV << " EeV, ";
+      97           0 :         ss << "x = " << position / Mpc << " Mpc, ";
+      98           0 :         ss << "p = " << direction;
+      99           0 :         return ss.str();
+     100           0 : }
+     101             : 
+     102             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html b/doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html new file mode 100644 index 000000000..eca58f129 --- /dev/null +++ b/doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html @@ -0,0 +1,132 @@ + + + + + + + LCOV - coverage.info.cleaned - src/PhotonBackground.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - PhotonBackground.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8812073.3 %
Date:2024-04-08 14:58:22Functions:121580.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20BlackbodyPhotonField11setQuantileEd0
_ZNK7crpropa18TabularPhotonField22getMaximumPhotonEnergyEd0
_ZNK7crpropa18TabularPhotonField22getMinimumPhotonEnergyEd0
_ZNK7crpropa20BlackbodyPhotonField22getMaximumPhotonEnergyEd29
_ZNK7crpropa20BlackbodyPhotonField22getMinimumPhotonEnergyEd29
_ZN7crpropa20BlackbodyPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd40
_ZN7crpropa18TabularPhotonField12readRedshiftENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE73
_ZN7crpropa18TabularPhotonField19initRedshiftScalingEv73
_ZN7crpropa18TabularPhotonField16readPhotonEnergyENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonField17readPhotonDensityENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEb94
_ZNK7crpropa18TabularPhotonField14checkInputDataEv94
_ZNK7crpropa20BlackbodyPhotonField16getPhotonDensityEdd10689
_ZNK7crpropa18TabularPhotonField18getRedshiftScalingEd16757
_ZNK7crpropa18TabularPhotonField16getPhotonDensityEdd9536930
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/PhotonBackground.cpp.func.html b/doc/coverageReport/src/PhotonBackground.cpp.func.html new file mode 100644 index 000000000..c0525218b --- /dev/null +++ b/doc/coverageReport/src/PhotonBackground.cpp.func.html @@ -0,0 +1,132 @@ + + + + + + + LCOV - coverage.info.cleaned - src/PhotonBackground.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - PhotonBackground.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8812073.3 %
Date:2024-04-08 14:58:22Functions:121580.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18TabularPhotonField12readRedshiftENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE73
_ZN7crpropa18TabularPhotonField16readPhotonEnergyENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonField17readPhotonDensityENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonField19initRedshiftScalingEv73
_ZN7crpropa18TabularPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEb94
_ZN7crpropa20BlackbodyPhotonField11setQuantileEd0
_ZN7crpropa20BlackbodyPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd40
_ZNK7crpropa18TabularPhotonField14checkInputDataEv94
_ZNK7crpropa18TabularPhotonField16getPhotonDensityEdd9536930
_ZNK7crpropa18TabularPhotonField18getRedshiftScalingEd16757
_ZNK7crpropa18TabularPhotonField22getMaximumPhotonEnergyEd0
_ZNK7crpropa18TabularPhotonField22getMinimumPhotonEnergyEd0
_ZNK7crpropa20BlackbodyPhotonField16getPhotonDensityEdd10689
_ZNK7crpropa20BlackbodyPhotonField22getMaximumPhotonEnergyEd29
_ZNK7crpropa20BlackbodyPhotonField22getMinimumPhotonEnergyEd29
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/PhotonBackground.cpp.gcov.html b/doc/coverageReport/src/PhotonBackground.cpp.gcov.html new file mode 100644 index 000000000..7d90ae0f2 --- /dev/null +++ b/doc/coverageReport/src/PhotonBackground.cpp.gcov.html @@ -0,0 +1,291 @@ + + + + + + + LCOV - coverage.info.cleaned - src/PhotonBackground.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - PhotonBackground.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8812073.3 %
Date:2024-04-08 14:58:22Functions:121580.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/PhotonBackground.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #include "kiss/logger.h"
+       6             : 
+       7             : #include <fstream>
+       8             : #include <stdexcept>
+       9             : #include <limits>
+      10             : #include <cmath>
+      11             : 
+      12             : namespace crpropa {
+      13             : 
+      14          94 : TabularPhotonField::TabularPhotonField(std::string fieldName, bool isRedshiftDependent) {
+      15          94 :         this->fieldName = fieldName;
+      16          94 :         this->isRedshiftDependent = isRedshiftDependent;
+      17             : 
+      18         188 :         readPhotonEnergy(getDataPath("") + "Scaling/" + this->fieldName + "_photonEnergy.txt");
+      19         188 :         readPhotonDensity(getDataPath("") + "Scaling/" + this->fieldName + "_photonDensity.txt");
+      20          94 :         if (this->isRedshiftDependent)
+      21         146 :                 readRedshift(getDataPath("") + "Scaling/" + this->fieldName + "_redshift.txt");
+      22             : 
+      23          94 :         checkInputData();
+      24             : 
+      25          94 :         if (this->isRedshiftDependent)
+      26          73 :                 initRedshiftScaling();
+      27          94 : }
+      28             : 
+      29             : 
+      30     9536930 : double TabularPhotonField::getPhotonDensity(double Ephoton, double z) const {   
+      31     9536930 :         if ((this->isRedshiftDependent)) {
+      32             :                 // fix behaviour for future redshift. See issue #414
+      33             :                 // with redshift < 0 the photon density is set to 0 in interpolate2d. 
+      34             :                 // Therefore it is assumed that the photon density does not change from values at z = 0. This is only valid for small changes in redshift.
+      35     9536930 :                 double zMin = this->redshifts[0];
+      36     9536930 :                 if(z < zMin){
+      37           0 :                         if(z < -1) {
+      38           0 :                                 KISS_LOG_WARNING << "Photon Field " << fieldName << " uses FutureRedshift with z < -1. The photon density is set to n(Ephoton, z=0). \n";
+      39             :                         }
+      40           0 :                         return getPhotonDensity(Ephoton, zMin);
+      41             :                 } else {
+      42     9536930 :                         return interpolate2d(Ephoton, z, this->photonEnergies, this->redshifts, this->photonDensity);
+      43             :                 }
+      44             :         } else {
+      45           0 :                 return interpolate(Ephoton, this->photonEnergies, this->photonDensity);
+      46             :         }
+      47             : }
+      48             : 
+      49             : 
+      50       16757 : double TabularPhotonField::getRedshiftScaling(double z) const {
+      51       16757 :         if (!this->isRedshiftDependent)
+      52             :                 return 1.;
+      53             :  
+      54       16573 :         if (z < this->redshifts.front())
+      55             :                 return 1.;
+      56             :  
+      57       16573 :         if (z > this->redshifts.back())
+      58             :                 return 0.;
+      59             :  
+      60       16573 :         return interpolate(z, this->redshifts, this->redshiftScalings);
+      61             : }
+      62             : 
+      63           0 : double TabularPhotonField::getMinimumPhotonEnergy(double z) const{
+      64           0 :         return photonEnergies[0];
+      65             : }
+      66             : 
+      67           0 : double TabularPhotonField::getMaximumPhotonEnergy(double z) const{
+      68           0 :         return photonEnergies[photonEnergies.size() -1];
+      69             : }
+      70             : 
+      71          94 : void TabularPhotonField::readPhotonEnergy(std::string filePath) {
+      72          94 :         std::ifstream infile(filePath.c_str());
+      73          94 :         if (!infile.good())
+      74           0 :                 throw std::runtime_error("TabularPhotonField::readPhotonEnergy: could not open " + filePath);
+      75             : 
+      76             :         std::string line;
+      77       15320 :         while (std::getline(infile, line)) {
+      78       15226 :                 if ((line.size() > 0) & (line[0] != '#') )
+      79       14944 :                         this->photonEnergies.push_back(std::stod(line));
+      80             :         }
+      81          94 :         infile.close();
+      82          94 : }
+      83             : 
+      84          94 : void TabularPhotonField::readPhotonDensity(std::string filePath) {
+      85          94 :         std::ifstream infile(filePath.c_str());
+      86          94 :         if (!infile.good())
+      87           0 :                 throw std::runtime_error("TabularPhotonField::readPhotonDensity: could not open " + filePath);
+      88             : 
+      89             :         std::string line;
+      90     4772519 :         while (std::getline(infile, line)) {
+      91     4772425 :                 if ((line.size() > 0) & (line[0] != '#') )
+      92     4772143 :                         this->photonDensity.push_back(std::stod(line));
+      93             :         }
+      94          94 :         infile.close();
+      95          94 : }
+      96             : 
+      97          73 : void TabularPhotonField::readRedshift(std::string filePath) {
+      98          73 :         std::ifstream infile(filePath.c_str());
+      99          73 :         if (!infile.good())
+     100           0 :                 throw std::runtime_error("TabularPhotonField::initRedshift: could not open " + filePath);
+     101             : 
+     102             :         std::string line;
+     103       14599 :         while (std::getline(infile, line)) {
+     104       14526 :                 if ((line.size() > 0) & (line[0] != '#') )
+     105       14307 :                         this->redshifts.push_back(std::stod(line));
+     106             :         }
+     107          73 :         infile.close();
+     108          73 : }
+     109             : 
+     110          73 : void TabularPhotonField::initRedshiftScaling() {
+     111             :         double n0 = 0.;
+     112       14380 :         for (int i = 0; i < this->redshifts.size(); ++i) {
+     113       14307 :                 double z = this->redshifts[i];
+     114             :                 double n = 0.;
+     115     4770022 :                 for (int j = 0; j < this->photonEnergies.size()-1; ++j) {
+     116     4755715 :                         double e_j = this->photonEnergies[j];
+     117     4755715 :                         double e_j1 = this->photonEnergies[j+1];
+     118     4755715 :                         double deltaLogE = std::log10(e_j1) - std::log10(e_j);
+     119     4755715 :                         if (z == 0.)
+     120       12750 :                                 n0 += (getPhotonDensity(e_j, 0) + getPhotonDensity(e_j1, 0)) / 2. * deltaLogE;
+     121     4755715 :                         n += (getPhotonDensity(e_j, z) + getPhotonDensity(e_j1, z)) / 2. * deltaLogE;
+     122             :                 }
+     123       14307 :                 this->redshiftScalings.push_back(n / n0);
+     124             :         }
+     125          73 : }
+     126             : 
+     127          94 : void TabularPhotonField::checkInputData() const {
+     128          94 :         if (this->isRedshiftDependent) {
+     129          73 :                 if (this->photonDensity.size() != this->photonEnergies.size() * this-> redshifts.size())
+     130           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: length of photon density input is unequal to length of photon energy input times length of redshift input");
+     131             :         } else {
+     132          21 :                 if (this->photonEnergies.size() != this->photonDensity.size())
+     133           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: length of photon energy input is unequal to length of photon density input");
+     134             :         }
+     135             : 
+     136       15038 :         for (int i = 0; i < this->photonEnergies.size(); ++i) {
+     137             :                 double ePrevious = 0.;
+     138       14944 :                 double e = this->photonEnergies[i];
+     139       14944 :                 if (e <= 0.)
+     140           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: a value in the photon energy input is not positive");
+     141             :                 if (e <= ePrevious)
+     142             :                         throw std::runtime_error("TabularPhotonField::checkInputData: photon energy values are not strictly increasing");
+     143             :                 ePrevious = e;
+     144             :         }
+     145             : 
+     146     4772237 :         for (int i = 0; i < this->photonDensity.size(); ++i) {
+     147     4772143 :                 if (this->photonDensity[i] < 0.)
+     148           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: a value in the photon density input is negative");
+     149             :         }
+     150             : 
+     151          94 :         if (this->isRedshiftDependent) {
+     152          73 :                 if (this->redshifts[0] != 0.)
+     153           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: redshift input must start with zero");
+     154             : 
+     155       14380 :                 for (int i = 0; i < this->redshifts.size(); ++i) {
+     156             :                         double zPrevious = -1.;
+     157       14307 :                         double z = this->redshifts[i];
+     158       14307 :                         if (z < 0.)
+     159           0 :                                 throw std::runtime_error("TabularPhotonField::checkInputData: a value in the redshift input is negative");
+     160       14307 :                         if (z <= zPrevious)
+     161           0 :                                 throw std::runtime_error("TabularPhotonField::checkInputData: redshift values are not strictly increasing");
+     162             :                         zPrevious = z;
+     163             :                 }
+     164             : 
+     165          73 :                 for (int i = 0; i < this->redshiftScalings.size(); ++i) {
+     166           0 :                         double scalingFactor = this->redshiftScalings[i];
+     167           0 :                         if (scalingFactor <= 0.)
+     168           0 :                                 throw std::runtime_error("TabularPhotonField::checkInputData: initRedshiftScaling has created a non-positive scaling factor");
+     169             :                 }
+     170             :         }
+     171          94 : }
+     172             : 
+     173          40 : BlackbodyPhotonField::BlackbodyPhotonField(std::string fieldName, double blackbodyTemperature) {
+     174          40 :         this->fieldName = fieldName;
+     175          40 :         this->blackbodyTemperature = blackbodyTemperature;
+     176          40 :         this->quantile = 0.0001; // tested to be sufficient, only used for extreme values of primary energy or temperature
+     177          40 : }
+     178             : 
+     179       10689 : double BlackbodyPhotonField::getPhotonDensity(double Ephoton, double z) const {
+     180       10689 :         return 8 * M_PI * pow_integer<3>(Ephoton / (h_planck * c_light)) / std::expm1(Ephoton / (k_boltzmann * this->blackbodyTemperature));
+     181             : }
+     182             : 
+     183          29 : double BlackbodyPhotonField::getMinimumPhotonEnergy(double z) const {
+     184             :         double A;
+     185          29 :         int quantile_int = 10000 * quantile;
+     186          29 :         switch (quantile_int)
+     187             :         {
+     188             :         case 1: // 0.01 % percentil
+     189             :                 A = 1.093586e-5 * eV / kelvin;
+     190             :                 break;
+     191           0 :         case 10:                // 0.1 % percentil
+     192             :                 A = 2.402189e-5 * eV / kelvin;
+     193           0 :                 break;
+     194           0 :         case 100:               // 1 % percentil
+     195             :                 A = 5.417942e-5 * eV / kelvin;
+     196           0 :                 break;
+     197           0 :         default:
+     198           0 :                 throw std::runtime_error("Quantile not understood. Please use 0.01 (1%), 0.001 (0.1%) or 0.0001 (0.01%) \n");
+     199             :                 break;
+     200             :         }
+     201          29 :         return A * this -> blackbodyTemperature;
+     202             : }
+     203             : 
+     204          29 : double BlackbodyPhotonField::getMaximumPhotonEnergy(double z) const {
+     205          29 :         double factor = std::max(1., blackbodyTemperature / 2.73);
+     206          29 :         return 0.1 * factor * eV; // T dependent scaling, starting at 0.1 eV as suitable for CMB
+     207             : }
+     208             : 
+     209           0 : void BlackbodyPhotonField::setQuantile(double q) {
+     210           0 :         if(not ((q == 0.0001) or (q == 0.001) or (q == 0.01)))
+     211           0 :                 throw std::runtime_error("Quantile not understood. Please use 0.01 (1%), 0.001 (0.1%) or 0.0001 (0.01%) \n");
+     212           0 :         this -> quantile = q;
+     213           0 : }
+     214             : 
+     215             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html b/doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html new file mode 100644 index 000000000..5818e83f3 --- /dev/null +++ b/doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ProgressBar.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ProgressBar.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:395078.0 %
Date:2024-04-08 14:58:22Functions:4580.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11ProgressBar8setErrorEv0
_ZN7crpropa11ProgressBar5startERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa11ProgressBarC2Emm5
_ZN7crpropa11ProgressBar11setPositionEm100
_ZN7crpropa11ProgressBar6updateEv100
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ProgressBar.cpp.func.html b/doc/coverageReport/src/ProgressBar.cpp.func.html new file mode 100644 index 000000000..eabab3799 --- /dev/null +++ b/doc/coverageReport/src/ProgressBar.cpp.func.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ProgressBar.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ProgressBar.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:395078.0 %
Date:2024-04-08 14:58:22Functions:4580.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11ProgressBar11setPositionEm100
_ZN7crpropa11ProgressBar5startERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa11ProgressBar6updateEv100
_ZN7crpropa11ProgressBar8setErrorEv0
_ZN7crpropa11ProgressBarC2Emm5
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/ProgressBar.cpp.gcov.html b/doc/coverageReport/src/ProgressBar.cpp.gcov.html new file mode 100644 index 000000000..4bcb4bfab --- /dev/null +++ b/doc/coverageReport/src/ProgressBar.cpp.gcov.html @@ -0,0 +1,153 @@ + + + + + + + LCOV - coverage.info.cleaned - src/ProgressBar.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - ProgressBar.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:395078.0 %
Date:2024-04-08 14:58:22Functions:4580.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/ProgressBar.h"
+       2             : 
+       3             : #include <cstdio>
+       4             : #include <iostream>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8             : /// Initialize a ProgressBar with [steps] number of steps, updated at [updateSteps] intervalls
+       9           5 : ProgressBar::ProgressBar(unsigned long steps, unsigned long updateSteps) :
+      10           5 :                 _steps(steps), _currentCount(0), _maxbarLength(10), _updateSteps(
+      11           5 :                                 updateSteps), _nextStep(1), _startTime(0) {
+      12           5 :         if (_updateSteps > _steps)
+      13           3 :                 _updateSteps = _steps;
+      14           5 :         arrow.append(">");
+      15           5 : }
+      16             : 
+      17           1 : void ProgressBar::start(const std::string &title) {
+      18           1 :         _startTime = time(NULL);
+      19           1 :         std::string s = ctime(&_startTime);
+      20           1 :         s.erase(s.end() - 1, s.end());
+      21           1 :         stringTmpl = "  Started ";
+      22             :         stringTmpl.append(s);
+      23           1 :         stringTmpl.append(" : [%-10s] %3i%%    %s: %02i:%02i:%02i %s\r");
+      24             :         std::cout << title << std::endl;
+      25             : 
+      26           1 : }
+      27             : /// update the progressbar
+      28             : /// should be called steps times in a loop
+      29         100 : void ProgressBar::update() {
+      30         100 :         _currentCount++;
+      31         100 :         if (_currentCount == _nextStep || _currentCount == _steps
+      32           0 :                         || _currentCount == 1000) {
+      33         100 :                                 _nextStep += long(_steps / float(_updateSteps));
+      34         100 :                         setPosition(_currentCount);
+      35             :                         }
+      36         100 : }
+      37             : 
+      38         100 : void ProgressBar::setPosition(unsigned long position) {
+      39         100 :         int percentage = int(100 * (position / float(_steps)));
+      40         100 :         time_t currentTime = time(NULL);
+      41         100 :         if (position < _steps) {
+      42          99 :                 if (arrow.size() <= (_maxbarLength) * (position) / (_steps))
+      43           9 :                         arrow.insert(0, "=");
+      44          99 :                 float tElapsed = currentTime - _startTime;
+      45          99 :                 float tToGo = (_steps - position) * tElapsed / position;
+      46          99 :                 std::printf(stringTmpl.c_str(), arrow.c_str(), percentage, "Finish in",
+      47          99 :                                 int(tToGo / 3600), (int(tToGo) % 3600) / 60,
+      48          99 :                                 int(tToGo) % 60, "");
+      49          99 :                 fflush(stdout);
+      50             :         } else {
+      51           1 :                 float tElapsed = currentTime - _startTime;
+      52           1 :                 std::string s = " - Finished at ";
+      53           1 :                 s.append(ctime(&currentTime));
+      54             :                 char fs[255];
+      55             :                 std::sprintf(fs, "%c[%d;%dm Finished %c[%dm", 27, 1, 32, 27, 0);
+      56           1 :                 std::printf(stringTmpl.c_str(), fs, 100, "Needed",
+      57           1 :                                 int(tElapsed / 3600), (int(tElapsed) % 3600) / 60,
+      58           1 :                                 int(tElapsed) % 60, s.c_str());
+      59             :         }
+      60         100 : }
+      61             : 
+      62             : 
+      63             : /// Mark the progressbar with an error
+      64           0 : void ProgressBar::setError() {
+      65           0 :         time_t currentTime = time(NULL);
+      66           0 :         _currentCount++;
+      67           0 :         float tElapsed = currentTime - _startTime;
+      68           0 :         std::string s = " - Finished at ";
+      69           0 :         s.append(ctime(&currentTime));
+      70             :         char fs[255];
+      71             :         std::sprintf(fs, "%c[%d;%dm  ERROR   %c[%dm", 27, 1, 31, 27, 0);
+      72           0 :         std::printf(stringTmpl.c_str(), fs, _currentCount, "Needed",
+      73           0 :                         int(tElapsed / 3600), (int(tElapsed) % 3600) / 60,
+      74           0 :                         int(tElapsed) % 60, s.c_str());
+      75           0 : }
+      76             : 
+      77             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Random.cpp.func-sort-c.html b/doc/coverageReport/src/Random.cpp.func-sort-c.html new file mode 100644 index 000000000..e9ea9e87a --- /dev/null +++ b/doc/coverageReport/src/Random.cpp.func-sort-c.html @@ -0,0 +1,256 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Random.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Random.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13924157.7 %
Date:2024-04-08 14:58:22Functions:264656.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Random10randDblExcERKd0
_ZN7crpropa6Random11seedThreadsEj0
_ZN7crpropa6Random12randRayleighEd0
_ZN7crpropa6Random14getSeedThreadsEv0
_ZN7crpropa6Random15randExponentialEv0
_ZN7crpropa6Random18randBrokenPowerLawEddddd0
_ZN7crpropa6Random18randVectorLambertsERKNS_7Vector3IdEE0
_ZN7crpropa6Random18randVectorLambertsEv0
_ZN7crpropa6Random4hashEll0
_ZN7crpropa6Random4loadEPj0
_ZN7crpropa6Random4randERKd0
_ZN7crpropa6Random6rand53Ev0
_ZN7crpropa6Random7randExcERKd0
_ZN7crpropa6Random7randIntERKj0
_ZN7crpropa6RandomC2EPjj0
_ZN7crpropa6RandomC2ERKj0
_ZN7crpropalsERSoRKNS_6RandomE0
_ZN7crproparsERSiRNS_6RandomE0
_ZNK7crpropa6Random14getSeed_base64B5cxx11Ev0
_ZNK7crpropa6Random4saveEPj0
_ZN7crpropa6Random4seedERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa6Random7getSeedEv2
_ZN7crpropa6Random4seedEj13
_ZN7crpropa6Random9randInt64ERKm421
_ZN7crpropa6Random9randInt64Ev864
_ZN7crpropa6Random10randFisherEd1000
_ZN7crpropa6Random16randFisherVectorERKNS_7Vector3IdEEd1000
_ZN7crpropa6Random12randPowerLawEddd1104
_ZN7crpropa6Random4seedEv4881
_ZN7crpropa6RandomC2Ev4881
_ZN7crpropa6Random4seedEPjj4884
_ZN7crpropa6Random10initializeEj4897
_ZN7crpropa6Random7randBinERKSt6vectorIfSaIfEE10102
_ZN7crpropa6Random6reloadEv46321
_ZN7crpropa6Random14randConeVectorERKNS_7Vector3IdEEd480001
_ZN7crpropa6Random20randVectorAroundMeanERKNS_7Vector3IdEEd481001
_ZN7crpropa6Random10randVectorEv962203
_ZN7crpropa6Random10randDblExcEv1715954
_ZN7crpropa6Random7randExcEv1715954
_ZN7crpropa6Random8randNormERKdS2_1715954
_ZN7crpropa6Random11randUniformEdd2404687
_ZN7crpropa6Random8instanceEv2658589
_ZN7crpropa6Random26randomInterpolatedPositionERKNS_7Vector3IdEES4_3628723
_ZN7crpropa6Random7randBinERKSt6vectorIdSaIdEE3739276
_ZN7crpropa6Random4randEv22414108
_ZN7crpropa6Random7randIntEv25852694
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Random.cpp.func.html b/doc/coverageReport/src/Random.cpp.func.html new file mode 100644 index 000000000..c6e8901c8 --- /dev/null +++ b/doc/coverageReport/src/Random.cpp.func.html @@ -0,0 +1,256 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Random.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Random.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13924157.7 %
Date:2024-04-08 14:58:22Functions:264656.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Random10initializeEj4897
_ZN7crpropa6Random10randDblExcERKd0
_ZN7crpropa6Random10randDblExcEv1715954
_ZN7crpropa6Random10randFisherEd1000
_ZN7crpropa6Random10randVectorEv962203
_ZN7crpropa6Random11randUniformEdd2404687
_ZN7crpropa6Random11seedThreadsEj0
_ZN7crpropa6Random12randPowerLawEddd1104
_ZN7crpropa6Random12randRayleighEd0
_ZN7crpropa6Random14getSeedThreadsEv0
_ZN7crpropa6Random14randConeVectorERKNS_7Vector3IdEEd480001
_ZN7crpropa6Random15randExponentialEv0
_ZN7crpropa6Random16randFisherVectorERKNS_7Vector3IdEEd1000
_ZN7crpropa6Random18randBrokenPowerLawEddddd0
_ZN7crpropa6Random18randVectorLambertsERKNS_7Vector3IdEE0
_ZN7crpropa6Random18randVectorLambertsEv0
_ZN7crpropa6Random20randVectorAroundMeanERKNS_7Vector3IdEEd481001
_ZN7crpropa6Random26randomInterpolatedPositionERKNS_7Vector3IdEES4_3628723
_ZN7crpropa6Random4hashEll0
_ZN7crpropa6Random4loadEPj0
_ZN7crpropa6Random4randERKd0
_ZN7crpropa6Random4randEv22414108
_ZN7crpropa6Random4seedEPjj4884
_ZN7crpropa6Random4seedERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa6Random4seedEj13
_ZN7crpropa6Random4seedEv4881
_ZN7crpropa6Random6rand53Ev0
_ZN7crpropa6Random6reloadEv46321
_ZN7crpropa6Random7randBinERKSt6vectorIdSaIdEE3739276
_ZN7crpropa6Random7randBinERKSt6vectorIfSaIfEE10102
_ZN7crpropa6Random7randExcERKd0
_ZN7crpropa6Random7randExcEv1715954
_ZN7crpropa6Random7randIntERKj0
_ZN7crpropa6Random7randIntEv25852694
_ZN7crpropa6Random8instanceEv2658589
_ZN7crpropa6Random8randNormERKdS2_1715954
_ZN7crpropa6Random9randInt64ERKm421
_ZN7crpropa6Random9randInt64Ev864
_ZN7crpropa6RandomC2EPjj0
_ZN7crpropa6RandomC2ERKj0
_ZN7crpropa6RandomC2Ev4881
_ZN7crpropalsERSoRKNS_6RandomE0
_ZN7crproparsERSiRNS_6RandomE0
_ZNK7crpropa6Random14getSeed_base64B5cxx11Ev0
_ZNK7crpropa6Random4saveEPj0
_ZNK7crpropa6Random7getSeedEv2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Random.cpp.gcov.html b/doc/coverageReport/src/Random.cpp.gcov.html new file mode 100644 index 000000000..4aaef80c6 --- /dev/null +++ b/doc/coverageReport/src/Random.cpp.gcov.html @@ -0,0 +1,605 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Random.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Random.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13924157.7 %
Date:2024-04-08 14:58:22Functions:264656.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : // Random.cpp is based on Random.h
+       2             : // Mersenne Twister random number generator -- a C++ class Random
+       3             : // Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
+       4             : // Richard J. Wagner  v1.0  15 May 2003  rjwagner@writeme.com
+       5             : 
+       6             : // The Mersenne Twister is an algorithm for generating random numbers.  It
+       7             : // was designed with consideration of the flaws in various other generators.
+       8             : // The period, 2^19937-1, and the order of equidistribution, 623 dimensions,
+       9             : // are far greater.  The generator is also fast; it avoids multiplication and
+      10             : // division, and it benefits from caches and pipelines.  For more information
+      11             : // see the inventors' web page at http://www.math.keio.ac.jp/~matumoto/emt.html
+      12             : 
+      13             : // Reference
+      14             : // M. Matsumoto and T. Nishimura, "Mersenne Twister: A 623-Dimensionally
+      15             : // Equidistributed Uniform Pseudo-Random Number Generator", ACM Transactions on
+      16             : // Modeling and Computer Simulation, Vol. 8, No. 1, January 1998, pp 3-30.
+      17             : 
+      18             : // Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura,
+      19             : // Copyright (C) 2000 - 2003, Richard J. Wagner
+      20             : // All rights reserved.                          
+      21             : //
+      22             : // Redistribution and use in source and binary forms, with or without
+      23             : // modification, are permitted provided that the following conditions
+      24             : // are met:
+      25             : //
+      26             : //   1. Redistributions of source code must retain the above copyright
+      27             : //      notice, this list of conditions and the following disclaimer.
+      28             : //
+      29             : //   2. Redistributions in binary form must reproduce the above copyright
+      30             : //      notice, this list of conditions and the following disclaimer in the
+      31             : //      documentation and/or other materials provided with the distribution.
+      32             : //
+      33             : //   3. The names of its contributors may not be used to endorse or promote 
+      34             : //      products derived from this software without specific prior written 
+      35             : //      permission.
+      36             : //
+      37             : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+      38             : // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+      39             : // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+      40             : // A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
+      41             : // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+      42             : // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+      43             : // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+      44             : // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+      45             : // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+      46             : // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+      47             : // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+      48             : 
+      49             : // The original code included the following notice:
+      50             : //
+      51             : //     When you use this, send an email to: matumoto@math.keio.ac.jp
+      52             : //     with an appropriate reference to your work.
+      53             : //
+      54             : // It would be nice to CC: rjwagner@writeme.com and Cokus@math.washington.edu
+      55             : // when you write.
+      56             : 
+      57             : // Parts of this file are modified beginning in 29.10.09 for adaption in PXL.
+      58             : // Parts of this file are modified beginning in 10.02.12 for adaption in CRPropa.
+      59             : 
+      60             : #include "crpropa/Random.h"
+      61             : 
+      62             : #include "crpropa/base64.h"
+      63             : 
+      64             : #include <cstdio>
+      65             : 
+      66             : namespace crpropa {
+      67             : 
+      68           0 : Random::Random(const uint32_t& oneSeed) {
+      69           0 :         seed(oneSeed);
+      70           0 : }
+      71             : 
+      72           0 : Random::Random(uint32_t * const bigSeed, const uint32_t seedLength) {
+      73           0 :         seed(bigSeed, seedLength);
+      74           0 : }
+      75             : 
+      76        4881 : Random::Random() {
+      77        4881 :         seed();
+      78        4881 : }
+      79             : 
+      80    22414108 : double Random::rand() {
+      81    22414108 :         return double(randInt()) * (1.0 / 4294967295.0);
+      82             : }
+      83             : 
+      84           0 : double Random::rand(const double& n) {
+      85           0 :         return rand() * n;
+      86             : }
+      87             : 
+      88     1715954 : double Random::randExc() {
+      89     1715954 :         return double(randInt()) * (1.0 / 4294967296.0);
+      90             : }
+      91             : 
+      92           0 : double Random::randExc(const double& n) {
+      93           0 :         return randExc() * n;
+      94             : }
+      95             : 
+      96     1715954 : double Random::randDblExc() {
+      97     1715954 :         return (double(randInt()) + 0.5) * (1.0 / 4294967296.0);
+      98             : }
+      99             : 
+     100           0 : double Random::randDblExc(const double& n) {
+     101           0 :         return randDblExc() * n;
+     102             : }
+     103             : 
+     104           0 : double Random::rand53() {
+     105           0 :         uint32_t a = randInt() >> 5, b = randInt() >> 6;
+     106           0 :         return (a * 67108864.0 + b) * (1.0 / 9007199254740992.0); // by Isaku Wada
+     107             : }
+     108             : 
+     109             : // Return a real number from a normal (Gaussian) distribution with given
+     110             : // mean and variance by Box-Muller method
+     111     1715954 : double Random::randNorm(const double& mean, const double& variance) {
+     112     1715954 :         double r = sqrt(-2.0 * log(1.0 - randDblExc())) * variance;
+     113     1715954 :         double phi = 2.0 * 3.14159265358979323846264338328 * randExc();
+     114     1715954 :         return mean + r * cos(phi);
+     115             : }
+     116             : 
+     117     2404687 : double Random::randUniform(double min, double max) {
+     118     2404687 :         return min + (max - min) * rand();
+     119             : }
+     120             : 
+     121           0 : double Random::randRayleigh(double sigma) {
+     122           0 :         return sigma * sqrt(-2.0 * log(1 - rand()));
+     123             : }
+     124             : 
+     125        1000 : double Random::randFisher(double kappa) {
+     126        1000 :         return acos(1. + 1. / kappa * log(1 - rand() * (1 - exp(-2 * kappa))));
+     127             : }
+     128             : 
+     129       10102 : size_t Random::randBin(const std::vector<float> &cdf) {
+     130             :         std::vector<float>::const_iterator it = std::lower_bound(cdf.begin(),
+     131       10102 :                         cdf.end(), rand() * cdf.back());
+     132       10102 :         return it - cdf.begin();
+     133             : }
+     134             : 
+     135     3739276 : size_t Random::randBin(const std::vector<double> &cdf) {
+     136             :         std::vector<double>::const_iterator it = std::lower_bound(cdf.begin(),
+     137     3739276 :                         cdf.end(), rand() * cdf.back());
+     138     3739276 :         return it - cdf.begin();
+     139             : }
+     140             : 
+     141      962203 : Vector3d Random::randVector() {
+     142      962203 :         double z = randUniform(-1.0, 1.0);
+     143      962203 :         double t = randUniform(-1.0 * M_PI, M_PI);
+     144      962203 :         double r = sqrt(1 - z * z);
+     145      962203 :         return Vector3d(r * cos(t), r * sin(t), z);
+     146             : }
+     147             : 
+     148      481001 : Vector3d Random::randVectorAroundMean(const Vector3d &meanDirection,
+     149             :                 double angle) {
+     150      481001 :         Vector3d axis = meanDirection.cross(randVector());
+     151             :         Vector3d v = meanDirection;
+     152      481001 :         return v.getRotated(axis, angle);
+     153             : }
+     154             : 
+     155        1000 : Vector3d Random::randFisherVector(const Vector3d &meanDirection, double kappa) {
+     156        1000 :         return randVectorAroundMean(meanDirection, randFisher(kappa));
+     157             : }
+     158             : 
+     159      480001 : Vector3d Random::randConeVector(const Vector3d &meanDirection, double angularRadius) {
+     160      480001 :         const double theta = acos(randUniform(1, cos(angularRadius)));
+     161      480001 :         return randVectorAroundMean(meanDirection, theta);
+     162             : }
+     163             : 
+     164           0 : Vector3d Random::randVectorLamberts() {
+     165             :         // random vector following Lamberts cosine law (https://en.wikipedia.org/wiki/Lambert%27s_cosine_law)
+     166             :         // for a surface element with normal vector pointing in positive z-axis (0, 0, 1)
+     167           0 :         double phi = randUniform(-1.0 * M_PI, M_PI);
+     168           0 :         double theta = M_PI / 2.0 - acos(sqrt(randUniform(0, 1)));
+     169           0 :         return Vector3d(cos(phi) * cos(theta), sin(phi) * cos(theta), sin(theta));
+     170             : }
+     171             : 
+     172           0 : Vector3d Random::randVectorLamberts(const Vector3d &normalVector) {
+     173             :         // random vector following Lamberts cosine law for a surface element described by normalVector
+     174           0 :         Vector3d vLambertz = randVectorLamberts();
+     175             :         // find rotation axis that rotates the z-axis to the normalVector of the surface element
+     176             :         Vector3d axis = normalVector.cross(Vector3d(0, 0, 1));
+     177           0 :         if (axis.getR() < std::numeric_limits<double>::epsilon()) {
+     178             :                 axis = Vector3d(0, 0, 1);
+     179             :         }
+     180           0 :         double angle = normalVector.getAngleTo(Vector3d(0, 0, 1));
+     181             :         // rotate the random Lamberts vector from z-axis to respective surface element
+     182           0 :         return vLambertz.getRotated(axis / axis.getR(), -angle);
+     183             : }
+     184             : 
+     185     3628723 : Vector3d Random::randomInterpolatedPosition(const Vector3d &a, const Vector3d &b) {
+     186     3628723 :         return a + rand() * (b - a);
+     187             : }
+     188             : 
+     189        1104 : double Random::randPowerLaw(double index, double min, double max) {
+     190        1104 :         if ((min < 0) || (max < min)) {
+     191           0 :                 throw std::runtime_error(
+     192           0 :                                 "Power law distribution only possible for 0 <= min <= max");
+     193             :         }
+     194             :         //check for index -1!
+     195        1104 :         if ((std::abs(index + 1.0)) < std::numeric_limits<double>::epsilon()) {
+     196           2 :                 double part1 = log(max);
+     197           2 :                 double part2 = log(min);
+     198           2 :                 return exp((part1 - part2) * rand() + part2);
+     199             :         } else {
+     200        1102 :                 double part1 = pow(max, index + 1);
+     201        1102 :                 double part2 = pow(min, index + 1);
+     202        1102 :                 double ex = 1 / (index + 1);
+     203        1102 :                 return pow((part1 - part2) * rand() + part2, ex);
+     204             :         }
+     205             : }
+     206             : 
+     207           0 : double Random::randBrokenPowerLaw(double index1, double index2,
+     208             :                 double breakpoint, double min, double max) {
+     209           0 :         if ((min <= 0) || (max < min)) {
+     210           0 :                 throw std::runtime_error(
+     211           0 :                                 "Power law distribution only possible for 0 < min <= max");
+     212             :         }
+     213           0 :         if (min >= breakpoint) {
+     214           0 :                 return this->randPowerLaw(index2, min, max);
+     215           0 :         } else if (max <= breakpoint) {
+     216           0 :                 return this->randPowerLaw(index2, min, max);
+     217             :         } else {
+     218             :                 double intPL1;
+     219             :                 // check if index1 = -1
+     220           0 :                 if ((std::abs(index1 + 1.0)) < std::numeric_limits<double>::epsilon()) {
+     221           0 :                         intPL1 = log(breakpoint / min);
+     222             :                 } else {
+     223           0 :                         intPL1 = (pow(breakpoint, index1 + 1) - pow(min, index1 + 1))
+     224             :                                         / (index1 + 1);
+     225             :                 }
+     226             :                 double intPL2;
+     227             :                 // check if index2 = -1
+     228           0 :                 if ((std::abs(index2 + 1.0)) < std::numeric_limits<double>::epsilon()) {
+     229           0 :                         intPL2 = log(max / breakpoint) * pow(breakpoint, index1 - index2);
+     230             :                 } else {
+     231           0 :                         intPL2 = (pow(max, index2 + 1) - pow(breakpoint, index2 + 1))
+     232           0 :                                         * pow(breakpoint, index1 - index2) / (index2 + 1);
+     233             :                 }
+     234           0 :                 if (rand() > intPL1 / (intPL1 + intPL2))
+     235           0 :                         return randPowerLaw(index2, breakpoint, max);
+     236             :                 else
+     237           0 :                         return randPowerLaw(index1, min, breakpoint);
+     238             :         }
+     239             : }
+     240             : 
+     241           0 : double Random::randExponential() {
+     242             :         double dum;
+     243             :         do {
+     244           0 :                 dum = rand();
+     245           0 :         } while (dum < std::numeric_limits<double>::epsilon());
+     246           0 :         return -1.0 * log(dum);
+     247             : }
+     248             : 
+     249    25852694 : uint32_t Random::randInt() {
+     250    25852694 :         if (left == 0)
+     251       41424 :                 reload();
+     252    25852694 :         --left;
+     253             : 
+     254             :         uint32_t s1;
+     255    25852694 :         s1 = *pNext++;
+     256    25852694 :         s1 ^= (s1 >> 11);
+     257    25852694 :         s1 ^= (s1 << 7) & 0x9d2c5680UL;
+     258    25852694 :         s1 ^= (s1 << 15) & 0xefc60000UL;
+     259    25852694 :         return (s1 ^ (s1 >> 18));
+     260             : }
+     261             : 
+     262           0 : uint32_t Random::randInt(const uint32_t& n) {
+     263             : // Find which bits are used in n
+     264             : // Optimized by Magnus Jonsson (magnus@smartelectronix.com)
+     265           0 :         uint32_t used = n;
+     266           0 :         used |= used >> 1;
+     267           0 :         used |= used >> 2;
+     268           0 :         used |= used >> 4;
+     269           0 :         used |= used >> 8;
+     270           0 :         used |= used >> 16;
+     271             : 
+     272             : // Draw numbers until one is found in [0,n]
+     273             :         uint32_t i;
+     274             :         do
+     275           0 :                 i = randInt() & used; // toss unused bits to shorten search
+     276           0 :         while (i > n);
+     277           0 :         return i;
+     278             : }
+     279             : 
+     280             : 
+     281         864 : uint64_t Random::randInt64()
+     282             : {
+     283         864 :         int64_t a = randInt();
+     284         864 :         int64_t b = randInt();
+     285         864 :         return (b + a << 32);
+     286             : }
+     287             : 
+     288             : 
+     289         421 : uint64_t Random::randInt64(const uint64_t &n)
+     290             : {
+     291         421 :         uint64_t used = n;
+     292         421 :         used |= used >> 1;
+     293         421 :         used |= used >> 2;
+     294         421 :         used |= used >> 4;
+     295         421 :         used |= used >> 8;
+     296         421 :         used |= used >> 16;
+     297         421 :         used |= used >> 32;
+     298             : 
+     299             :         // Draw numbers until one is found in [0,n]
+     300             :         uint64_t i;
+     301             :         do
+     302         864 :                 i = randInt64() & used; // toss unused bits to shorten search
+     303         864 :         while (i > n);
+     304         421 :         return i;
+     305             : }
+     306             : 
+     307             : 
+     308             : 
+     309          13 : void Random::seed(const uint32_t oneSeed) {
+     310          13 :         initial_seed.resize(1);
+     311          13 :         initial_seed[0] = oneSeed;
+     312          13 :         initialize(oneSeed);
+     313          13 :         reload();
+     314          13 : }
+     315             : 
+     316        4884 : void Random::seed(uint32_t * const bigSeed, const uint32_t seedLength) {
+     317             : 
+     318        4884 :         initial_seed.resize(seedLength);
+     319     3051260 :         for (size_t i =0; i< seedLength; i++)
+     320             :         {
+     321     3046376 :                 initial_seed[i] = bigSeed[i];
+     322             :         }
+     323             : 
+     324        4884 :         initialize(19650218UL);
+     325             :         int i = 1;
+     326             :         uint32_t j = 0;
+     327        4884 :         int k = (N > seedLength ? N : seedLength);
+     328     3052500 :         for (; k; --k) {
+     329     3047616 :                 state[i] = state[i]
+     330     3047616 :                                 ^ ((state[i - 1] ^ (state[i - 1] >> 30)) * 1664525UL);
+     331     3047616 :                 state[i] += (bigSeed[j] & 0xffffffffUL) + j;
+     332             :                 state[i] &= 0xffffffffUL;
+     333     3047616 :                 ++i;
+     334     3047616 :                 ++j;
+     335     3047616 :                 if (i >= N) {
+     336        4884 :                         state[0] = state[N - 1];
+     337             :                         i = 1;
+     338             :                 }
+     339     3047616 :                 if (j >= seedLength)
+     340             :                         j = 0;
+     341             :         }
+     342     3047616 :         for (k = N - 1; k; --k) {
+     343     3042732 :                 state[i] = state[i]
+     344     3042732 :                                 ^ ((state[i - 1] ^ (state[i - 1] >> 30)) * 1566083941UL);
+     345     3042732 :                 state[i] -= i;
+     346             :                 state[i] &= 0xffffffffUL;
+     347     3042732 :                 ++i;
+     348     3042732 :                 if (i >= N) {
+     349        4884 :                         state[0] = state[N - 1];
+     350             :                         i = 1;
+     351             :                 }
+     352             :         }
+     353        4884 :         state[0] = 0x80000000UL; // MSB is 1, assuring non-zero initial array
+     354        4884 :         reload();
+     355        4884 : }
+     356             : 
+     357        4881 : void Random::seed() {
+     358             : // First try getting an array from /dev/urandom
+     359        4881 :         FILE* urandom = std::fopen("/dev/urandom", "rb");
+     360        4881 :         if (urandom) {
+     361             :                 uint32_t bigSeed[N];
+     362             :                 uint32_t *s = bigSeed;
+     363             :                 int i = N;
+     364             :                 bool success = true;
+     365     3050625 :                 while (success && i--)
+     366     6091488 :                         success = std::fread(s++, sizeof(uint32_t), 1, urandom) != 0;
+     367        4881 :                 std::fclose(urandom);
+     368        4881 :                 if (success) {
+     369        4881 :                         seed(bigSeed, N);
+     370        4881 :                         return;
+     371             :                 }
+     372             :         }
+     373             : 
+     374             : // Was not successful, so use time() and clock() instead
+     375           0 :         seed(hash(time(NULL), clock()));
+     376             : }
+     377             : 
+     378             : 
+     379        4897 : void Random::initialize(const uint32_t seed) {
+     380        4897 :         uint32_t *s = state;
+     381             :         uint32_t *r = state;
+     382             :         int i = 1;
+     383        4897 :         *s++ = seed & 0xffffffffUL;
+     384     3055728 :         for (; i < N; ++i) {
+     385     3050831 :                 *s++ = (1812433253UL * (*r ^ (*r >> 30)) + i) & 0xffffffffUL;
+     386     3050831 :                 r++;
+     387             :         }
+     388        4897 : }
+     389             : 
+     390       46321 : void Random::reload() {
+     391       46321 :         uint32_t *p = state;
+     392             :         int i;
+     393    10561188 :         for (i = N - M; i--; ++p)
+     394    10514867 :                 *p = twist(p[M], p[0], p[1]);
+     395    18389437 :         for (i = M; --i; ++p)
+     396    18343116 :                 *p = twist(p[M - N], p[0], p[1]);
+     397       46321 :         *p = twist(p[M - N], p[0], state[0]);
+     398             : 
+     399       46321 :         left = N, pNext = state;
+     400       46321 : }
+     401             : 
+     402           0 : uint32_t Random::hash(time_t t, clock_t c) {
+     403             :         static uint32_t differ = 0; // guarantee time-based seeds will change
+     404             : 
+     405             :         uint32_t h1 = 0;
+     406             :         unsigned char *p = (unsigned char *) &t;
+     407           0 :         for (size_t i = 0; i < sizeof(t); ++i) {
+     408           0 :                 h1 *= std::numeric_limits<unsigned char>::max() + 2U;
+     409           0 :                 h1 += p[i];
+     410             :         }
+     411             :         uint32_t h2 = 0;
+     412             :         p = (unsigned char *) &c;
+     413           0 :         for (size_t j = 0; j < sizeof(c); ++j) {
+     414           0 :                 h2 *= std::numeric_limits<unsigned char>::max() + 2U;
+     415           0 :                 h2 += p[j];
+     416             :         }
+     417           0 :         return (h1 + differ++) ^ h2;
+     418             : }
+     419             : 
+     420           0 : void Random::save(uint32_t* saveArray) const {
+     421             :         uint32_t *sa = saveArray;
+     422           0 :         const uint32_t *s = state;
+     423             :         int i = N;
+     424           0 :         for (; i--; *sa++ = *s++) {
+     425             :         }
+     426           0 :         *sa = left;
+     427           0 : }
+     428             : 
+     429           2 : const std::vector<uint32_t> &Random::getSeed() const
+     430             : {
+     431           2 :         return initial_seed;
+     432             : }
+     433             : 
+     434           0 : void Random::load(uint32_t * const loadArray) {
+     435           0 :         uint32_t *s = state;
+     436             :         uint32_t *la = loadArray;
+     437             :         int i = N;
+     438           0 :         for (; i--; *s++ = *la++) {
+     439             :         }
+     440           0 :         left = *la;
+     441           0 :         pNext = &state[N - left];
+     442           0 : }
+     443             : 
+     444           0 : std::ostream& operator<<(std::ostream& os, const Random& mtrand) {
+     445           0 :         const uint32_t *s = mtrand.state;
+     446             :         int i = mtrand.N;
+     447           0 :         for (; i--; os << *s++ << "\t") {
+     448             :         }
+     449           0 :         return os << mtrand.left;
+     450             : }
+     451             : 
+     452           0 : std::istream& operator>>(std::istream& is, Random& mtrand) {
+     453           0 :         uint32_t *s = mtrand.state;
+     454             :         int i = mtrand.N;
+     455           0 :         for (; i--; is >> *s++) {
+     456             :         }
+     457           0 :         is >> mtrand.left;
+     458           0 :         mtrand.pNext = &mtrand.state[mtrand.N - mtrand.left];
+     459           0 :         return is;
+     460             : }
+     461             : 
+     462             : #ifdef _OPENMP
+     463             : #include <omp.h>
+     464             : #include <stdexcept>
+     465             : 
+     466             : // see http://stackoverflow.com/questions/8051108/using-the-openmp-threadprivate-directive-on-static-instances-of-c-stl-types
+     467             : const static int MAX_THREAD = 256;
+     468             : 
+     469             : struct RANDOM_TLS_ITEM {
+     470             :         Random r;
+     471             :         char padding[(sizeof(Random) / 64 + 1) * 64 - sizeof(Random)];
+     472             : };
+     473             : 
+     474             : #ifdef _MSC_VER
+     475             : __declspec(align(64)) static RANDOM_TLS_ITEM _tls[MAX_THREAD];
+     476             : #else
+     477             : __attribute__ ((aligned(64))) static RANDOM_TLS_ITEM _tls[MAX_THREAD];
+     478             : #endif
+     479             : 
+     480     2658589 : Random &Random::instance() {
+     481     2658589 :         int i = omp_get_thread_num();
+     482     2658589 :         if (i >= MAX_THREAD)
+     483           0 :         throw std::runtime_error("crpropa::Random: more than MAX_THREAD threads!");
+     484     2658589 :         return _tls[i].r;
+     485             : }
+     486             : 
+     487           0 : void Random::seedThreads(const uint32_t oneSeed) {
+     488           0 :         for(size_t i = 0; i < MAX_THREAD; ++i)
+     489           0 :         _tls[i].r.seed(oneSeed + i);
+     490           0 : }
+     491             : 
+     492           0 : std::vector< std::vector<uint32_t> > Random::getSeedThreads()
+     493             : {
+     494             :         std::vector< std::vector<uint32_t> > seeds;
+     495           0 :         for(size_t i = 0; i < omp_get_num_threads(); ++i)
+     496           0 :                 seeds.push_back(_tls[i].r.getSeed() ); 
+     497           0 :         return seeds;
+     498           0 : }
+     499             : 
+     500             : #else
+     501             : static Random _random;
+     502             : Random &Random::instance() {
+     503             :         return _random;
+     504             : }
+     505             : void Random::seedThreads(const uint32_t oneSeed) {
+     506             :         _random.seed(oneSeed);
+     507             : }
+     508             : std::vector< std::vector<uint32_t> > Random::getSeedThreads()
+     509             : {
+     510             :         std::vector< std::vector<uint32_t> > seeds;
+     511             :                 seeds.push_back(_random.getSeed() ); 
+     512             :         return seeds;
+     513             : }
+     514             : #endif
+     515             : 
+     516           0 : const std::string Random::getSeed_base64() const
+     517             : {
+     518           0 :         return Base64::encode((unsigned char*) &initial_seed[0], sizeof(initial_seed[0]) * initial_seed.size() / sizeof(unsigned char));
+     519             : }
+     520             : 
+     521           1 : void Random::seed(const std::string &b64Seed)
+     522             : {
+     523           1 :         std::string decoded_data = Base64::decode(b64Seed);
+     524           1 :         size_t seedSize = decoded_data.size() * sizeof(decoded_data[0]) / sizeof(uint32_t);
+     525           1 :         seed((uint32_t*)decoded_data.c_str(), seedSize );
+     526           1 : }
+     527             : 
+     528             : } // namespace crpropa
+     529             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Source.cpp.func-sort-c.html b/doc/coverageReport/src/Source.cpp.func-sort-c.html new file mode 100644 index 000000000..34e0bcd2a --- /dev/null +++ b/doc/coverageReport/src/Source.cpp.func-sort-c.html @@ -0,0 +1,656 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Source.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Source.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:45978458.5 %
Date:2024-04-08 14:58:22Functions:8114655.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14SourcePositionC2Ed0
_ZN7crpropa15SourceDirection14setDescriptionEv0
_ZN7crpropa15SourceDirectionC2ENS_7Vector3IdEE0
_ZN7crpropa17SourceEmissionMap14setDescriptionEv0
_ZN7crpropa17SourceEmissionMap14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17SourceEmissionMapC2EPNS_11EmissionMapE0
_ZN7crpropa18SourceUniformShell14setDescriptionEv0
_ZN7crpropa18SourceUniformShellC2ENS_7Vector3IdEEd0
_ZN7crpropa21SourceSNRDistribution14setDescriptionEv0
_ZN7crpropa21SourceSNRDistribution7setBetaEd0
_ZN7crpropa21SourceSNRDistributionC2Ev0
_ZN7crpropa21SourceUniformCylinder14setDescriptionEv0
_ZN7crpropa21SourceUniformRedshift14setDescriptionEv0
_ZN7crpropa21SourceUniformRedshiftC2Edd0
_ZN7crpropa22SourceMassDistribution14getDescriptionB5cxx11Ev0
_ZN7crpropa22SourceMassDistribution15setMaximalTriesEi0
_ZN7crpropa22SourceMassDistribution17setMaximalDensityEd0
_ZN7crpropa22SourceMassDistribution9setXrangeEdd0
_ZN7crpropa22SourceMassDistribution9setYrangeEdd0
_ZN7crpropa22SourceMassDistribution9setZrangeEdd0
_ZN7crpropa22SourceMassDistributionC2ENS_7ref_ptrINS_7DensityEEEdddd0
_ZN7crpropa24SourceGenericComposition3addEiid0
_ZN7crpropa24SourcePulsarDistribution12getThetaBlurEv0
_ZN7crpropa24SourcePulsarDistribution12setThetaBlurEd0
_ZN7crpropa24SourcePulsarDistribution14setDescriptionEv0
_ZN7crpropa24SourcePulsarDistribution7getRMaxEv0
_ZN7crpropa24SourcePulsarDistribution7getZMaxEv0
_ZN7crpropa24SourcePulsarDistribution7setRMaxEd0
_ZN7crpropa24SourcePulsarDistribution7setZMaxEd0
_ZN7crpropa24SourcePulsarDistribution8getFrMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getFzMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getRBlurEv0
_ZN7crpropa24SourcePulsarDistribution8setFrMaxEdd0
_ZN7crpropa24SourcePulsarDistribution8setFzMaxEd0
_ZN7crpropa24SourcePulsarDistribution8setRBlurEd0
_ZN7crpropa24SourcePulsarDistributionC2Eddddd0
_ZN7crpropa24SourcePulsarDistributionC2Ev0
_ZN7crpropa27SourceMultipleParticleTypes14setDescriptionEv0
_ZN7crpropa27SourceMultipleParticleTypes3addEid0
_ZN7crpropa27SourceMultipleParticleTypesC2Ev0
_ZN7crpropa33SourceLambertDistributionOnSphere14setDescriptionEv0
_ZN7crpropa33SourceLambertDistributionOnSphereC2ERKNS_7Vector3IdEEdb0
_ZNK7crpropa10SourceList14getDescriptionB5cxx11Ev0
_ZNK7crpropa13SourceFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa15SourceDirection15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa17SourceEmissionMap16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa18SourceUniformShell15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa21SourceSNRDistribution7getBetaEv0
_ZNK7crpropa21SourceSNRDistribution7getRMaxEv0
_ZNK7crpropa21SourceSNRDistribution7getZMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getAlphaEv0
_ZNK7crpropa21SourceSNRDistribution8getFrMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getFzMaxEv0
_ZNK7crpropa21SourceUniformRedshift16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa22SourceMassDistribution14samplePositionEv0
_ZNK7crpropa22SourceMassDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa24SourcePulsarDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa24SourcePulsarDistribution2frEd0
_ZNK7crpropa24SourcePulsarDistribution2fzEd0
_ZNK7crpropa24SourcePulsarDistribution5blurREd0
_ZNK7crpropa24SourcePulsarDistribution6fthetaEid0
_ZNK7crpropa24SourcePulsarDistribution9blurThetaEdd0
_ZNK7crpropa27SourceMultipleParticleTypes15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa33SourceLambertDistributionOnSphere15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa6Source14getDescriptionB5cxx11Ev0
_ZN7crpropa14SourceRedshift14setDescriptionEv1
_ZN7crpropa14SourceRedshiftC2Ed1
_ZN7crpropa15SourceUniform1D14setDescriptionEv1
_ZN7crpropa15SourceUniform1DC2Eddb1
_ZN7crpropa16SourceRedshift1D14setDescriptionEv1
_ZN7crpropa16SourceRedshift1DC2Ev1
_ZN7crpropa16SourceUniformBox14setDescriptionEv1
_ZN7crpropa16SourceUniformBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa18SourceEmissionCone12setDirectionENS_7Vector3IdEE1
_ZN7crpropa18SourceEmissionCone14setDescriptionEv1
_ZN7crpropa18SourceEmissionConeC2ENS_7Vector3IdEEd1
_ZN7crpropa19SourceUniformSphere14setDescriptionEv1
_ZN7crpropa19SourceUniformSphereC2ENS_7Vector3IdEEd1
_ZN7crpropa21SourceSNRDistribution7setZMaxEd1
_ZN7crpropa21SourceSNRDistribution8setAlphaEd1
_ZN7crpropa21SourceSNRDistribution8setFzMaxEd1
_ZN7crpropa21SourceSNRDistributionC2Edddd1
_ZN7crpropa21SourceUniformCylinderC2ENS_7Vector3IdEEdd1
_ZN7crpropa22SourceDirectedEmission14setDescriptionEv1
_ZN7crpropa22SourceDirectedEmissionC2ENS_7Vector3IdEEd1
_ZN7crpropa23SourceMultiplePositions14setDescriptionEv1
_ZN7crpropa23SourceMultiplePositionsC2Ev1
_ZN7crpropa24SourceGenericComposition14setDescriptionEv1
_ZN7crpropa24SourceGenericCompositionC2EddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEm1
_ZN7crpropa25SourceUniformHollowSphere14setDescriptionEv1
_ZN7crpropa25SourceUniformHollowSphereC2ENS_7Vector3IdEEdd1
_ZN7crpropa9SourceTag14setDescriptionEv1
_ZN7crpropa9SourceTag6setTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa9SourceTagC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa14SourceRedshift16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa15SourceUniform1D15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa16SourceRedshift1D16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa16SourceUniformBox15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa18SourceEmissionCone15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa19SourceUniformSphere15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa21SourceUniformCylinder15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa9SourceTag16prepareCandidateERNS_9CandidateE1
_ZN7crpropa12SourceEnergy14setDescriptionEv2
_ZN7crpropa12SourceEnergyC2Ed2
_ZN7crpropa17SourceDensityGrid14setDescriptionEv2
_ZN7crpropa17SourceDensityGridC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa19SourceDensityGrid1D14setDescriptionEv2
_ZN7crpropa19SourceDensityGrid1DC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa21SourceSNRDistribution7setRMaxEd2
_ZN7crpropa21SourceSNRDistribution8setFrMaxEv2
_ZN7crpropa23SourceMultiplePositions3addENS_7Vector3IdEEd2
_ZN7crpropa23SourceRedshiftEvolutionC2Eddd2
_ZN7crpropa24SourceGenericComposition3addEid2
_ZN7crpropa10SourceList3addEPNS_6SourceEd3
_ZN7crpropa17SourceCompositionC2Eddd3
_ZN7crpropa18SourceParticleType14setDescriptionEv3
_ZN7crpropa18SourceParticleTypeC2Ei3
_ZN7crpropa23SourceIsotropicEmission14setDescriptionEv3
_ZN7crpropa23SourceIsotropicEmissionC2Ev3
_ZNK7crpropa17SourceComposition15prepareParticleERNS_13ParticleStateE3
_ZN7crpropa17SourceComposition3addEiid4
_ZN7crpropa22SourcePowerLawSpectrum14setDescriptionEv4
_ZN7crpropa22SourcePowerLawSpectrumC2Eddd4
_ZN7crpropa14SourcePosition14setDescriptionEv5
_ZN7crpropa14SourcePositionC2ENS_7Vector3IdEE5
_ZN7crpropa17SourceComposition3addEid5
_ZN7crpropa17SourceComposition14setDescriptionEv8
_ZN7crpropa6Source3addEPNS_13SourceFeatureE19
_ZNK7crpropa25SourceUniformHollowSphere15prepareParticleERNS_13ParticleStateE100
_ZNK7crpropa19SourceDensityGrid1D15prepareParticleERNS_13ParticleStateE101
_ZNK7crpropa23SourceRedshiftEvolution16prepareCandidateERNS_9CandidateE200
_ZNK7crpropa12SourceEnergy15prepareParticleERNS_13ParticleStateE1000
_ZNK7crpropa22SourceDirectedEmission16prepareCandidateERNS_9CandidateE1000
_ZNK7crpropa10SourceList12getCandidateEv1002
_ZNK7crpropa18SourceParticleType15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa23SourceIsotropicEmission15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa22SourcePowerLawSpectrum15prepareParticleERNS_13ParticleStateE1102
_ZNK7crpropa14SourcePosition15prepareParticleERNS_13ParticleStateE1103
_ZNK7crpropa6Source12getCandidateEv2103
_ZNK7crpropa13SourceFeature16prepareCandidateERNS_9CandidateE5407
_ZNK7crpropa23SourceMultiplePositions15prepareParticleERNS_13ParticleStateE10000
_ZNK7crpropa17SourceDensityGrid15prepareParticleERNS_13ParticleStateE10001
_ZNK7crpropa24SourceGenericComposition15prepareParticleERNS_13ParticleStateE100000
_ZNK7crpropa21SourceSNRDistribution15prepareParticleERNS_13ParticleStateE100001
_ZNK7crpropa21SourceSNRDistribution2frEd193272
_ZNK7crpropa21SourceSNRDistribution2fzEd1663640
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Source.cpp.func.html b/doc/coverageReport/src/Source.cpp.func.html new file mode 100644 index 000000000..cbdfefa59 --- /dev/null +++ b/doc/coverageReport/src/Source.cpp.func.html @@ -0,0 +1,656 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Source.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Source.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:45978458.5 %
Date:2024-04-08 14:58:22Functions:8114655.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10SourceList3addEPNS_6SourceEd3
_ZN7crpropa12SourceEnergy14setDescriptionEv2
_ZN7crpropa12SourceEnergyC2Ed2
_ZN7crpropa14SourcePosition14setDescriptionEv5
_ZN7crpropa14SourcePositionC2ENS_7Vector3IdEE5
_ZN7crpropa14SourcePositionC2Ed0
_ZN7crpropa14SourceRedshift14setDescriptionEv1
_ZN7crpropa14SourceRedshiftC2Ed1
_ZN7crpropa15SourceDirection14setDescriptionEv0
_ZN7crpropa15SourceDirectionC2ENS_7Vector3IdEE0
_ZN7crpropa15SourceUniform1D14setDescriptionEv1
_ZN7crpropa15SourceUniform1DC2Eddb1
_ZN7crpropa16SourceRedshift1D14setDescriptionEv1
_ZN7crpropa16SourceRedshift1DC2Ev1
_ZN7crpropa16SourceUniformBox14setDescriptionEv1
_ZN7crpropa16SourceUniformBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa17SourceComposition14setDescriptionEv8
_ZN7crpropa17SourceComposition3addEid5
_ZN7crpropa17SourceComposition3addEiid4
_ZN7crpropa17SourceCompositionC2Eddd3
_ZN7crpropa17SourceDensityGrid14setDescriptionEv2
_ZN7crpropa17SourceDensityGridC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa17SourceEmissionMap14setDescriptionEv0
_ZN7crpropa17SourceEmissionMap14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17SourceEmissionMapC2EPNS_11EmissionMapE0
_ZN7crpropa18SourceEmissionCone12setDirectionENS_7Vector3IdEE1
_ZN7crpropa18SourceEmissionCone14setDescriptionEv1
_ZN7crpropa18SourceEmissionConeC2ENS_7Vector3IdEEd1
_ZN7crpropa18SourceParticleType14setDescriptionEv3
_ZN7crpropa18SourceParticleTypeC2Ei3
_ZN7crpropa18SourceUniformShell14setDescriptionEv0
_ZN7crpropa18SourceUniformShellC2ENS_7Vector3IdEEd0
_ZN7crpropa19SourceDensityGrid1D14setDescriptionEv2
_ZN7crpropa19SourceDensityGrid1DC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa19SourceUniformSphere14setDescriptionEv1
_ZN7crpropa19SourceUniformSphereC2ENS_7Vector3IdEEd1
_ZN7crpropa21SourceSNRDistribution14setDescriptionEv0
_ZN7crpropa21SourceSNRDistribution7setBetaEd0
_ZN7crpropa21SourceSNRDistribution7setRMaxEd2
_ZN7crpropa21SourceSNRDistribution7setZMaxEd1
_ZN7crpropa21SourceSNRDistribution8setAlphaEd1
_ZN7crpropa21SourceSNRDistribution8setFrMaxEv2
_ZN7crpropa21SourceSNRDistribution8setFzMaxEd1
_ZN7crpropa21SourceSNRDistributionC2Edddd1
_ZN7crpropa21SourceSNRDistributionC2Ev0
_ZN7crpropa21SourceUniformCylinder14setDescriptionEv0
_ZN7crpropa21SourceUniformCylinderC2ENS_7Vector3IdEEdd1
_ZN7crpropa21SourceUniformRedshift14setDescriptionEv0
_ZN7crpropa21SourceUniformRedshiftC2Edd0
_ZN7crpropa22SourceDirectedEmission14setDescriptionEv1
_ZN7crpropa22SourceDirectedEmissionC2ENS_7Vector3IdEEd1
_ZN7crpropa22SourceMassDistribution14getDescriptionB5cxx11Ev0
_ZN7crpropa22SourceMassDistribution15setMaximalTriesEi0
_ZN7crpropa22SourceMassDistribution17setMaximalDensityEd0
_ZN7crpropa22SourceMassDistribution9setXrangeEdd0
_ZN7crpropa22SourceMassDistribution9setYrangeEdd0
_ZN7crpropa22SourceMassDistribution9setZrangeEdd0
_ZN7crpropa22SourceMassDistributionC2ENS_7ref_ptrINS_7DensityEEEdddd0
_ZN7crpropa22SourcePowerLawSpectrum14setDescriptionEv4
_ZN7crpropa22SourcePowerLawSpectrumC2Eddd4
_ZN7crpropa23SourceIsotropicEmission14setDescriptionEv3
_ZN7crpropa23SourceIsotropicEmissionC2Ev3
_ZN7crpropa23SourceMultiplePositions14setDescriptionEv1
_ZN7crpropa23SourceMultiplePositions3addENS_7Vector3IdEEd2
_ZN7crpropa23SourceMultiplePositionsC2Ev1
_ZN7crpropa23SourceRedshiftEvolutionC2Eddd2
_ZN7crpropa24SourceGenericComposition14setDescriptionEv1
_ZN7crpropa24SourceGenericComposition3addEid2
_ZN7crpropa24SourceGenericComposition3addEiid0
_ZN7crpropa24SourceGenericCompositionC2EddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEm1
_ZN7crpropa24SourcePulsarDistribution12getThetaBlurEv0
_ZN7crpropa24SourcePulsarDistribution12setThetaBlurEd0
_ZN7crpropa24SourcePulsarDistribution14setDescriptionEv0
_ZN7crpropa24SourcePulsarDistribution7getRMaxEv0
_ZN7crpropa24SourcePulsarDistribution7getZMaxEv0
_ZN7crpropa24SourcePulsarDistribution7setRMaxEd0
_ZN7crpropa24SourcePulsarDistribution7setZMaxEd0
_ZN7crpropa24SourcePulsarDistribution8getFrMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getFzMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getRBlurEv0
_ZN7crpropa24SourcePulsarDistribution8setFrMaxEdd0
_ZN7crpropa24SourcePulsarDistribution8setFzMaxEd0
_ZN7crpropa24SourcePulsarDistribution8setRBlurEd0
_ZN7crpropa24SourcePulsarDistributionC2Eddddd0
_ZN7crpropa24SourcePulsarDistributionC2Ev0
_ZN7crpropa25SourceUniformHollowSphere14setDescriptionEv1
_ZN7crpropa25SourceUniformHollowSphereC2ENS_7Vector3IdEEdd1
_ZN7crpropa27SourceMultipleParticleTypes14setDescriptionEv0
_ZN7crpropa27SourceMultipleParticleTypes3addEid0
_ZN7crpropa27SourceMultipleParticleTypesC2Ev0
_ZN7crpropa33SourceLambertDistributionOnSphere14setDescriptionEv0
_ZN7crpropa33SourceLambertDistributionOnSphereC2ERKNS_7Vector3IdEEdb0
_ZN7crpropa6Source3addEPNS_13SourceFeatureE19
_ZN7crpropa9SourceTag14setDescriptionEv1
_ZN7crpropa9SourceTag6setTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa9SourceTagC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa10SourceList12getCandidateEv1002
_ZNK7crpropa10SourceList14getDescriptionB5cxx11Ev0
_ZNK7crpropa12SourceEnergy15prepareParticleERNS_13ParticleStateE1000
_ZNK7crpropa13SourceFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa13SourceFeature16prepareCandidateERNS_9CandidateE5407
_ZNK7crpropa14SourcePosition15prepareParticleERNS_13ParticleStateE1103
_ZNK7crpropa14SourceRedshift16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa15SourceDirection15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa15SourceUniform1D15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa16SourceRedshift1D16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa16SourceUniformBox15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa17SourceComposition15prepareParticleERNS_13ParticleStateE3
_ZNK7crpropa17SourceDensityGrid15prepareParticleERNS_13ParticleStateE10001
_ZNK7crpropa17SourceEmissionMap16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa18SourceEmissionCone15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa18SourceParticleType15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa18SourceUniformShell15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa19SourceDensityGrid1D15prepareParticleERNS_13ParticleStateE101
_ZNK7crpropa19SourceUniformSphere15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa21SourceSNRDistribution15prepareParticleERNS_13ParticleStateE100001
_ZNK7crpropa21SourceSNRDistribution2frEd193272
_ZNK7crpropa21SourceSNRDistribution2fzEd1663640
_ZNK7crpropa21SourceSNRDistribution7getBetaEv0
_ZNK7crpropa21SourceSNRDistribution7getRMaxEv0
_ZNK7crpropa21SourceSNRDistribution7getZMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getAlphaEv0
_ZNK7crpropa21SourceSNRDistribution8getFrMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getFzMaxEv0
_ZNK7crpropa21SourceUniformCylinder15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa21SourceUniformRedshift16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa22SourceDirectedEmission16prepareCandidateERNS_9CandidateE1000
_ZNK7crpropa22SourceMassDistribution14samplePositionEv0
_ZNK7crpropa22SourceMassDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa22SourcePowerLawSpectrum15prepareParticleERNS_13ParticleStateE1102
_ZNK7crpropa23SourceIsotropicEmission15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa23SourceMultiplePositions15prepareParticleERNS_13ParticleStateE10000
_ZNK7crpropa23SourceRedshiftEvolution16prepareCandidateERNS_9CandidateE200
_ZNK7crpropa24SourceGenericComposition15prepareParticleERNS_13ParticleStateE100000
_ZNK7crpropa24SourcePulsarDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa24SourcePulsarDistribution2frEd0
_ZNK7crpropa24SourcePulsarDistribution2fzEd0
_ZNK7crpropa24SourcePulsarDistribution5blurREd0
_ZNK7crpropa24SourcePulsarDistribution6fthetaEid0
_ZNK7crpropa24SourcePulsarDistribution9blurThetaEdd0
_ZNK7crpropa25SourceUniformHollowSphere15prepareParticleERNS_13ParticleStateE100
_ZNK7crpropa27SourceMultipleParticleTypes15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa33SourceLambertDistributionOnSphere15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa6Source12getCandidateEv2103
_ZNK7crpropa6Source14getDescriptionB5cxx11Ev0
_ZNK7crpropa9SourceTag16prepareCandidateERNS_9CandidateE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Source.cpp.gcov.html b/doc/coverageReport/src/Source.cpp.gcov.html new file mode 100644 index 000000000..6cc5e6642 --- /dev/null +++ b/doc/coverageReport/src/Source.cpp.gcov.html @@ -0,0 +1,1218 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Source.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Source.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:45978458.5 %
Date:2024-04-08 14:58:22Functions:8114655.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Source.h"
+       2             : #include "crpropa/Random.h"
+       3             : #include "crpropa/Cosmology.h"
+       4             : #include "crpropa/Common.h"
+       5             : #include "crpropa/Units.h"
+       6             : #include "crpropa/ParticleID.h"
+       7             : 
+       8             : #ifdef CRPROPA_HAVE_MUPARSER
+       9             : #include "muParser.h"
+      10             : #endif
+      11             : 
+      12             : #include <sstream>
+      13             : #include <stdexcept>
+      14             : 
+      15             : namespace crpropa {
+      16             : 
+      17             : // Source ---------------------------------------------------------------------
+      18          19 : void Source::add(SourceFeature* property) {
+      19          19 :         features.push_back(property);
+      20          19 : }
+      21             : 
+      22        2103 : ref_ptr<Candidate> Source::getCandidate() const {
+      23        4206 :         ref_ptr<Candidate> candidate = new Candidate();
+      24        7512 :         for (int i = 0; i < features.size(); i++)
+      25        5409 :                 (*features[i]).prepareCandidate(*candidate);
+      26        2103 :         return candidate;
+      27             : }
+      28             : 
+      29           0 : std::string Source::getDescription() const {
+      30           0 :         std::stringstream ss;
+      31           0 :         ss << "Cosmic ray source\n";
+      32           0 :         for (int i = 0; i < features.size(); i++)
+      33           0 :                 ss << "    " << features[i]->getDescription();
+      34           0 :         return ss.str();
+      35           0 : }
+      36             : 
+      37             : // SourceList------------------------------------------------------------------
+      38           3 : void SourceList::add(Source* source, double weight) {
+      39           6 :         sources.push_back(source);
+      40           3 :         if (cdf.size() > 0)
+      41           1 :                 weight += cdf.back();
+      42           3 :         cdf.push_back(weight);
+      43           3 : }
+      44             : 
+      45        1002 : ref_ptr<Candidate> SourceList::getCandidate() const {
+      46        1002 :         if (sources.size() == 0)
+      47           1 :                 throw std::runtime_error("SourceList: no sources set");
+      48        1001 :         size_t i = Random::instance().randBin(cdf);
+      49        1001 :         return (sources[i])->getCandidate();
+      50             : }
+      51             : 
+      52           0 : std::string SourceList::getDescription() const {
+      53           0 :         std::stringstream ss;
+      54           0 :         ss << "List of cosmic ray sources\n";
+      55           0 :         for (int i = 0; i < sources.size(); i++)
+      56           0 :                 ss << "  " << sources[i]->getDescription();
+      57           0 :         return ss.str();
+      58           0 : }
+      59             : 
+      60             : // SourceFeature---------------------------------------------------------------
+      61        5407 : void SourceFeature::prepareCandidate(Candidate& candidate) const {
+      62        5407 :         ParticleState &source = candidate.source;
+      63        5407 :         prepareParticle(source);
+      64             :         candidate.created = source;
+      65             :         candidate.current = source;
+      66             :         candidate.previous = source;
+      67        5407 : }
+      68             : 
+      69           0 : std::string SourceFeature::getDescription() const {
+      70           0 :         return description;
+      71             : }
+      72             : 
+      73             : // ----------------------------------------------------------------------------
+      74           3 : SourceParticleType::SourceParticleType(int id) :
+      75           3 :                 id(id) {
+      76           3 :         setDescription();
+      77           3 : }
+      78             : 
+      79        1101 : void SourceParticleType::prepareParticle(ParticleState& particle) const {
+      80        1101 :         particle.setId(id);
+      81        1101 : }
+      82             : 
+      83           3 : void SourceParticleType::setDescription() {
+      84           3 :         std::stringstream ss;
+      85           3 :         ss << "SourceParticleType: " << id << "\n";
+      86           3 :         description = ss.str();
+      87           3 : }
+      88             : 
+      89             : // ----------------------------------------------------------------------------
+      90           0 : SourceMultipleParticleTypes::SourceMultipleParticleTypes() {
+      91           0 :         setDescription();
+      92           0 : }
+      93             : 
+      94           0 : void SourceMultipleParticleTypes::add(int id, double a) {
+      95           0 :         particleTypes.push_back(id);
+      96           0 :         if (cdf.size() > 0)
+      97           0 :                 a += cdf.back();
+      98           0 :         cdf.push_back(a);
+      99           0 :         setDescription();
+     100           0 : }
+     101             : 
+     102           0 : void SourceMultipleParticleTypes::prepareParticle(ParticleState& particle) const {
+     103           0 :         if (particleTypes.size() == 0)
+     104           0 :                 throw std::runtime_error("SourceMultipleParticleTypes: no nuclei set");
+     105           0 :         size_t i = Random::instance().randBin(cdf);
+     106           0 :         particle.setId(particleTypes[i]);
+     107           0 : }
+     108             : 
+     109           0 : void SourceMultipleParticleTypes::setDescription() {
+     110           0 :         std::stringstream ss;
+     111           0 :         ss << "SourceMultipleParticleTypes: Random particle type\n";
+     112           0 :         for (int i = 0; i < particleTypes.size(); i++)
+     113           0 :                 ss << "      ID = " << particleTypes[i] << "\n";
+     114           0 :         description = ss.str();
+     115           0 : }
+     116             : 
+     117             : // ----------------------------------------------------------------------------
+     118           2 : SourceEnergy::SourceEnergy(double energy) :
+     119           2 :                 E(energy) {
+     120           2 :         setDescription();
+     121           2 : }
+     122             : 
+     123        1000 : void SourceEnergy::prepareParticle(ParticleState& p) const {
+     124        1000 :         p.setEnergy(E);
+     125        1000 : }
+     126             : 
+     127           2 : void SourceEnergy::setDescription() {
+     128           2 :         std::stringstream ss;
+     129           2 :         ss << "SourceEnergy: " << E / EeV << " EeV\n";
+     130           2 :         description = ss.str();
+     131           2 : }
+     132             : 
+     133             : // ----------------------------------------------------------------------------
+     134           4 : SourcePowerLawSpectrum::SourcePowerLawSpectrum(double Emin, double Emax,
+     135           4 :                 double index) :
+     136           4 :                 Emin(Emin), Emax(Emax), index(index) {
+     137           4 :         setDescription();
+     138           4 : }
+     139             : 
+     140        1102 : void SourcePowerLawSpectrum::prepareParticle(ParticleState& particle) const {
+     141        1102 :         Random &random = Random::instance();
+     142        1102 :         double E = random.randPowerLaw(index, Emin, Emax);
+     143        1102 :         particle.setEnergy(E);
+     144        1102 : }
+     145             : 
+     146           4 : void SourcePowerLawSpectrum::setDescription() {
+     147           4 :         std::stringstream ss;
+     148           4 :         ss << "SourcePowerLawSpectrum: Random energy ";
+     149           8 :         ss << "E = " << Emin / EeV << " - " << Emax / EeV << " EeV, ";
+     150           4 :         ss << "dN/dE ~ E^" << index  << "\n";
+     151           4 :         description = ss.str();
+     152           4 : }
+     153             : 
+     154             : // ----------------------------------------------------------------------------
+     155           3 : SourceComposition::SourceComposition(double Emin, double Rmax, double index) :
+     156           3 :                 Emin(Emin), Rmax(Rmax), index(index) {
+     157           3 :         setDescription();
+     158           3 : }
+     159             : 
+     160           5 : void SourceComposition::add(int id, double weight) {
+     161           5 :         nuclei.push_back(id);
+     162           5 :         int A = massNumber(id);
+     163           5 :         int Z = chargeNumber(id);
+     164             : 
+     165           5 :         double a = 1 + index;
+     166           5 :         if (std::abs(a) < std::numeric_limits<double>::min())
+     167           5 :                 weight *= log(Z * Rmax / Emin);
+     168             :         else
+     169           0 :                 weight *= (pow(Z * Rmax, a) - pow(Emin, a)) / a;
+     170             : 
+     171           5 :         weight *= pow(A, -a);
+     172             : 
+     173           5 :         if (cdf.size() > 0)
+     174           3 :                 weight += cdf.back();
+     175           5 :         cdf.push_back(weight);
+     176           5 :         setDescription();
+     177           5 : }
+     178             : 
+     179           4 : void SourceComposition::add(int A, int Z, double a) {
+     180           4 :         add(nucleusId(A, Z), a);
+     181           4 : }
+     182             : 
+     183           3 : void SourceComposition::prepareParticle(ParticleState& particle) const {
+     184           3 :         if (nuclei.size() == 0)
+     185           1 :                 throw std::runtime_error("SourceComposition: No source isotope set");
+     186             : 
+     187           2 :         Random &random = Random::instance();
+     188             : 
+     189             :         // draw random particle type
+     190           2 :         size_t i = random.randBin(cdf);
+     191           2 :         int id = nuclei[i];
+     192           2 :         particle.setId(id);
+     193             : 
+     194             :         // random energy from power law
+     195           2 :         int Z = chargeNumber(id);
+     196           2 :         particle.setEnergy(random.randPowerLaw(index, Emin, Z * Rmax));
+     197           2 : }
+     198             : 
+     199           8 : void SourceComposition::setDescription() {
+     200           8 :         std::stringstream ss;
+     201           8 :         ss << "SourceComposition: Random element and energy ";
+     202          16 :         ss << "E = " << Emin / EeV << " - Z*" << Rmax / EeV << " EeV, ";
+     203           8 :         ss << "dN/dE ~ E^" << index << "\n";
+     204          19 :         for (int i = 0; i < nuclei.size(); i++)
+     205          11 :                 ss << "      ID = " << nuclei[i] << "\n";
+     206           8 :         description = ss.str();
+     207           8 : }
+     208             : 
+     209             : // ----------------------------------------------------------------------------
+     210           5 : SourcePosition::SourcePosition(Vector3d position) :
+     211           5 :                 position(position) {
+     212           5 :         setDescription();
+     213           5 : }
+     214             : 
+     215           0 : SourcePosition::SourcePosition(double d) :
+     216           0 :                 position(Vector3d(d, 0, 0)) {
+     217           0 :         setDescription();
+     218           0 : }
+     219             : 
+     220        1103 : void SourcePosition::prepareParticle(ParticleState& particle) const {
+     221        1103 :         particle.setPosition(position);
+     222        1103 : }
+     223             : 
+     224           5 : void SourcePosition::setDescription() {
+     225           5 :         std::stringstream ss;
+     226           5 :         ss << "SourcePosition: " << position / Mpc << " Mpc\n";
+     227           5 :         description = ss.str();
+     228           5 : }
+     229             : 
+     230             : // ----------------------------------------------------------------------------
+     231           1 : SourceMultiplePositions::SourceMultiplePositions() {
+     232           1 :         setDescription();
+     233           1 : }
+     234             : 
+     235           2 : void SourceMultiplePositions::add(Vector3d pos, double weight) {
+     236           2 :         positions.push_back(pos);
+     237           2 :         if (cdf.size() > 0)
+     238           1 :                 weight += cdf.back();
+     239           2 :         cdf.push_back(weight);
+     240           2 : }
+     241             : 
+     242       10000 : void SourceMultiplePositions::prepareParticle(ParticleState& particle) const {
+     243       10000 :         if (positions.size() == 0)
+     244           0 :                 throw std::runtime_error("SourceMultiplePositions: no position set");
+     245       10000 :         size_t i = Random::instance().randBin(cdf);
+     246       10000 :         particle.setPosition(positions[i]);
+     247       10000 : }
+     248             : 
+     249           1 : void SourceMultiplePositions::setDescription() {
+     250           1 :         std::stringstream ss;
+     251           1 :         ss << "SourceMultiplePositions: Random position from list\n";
+     252           1 :         for (int i = 0; i < positions.size(); i++)
+     253           0 :                 ss << "  " << positions[i] / Mpc << " Mpc\n";
+     254           1 :         description = ss.str();
+     255           1 : }
+     256             : 
+     257             : // ----------------------------------------------------------------------------
+     258           1 : SourceUniformSphere::SourceUniformSphere(Vector3d center, double radius) :
+     259           1 :                 center(center), radius(radius) {
+     260           1 :         setDescription();
+     261           1 : }
+     262             : 
+     263           1 : void SourceUniformSphere::prepareParticle(ParticleState& particle) const {
+     264           1 :         Random &random = Random::instance();
+     265           1 :         double r = pow(random.rand(), 1. / 3.) * radius;
+     266           1 :         particle.setPosition(center + random.randVector() * r);
+     267           1 : }
+     268             : 
+     269           1 : void SourceUniformSphere::setDescription() {
+     270           1 :         std::stringstream ss;
+     271           1 :         ss << "SourceUniformSphere: Random position within a sphere at ";
+     272           1 :         ss << center / Mpc << " Mpc with";
+     273           1 :         ss  << radius / Mpc << " Mpc radius\n";
+     274           1 :         description = ss.str();
+     275           1 : }
+     276             : 
+     277             : // ----------------------------------------------------------------------------
+     278           1 : SourceUniformHollowSphere::SourceUniformHollowSphere(
+     279             :                 Vector3d center,
+     280             :                 double radius_inner,
+     281           1 :                 double radius_outer) :
+     282           1 :                 center(center), radius_inner(radius_inner),
+     283           1 :                 radius_outer(radius_outer) {
+     284           1 :         setDescription();
+     285           1 : }
+     286             : 
+     287         100 : void SourceUniformHollowSphere::prepareParticle(ParticleState& particle) const {
+     288         100 :         Random &random = Random::instance();
+     289         100 :         double r = radius_inner + pow(random.rand(), 1. / 3.) * (radius_outer - radius_inner);
+     290         100 :         particle.setPosition(center + random.randVector() * r);
+     291         100 : }
+     292             : 
+     293           1 : void SourceUniformHollowSphere::setDescription() {
+     294           1 :         std::stringstream ss;
+     295           1 :         ss << "SourceUniformHollowSphere: Random position within a sphere at ";
+     296           1 :         ss << center / Mpc << " Mpc with";
+     297           1 :         ss << radius_inner / Mpc << " Mpc inner radius\n";
+     298           1 :         ss << radius_outer / Mpc << " Mpc outer radius\n";
+     299           1 :         description = ss.str();
+     300           1 : }
+     301             : 
+     302             : // ----------------------------------------------------------------------------
+     303           0 : SourceUniformShell::SourceUniformShell(Vector3d center, double radius) :
+     304           0 :                 center(center), radius(radius) {
+     305           0 :         setDescription();
+     306           0 : }
+     307             : 
+     308           0 : void SourceUniformShell::prepareParticle(ParticleState& particle) const {
+     309           0 :         Random &random = Random::instance();
+     310           0 :         particle.setPosition(center + random.randVector() * radius);
+     311           0 : }
+     312             : 
+     313           0 : void SourceUniformShell::setDescription() {
+     314           0 :         std::stringstream ss;
+     315           0 :         ss << "SourceUniformShell: Random position on a spherical shell at ";
+     316           0 :         ss << center / Mpc << " Mpc with ";
+     317           0 :         ss << radius / Mpc << " Mpc radius\n";
+     318           0 :         description = ss.str();
+     319           0 : }
+     320             : 
+     321             : // ----------------------------------------------------------------------------
+     322           1 : SourceUniformBox::SourceUniformBox(Vector3d origin, Vector3d size) :
+     323           1 :                 origin(origin), size(size) {
+     324           1 :         setDescription();
+     325           1 : }
+     326             : 
+     327           1 : void SourceUniformBox::prepareParticle(ParticleState& particle) const {
+     328           1 :         Random &random = Random::instance();
+     329           1 :         Vector3d pos(random.rand(), random.rand(), random.rand());
+     330           1 :         particle.setPosition(pos * size + origin);
+     331           1 : }
+     332             : 
+     333           1 : void SourceUniformBox::setDescription() {
+     334           1 :         std::stringstream ss;
+     335           1 :         ss << "SourceUniformBox: Random uniform position in box with ";
+     336           1 :         ss << "origin = " << origin / Mpc << " Mpc and ";
+     337           1 :         ss << "size = " << size / Mpc << " Mpc\n";
+     338           1 :         description = ss.str();
+     339           1 : }
+     340             : 
+     341             : // ---------------------------------------------------------------------------
+     342           1 : SourceUniformCylinder::SourceUniformCylinder(Vector3d origin, double height, double radius) :
+     343           1 :     origin(origin), height(height), radius(radius) {
+     344           1 : }
+     345             : 
+     346           1 : void SourceUniformCylinder::prepareParticle(ParticleState& particle) const {
+     347           1 :   Random &random = Random::instance();
+     348           1 :   double phi = 2*M_PI*random.rand();
+     349           1 :   double RandRadius = radius*pow(random.rand(), 1. / 2.);
+     350           1 :   Vector3d pos(cos(phi)*RandRadius, sin(phi)*RandRadius, (-0.5+random.rand())*height);
+     351           1 :   particle.setPosition(pos + origin);
+     352           1 :   }
+     353             : 
+     354           0 : void SourceUniformCylinder::setDescription() {
+     355           0 :         std::stringstream ss;
+     356           0 :         ss << "SourceUniformCylinder: Random uniform position in cylinder with ";
+     357           0 :         ss << "origin = " << origin / Mpc << " Mpc and ";
+     358           0 :         ss << "radius = " << radius / Mpc << " Mpc and";
+     359           0 :         ss << "height = " << height / Mpc << " Mpc\n";
+     360           0 :         description = ss.str();
+     361           0 : }
+     362             : 
+     363             : // ---------------------------------------------------------------------------
+     364           0 : SourceSNRDistribution::SourceSNRDistribution() :
+     365           0 :     rEarth(8.5 * kpc), beta(3.53), zg(0.3 * kpc) {
+     366           0 :         setAlpha(2.);
+     367           0 :         setFrMax();
+     368           0 :         setFzMax(0.3 * kpc);
+     369           0 :         setRMax(20 * kpc);
+     370           0 :         setZMax(5 * kpc);
+     371           0 : }
+     372             : 
+     373           1 : SourceSNRDistribution::SourceSNRDistribution(double rEarth, double alpha, double beta, double zg) :
+     374           1 :     rEarth(rEarth), beta(beta), zg(zg) {
+     375           1 :         setAlpha(alpha);
+     376           1 :         setFrMax();
+     377           1 :         setFzMax(zg);
+     378           1 :         setRMax(20 * kpc);
+     379           1 :         setZMax(5 * kpc);
+     380           1 : }
+     381             : 
+     382      100001 : void SourceSNRDistribution::prepareParticle(ParticleState& particle) const {
+     383      100001 :         Random &random = Random::instance();
+     384             :         double RPos;
+     385             :         while (true) {
+     386      193272 :                 RPos = random.rand() * rMax;
+     387      193272 :                 double fTest = random.rand() * frMax;
+     388      193272 :                 double fR = fr(RPos);
+     389      193272 :                 if (fTest <= fR) {
+     390             :                         break;
+     391             :                 }
+     392             :         }
+     393             :         double ZPos;
+     394             :         while (true) {
+     395     1663640 :                 ZPos = (random.rand() - 0.5) * 2 * zMax;
+     396     1663640 :                 double fTest = random.rand() * fzMax;
+     397     1663640 :                 double fZ=fz(ZPos);
+     398     1663640 :                 if (fTest<=fZ) {
+     399             :                         break;
+     400             :                 }
+     401             :         }
+     402      100001 :         double phi = random.rand() * 2 * M_PI;
+     403      100001 :         Vector3d pos(cos(phi) * RPos, sin(phi) * RPos, ZPos);
+     404      100001 :         particle.setPosition(pos);
+     405      100001 : }
+     406             : 
+     407      193272 : double SourceSNRDistribution::fr(double r) const {
+     408      193272 :         return pow(r / rEarth, alpha) * exp(- beta * (r - rEarth) / rEarth);
+     409             : }
+     410             : 
+     411     1663640 : double SourceSNRDistribution::fz(double z) const{
+     412             :         double Az = 1.;
+     413     1663640 :         double f = 1. / zg * exp(- fabs(z) / zg);
+     414             :         double fz = Az * f;
+     415     1663640 :         return fz;
+     416             : }
+     417             : 
+     418           0 : double SourceSNRDistribution::getAlpha() const {
+     419           0 :         return alpha - 1;  // -1 to account for the R-term in the volume element dV = R * dR * dphi * dz
+     420             : }
+     421             : 
+     422           0 : double SourceSNRDistribution::getBeta() const {
+     423           0 :         return beta;
+     424             : }
+     425             : 
+     426           2 : void SourceSNRDistribution::setFrMax() {
+     427           2 :         frMax = pow(alpha / beta, alpha) * exp(beta - alpha);
+     428           2 :         return;
+     429             : }
+     430             : 
+     431           1 : void SourceSNRDistribution::setFzMax(double zg) {
+     432           1 :         fzMax = 1. / zg;
+     433           1 :         return;
+     434             : }
+     435             : 
+     436           2 : void SourceSNRDistribution::setRMax(double r) {
+     437           2 :         rMax = r;
+     438           2 :         return;
+     439             : }
+     440             : 
+     441           1 : void SourceSNRDistribution::setZMax(double z) {
+     442           1 :         zMax = z;
+     443           1 :         return;
+     444             : }
+     445             : 
+     446           0 : double SourceSNRDistribution::getFrMax() const {
+     447           0 :         return frMax;
+     448             : }
+     449             : 
+     450           0 : double SourceSNRDistribution::getFzMax() const {
+     451           0 :         return fzMax;
+     452             : }
+     453             : 
+     454           0 : double SourceSNRDistribution::getRMax() const {
+     455           0 :         return rMax;
+     456             : }
+     457             : 
+     458           0 : double SourceSNRDistribution::getZMax() const {
+     459           0 :         return zMax;
+     460             : }
+     461             : 
+     462           1 : void SourceSNRDistribution::setAlpha(double a) {
+     463           1 :         alpha = a + 1.; // add 1 for dV = r * dR * dphi * dz
+     464           1 :         setRMax(rMax);
+     465           1 :         setFrMax();
+     466           1 : }
+     467             : 
+     468           0 : void SourceSNRDistribution::setBeta(double b) {
+     469           0 :         beta = b;
+     470           0 :         setRMax(rMax);
+     471           0 :         setFrMax();
+     472           0 : }
+     473             : 
+     474           0 : void SourceSNRDistribution::setDescription() {
+     475           0 :         std::stringstream ss;
+     476           0 :         ss << "SourceSNRDistribution: Random position according to SNR distribution";
+     477           0 :         ss << "rEarth = " << rEarth / kpc << " kpc and ";
+     478           0 :         ss << "zg = " << zg / kpc << " kpc and";
+     479           0 :         ss << "beta = " << beta << " \n";
+     480           0 :         description = ss.str();
+     481           0 : }
+     482             : 
+     483             : // ---------------------------------------------------------------------------
+     484           0 : SourcePulsarDistribution::SourcePulsarDistribution() :
+     485           0 :     rEarth(8.5*kpc), beta(3.53), zg(0.3*kpc) {
+     486           0 :         setFrMax(8.5*kpc, 3.53);
+     487           0 :         setFzMax(0.3*kpc);
+     488           0 :         setRMax(22*kpc);
+     489           0 :         setZMax(5*kpc);
+     490           0 :         setRBlur(0.07);
+     491           0 :         setThetaBlur(0.35/kpc);
+     492           0 : }
+     493             : 
+     494           0 : SourcePulsarDistribution::SourcePulsarDistribution(double rEarth, double beta, double zg, double rB, double tB) :
+     495           0 :     rEarth(rEarth), beta(beta), zg(zg) {
+     496           0 :         setFrMax(rEarth, beta);
+     497           0 :         setFzMax(zg);
+     498           0 :         setRBlur(rB);
+     499           0 :         setThetaBlur(tB);
+     500           0 :         setRMax(22 * kpc);
+     501           0 :         setZMax(5 * kpc);
+     502           0 : }
+     503             : 
+     504           0 : void SourcePulsarDistribution::prepareParticle(ParticleState& particle) const {
+     505           0 :         Random &random = Random::instance();
+     506             :         double Rtilde;
+     507             :         while (true) {
+     508           0 :                 Rtilde = random.rand() * rMax;
+     509           0 :                 double fTest = random.rand() * frMax * 1.1;
+     510           0 :                 double fR = fr(Rtilde);
+     511           0 :                 if (fTest <= fR) {
+     512             :                         break;
+     513             :                 }
+     514             :         }
+     515             :         double ZPos;
+     516             :         while (true) {
+     517           0 :                 ZPos = (random.rand() - 0.5) * 2 * zMax;
+     518           0 :                 double fTest = random.rand() * fzMax;
+     519           0 :                 double fZ = fz(ZPos);
+     520           0 :                 if (fTest <= fZ) {
+     521             :                         break;
+     522             :                 }
+     523             :         }
+     524             : 
+     525           0 :         int i = random.randInt(3);
+     526           0 :         double thetaTilde = ftheta(i, Rtilde);
+     527           0 :         double RPos = blurR(Rtilde);
+     528           0 :         double phi = blurTheta(thetaTilde, Rtilde);
+     529           0 :         Vector3d pos(cos(phi) * RPos, sin(phi) * RPos, ZPos);
+     530             : 
+     531           0 :         particle.setPosition(pos);
+     532           0 :   }
+     533             : 
+     534           0 : double SourcePulsarDistribution::fr(double r) const {
+     535           0 :         double f = r * pow(r / rEarth, 2.) * exp(-beta * (r - rEarth) / rEarth);
+     536           0 :         return f;
+     537             : }
+     538             : 
+     539           0 : double SourcePulsarDistribution::fz(double z) const{
+     540             :         double Az = 1.;
+     541           0 :         double f = 1. / zg * exp(- fabs(z) / zg);
+     542             :         double fz = Az * f;
+     543           0 :         return fz;
+     544             : }
+     545             : 
+     546           0 : double SourcePulsarDistribution::ftheta(int i, double r) const {
+     547           0 :         const double k_0[] = {4.25, 4.25, 4.89, 4.89};
+     548           0 :         const double r_0[] = {3.48 * kpc, 3.48 * kpc, 4.9 * kpc, 4.9 * kpc};
+     549           0 :         const double theta_0[] = {0., 3.14, 2.52, -0.62};
+     550           0 :         double K = k_0[i];
+     551           0 :         double R = r_0[i];
+     552           0 :         double Theta = theta_0[i];
+     553             : 
+     554           0 :         double theta = K * log(r / R) + Theta;
+     555             : 
+     556           0 :         return theta;
+     557             : }
+     558             : 
+     559           0 : double SourcePulsarDistribution::blurR(double rTilde) const {
+     560           0 :         Random &random = Random::instance();
+     561           0 :         return random.randNorm(rTilde, rBlur * rTilde);
+     562             : }
+     563             : 
+     564           0 : double SourcePulsarDistribution::blurTheta(double thetaTilde, double rTilde) const {
+     565           0 :         Random &random = Random::instance();
+     566           0 :         double thetaCorr = (random.rand() - 0.5) * 2 * M_PI;
+     567           0 :         double tau = thetaCorr * exp(- thetaBlur * rTilde);
+     568           0 :         return thetaTilde + tau;
+     569             : }
+     570             : 
+     571           0 : void SourcePulsarDistribution::setFrMax(double R, double b) {
+     572           0 :         double r = 3 * R / b;
+     573           0 :         frMax = fr(r);
+     574           0 : }
+     575             : 
+     576           0 : void SourcePulsarDistribution::setFzMax(double zg) {
+     577           0 :         fzMax = 1. / zg;
+     578           0 :         return;
+     579             : }
+     580             : 
+     581           0 : void SourcePulsarDistribution::setRMax(double r) {
+     582           0 :         rMax = r;
+     583           0 :         return;
+     584             : }
+     585             : 
+     586           0 : void SourcePulsarDistribution::setZMax(double z) {
+     587           0 :         zMax = z;
+     588           0 :         return;
+     589             : }
+     590             : 
+     591           0 : void SourcePulsarDistribution::setRBlur(double r) {
+     592           0 :         rBlur = r;
+     593           0 :         return;
+     594             : }
+     595             : 
+     596           0 : void SourcePulsarDistribution::setThetaBlur(double theta) {
+     597           0 :         thetaBlur = theta;
+     598           0 :         return;
+     599             : }
+     600             : 
+     601           0 : double SourcePulsarDistribution::getFrMax() {
+     602           0 :         return frMax;
+     603             : }
+     604             : 
+     605           0 : double SourcePulsarDistribution::getFzMax() {
+     606           0 :         return fzMax;
+     607             : }
+     608             : 
+     609           0 : double SourcePulsarDistribution::getRMax() {
+     610           0 :         return rMax;
+     611             : }
+     612             : 
+     613           0 : double SourcePulsarDistribution::getZMax() {
+     614           0 :         return zMax;
+     615             : }
+     616             : 
+     617           0 : double SourcePulsarDistribution::getRBlur() {
+     618           0 :         return rBlur;
+     619             : }
+     620             : 
+     621           0 : double SourcePulsarDistribution::getThetaBlur() {
+     622           0 :         return thetaBlur;
+     623             : }
+     624             : 
+     625             : 
+     626           0 : void SourcePulsarDistribution::setDescription() {
+     627           0 :         std::stringstream ss;
+     628           0 :         ss << "SourcePulsarDistribution: Random position according to pulsar distribution";
+     629           0 :         ss << "rEarth = " << rEarth / kpc << " kpc and ";
+     630           0 :         ss << "zg = " << zg / kpc << " kpc and ";
+     631           0 :         ss << "beta = " << beta << " and ";
+     632           0 :         ss << "r_blur = " << rBlur << " and ";
+     633           0 :         ss << "theta blur = " << thetaBlur << "\n";
+     634           0 :         description = ss.str();
+     635           0 : }
+     636             : 
+     637             : // ----------------------------------------------------------------------------
+     638           1 : SourceUniform1D::SourceUniform1D(double minD, double maxD, bool withCosmology) {
+     639           1 :         this->withCosmology = withCosmology;
+     640           1 :         if (withCosmology) {
+     641           1 :                 this->minD = comoving2LightTravelDistance(minD);
+     642           1 :                 this->maxD = comoving2LightTravelDistance(maxD);
+     643             :         } else {
+     644           0 :                 this->minD = minD;
+     645           0 :                 this->maxD = maxD;
+     646             :         }
+     647           1 :         setDescription();
+     648           1 : }
+     649             : 
+     650           1 : void SourceUniform1D::prepareParticle(ParticleState& particle) const {
+     651           1 :         Random& random = Random::instance();
+     652           1 :         double d = random.rand() * (maxD - minD) + minD;
+     653           1 :         if (withCosmology)
+     654           1 :                 d = lightTravel2ComovingDistance(d);
+     655           1 :         particle.setPosition(Vector3d(d, 0, 0));
+     656           1 : }
+     657             : 
+     658           1 : void SourceUniform1D::setDescription() {
+     659           1 :         std::stringstream ss;
+     660           1 :         ss << "SourceUniform1D: Random uniform position in D = ";
+     661           2 :         ss << minD / Mpc << " - " << maxD / Mpc << " Mpc";
+     662           1 :         if (withCosmology)
+     663           1 :                 ss << " (including cosmology)";
+     664           1 :         ss << "\n";
+     665           1 :         description = ss.str();
+     666           1 : }
+     667             : 
+     668             : // ----------------------------------------------------------------------------
+     669           2 : SourceDensityGrid::SourceDensityGrid(ref_ptr<Grid1f> grid) :
+     670           2 :                 grid(grid) {
+     671             :         float sum = 0;
+     672          14 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     673         116 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
+     674        1112 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
+     675        1008 :                                 sum += grid->get(ix, iy, iz);
+     676        1008 :                                 grid->get(ix, iy, iz) = sum;
+     677             :                         }
+     678             :                 }
+     679             :         }
+     680           2 :         setDescription();
+     681           2 : }
+     682             : 
+     683       10001 : void SourceDensityGrid::prepareParticle(ParticleState& particle) const {
+     684       10001 :         Random &random = Random::instance();
+     685             : 
+     686             :         // draw random bin
+     687       10001 :         size_t i = random.randBin(grid->getGrid());
+     688       10001 :         Vector3d pos = grid->positionFromIndex(i);
+     689             : 
+     690             :         // draw uniform position within bin
+     691       10001 :         double dx = random.rand() - 0.5;
+     692       10001 :         double dy = random.rand() - 0.5;
+     693       10001 :         double dz = random.rand() - 0.5;
+     694             :         pos += Vector3d(dx, dy, dz) * grid->getSpacing();
+     695             : 
+     696       10001 :         particle.setPosition(pos);
+     697       10001 : }
+     698             : 
+     699           2 : void SourceDensityGrid::setDescription() {
+     700           2 :         description = "SourceDensityGrid: 3D source distribution according to density grid\n";
+     701           2 : }
+     702             : 
+     703             : // ----------------------------------------------------------------------------
+     704           2 : SourceDensityGrid1D::SourceDensityGrid1D(ref_ptr<Grid1f> grid) :
+     705           2 :                 grid(grid) {
+     706           2 :         if (grid->getNy() != 1)
+     707           0 :                 throw std::runtime_error("SourceDensityGrid1D: Ny != 1");
+     708           2 :         if (grid->getNz() != 1)
+     709           0 :                 throw std::runtime_error("SourceDensityGrid1D: Nz != 1");
+     710             : 
+     711             :         float sum = 0;
+     712          22 :         for (int ix = 0; ix < grid->getNx(); ix++) {
+     713          20 :                 sum += grid->get(ix, 0, 0);
+     714          20 :                 grid->get(ix, 0, 0) = sum;
+     715             :         }
+     716           2 :         setDescription();
+     717           2 : }
+     718             : 
+     719         101 : void SourceDensityGrid1D::prepareParticle(ParticleState& particle) const {
+     720         101 :         Random &random = Random::instance();
+     721             : 
+     722             :         // draw random bin
+     723         101 :         size_t i = random.randBin(grid->getGrid());
+     724         101 :         Vector3d pos = grid->positionFromIndex(i);
+     725             : 
+     726             :         // draw uniform position within bin
+     727         101 :         double dx = random.rand() - 0.5;
+     728         101 :         pos.x += dx * grid->getSpacing().x;
+     729             : 
+     730         101 :         particle.setPosition(pos);
+     731         101 : }
+     732             : 
+     733           2 : void SourceDensityGrid1D::setDescription() {
+     734           2 :         description = "SourceDensityGrid1D: 1D source distribution according to density grid\n";
+     735           2 : }
+     736             : 
+     737             : // ----------------------------------------------------------------------------
+     738           3 : SourceIsotropicEmission::SourceIsotropicEmission() {
+     739           3 :         setDescription();
+     740           3 : }
+     741             : 
+     742        1101 : void SourceIsotropicEmission::prepareParticle(ParticleState& particle) const {
+     743        1101 :         Random &random = Random::instance();
+     744        1101 :         particle.setDirection(random.randVector());
+     745        1101 : }
+     746             : 
+     747           3 : void SourceIsotropicEmission::setDescription() {
+     748           3 :         description = "SourceIsotropicEmission: Random isotropic direction\n";
+     749           3 : }
+     750             : 
+     751             : // ----------------------------------------------------------------------------
+     752           1 : SourceDirectedEmission::SourceDirectedEmission(Vector3d mu, double kappa): mu(mu), kappa(kappa) {
+     753           1 :         if (kappa <= 0)
+     754           0 :                 throw std::runtime_error("The concentration parameter kappa should be larger than 0.");
+     755           1 :         setDescription();
+     756           1 : }
+     757             : 
+     758        1000 : void SourceDirectedEmission::prepareCandidate(Candidate &candidate) const {
+     759        1000 :         Random &random = Random::instance();
+     760             : 
+     761             :         Vector3d muvec = mu / mu.getR();
+     762        1000 :         Vector3d v = random.randFisherVector(muvec, kappa);
+     763             : 
+     764        1000 :         v = v.getUnitVector();
+     765        1000 :         candidate.source.setDirection(v);
+     766        1000 :         candidate.created.setDirection(v);
+     767        1000 :         candidate.previous.setDirection(v);
+     768        1000 :         candidate.current.setDirection(v);
+     769             : 
+     770             :         //set the weight of the particle, see eq. 3.1 of PoS(ICRC2019)447
+     771        1000 :         double pdfVonMises = kappa / (2. * M_PI * (1. - exp(-2. * kappa))) * exp(-kappa * (1. - v.dot(mu)));
+     772        1000 :         double weight = 1. / (4. * M_PI * pdfVonMises);
+     773        1000 :         candidate.setWeight(weight);
+     774        1000 : }
+     775             : 
+     776           1 : void SourceDirectedEmission::setDescription() {
+     777           1 :         std::stringstream ss;
+     778           1 :         ss << "SourceDirectedEmission: Random directed emission following the von-Mises-Fisher distribution with mean direction ";
+     779           1 :         ss << mu << " and concentration parameter kappa = ";
+     780           1 :         ss << kappa << "\n";
+     781           1 :         description = ss.str();
+     782           1 : }
+     783             : 
+     784             : // ----------------------------------------------------------------------------
+     785           0 : SourceLambertDistributionOnSphere::SourceLambertDistributionOnSphere(const Vector3d &center, double radius, bool inward) :
+     786           0 :                 center(center), radius(radius) {
+     787           0 :         this->inward = inward;
+     788           0 :         setDescription();
+     789           0 : }
+     790             : 
+     791           0 : void SourceLambertDistributionOnSphere::prepareParticle(ParticleState& particle) const {
+     792           0 :         Random &random = Random::instance();
+     793           0 :         Vector3d normalVector = random.randVector();
+     794           0 :         particle.setPosition(center + normalVector * radius);
+     795           0 :         double sign = inward ? -1 : 1; // negative (positive) Lamberts vector for inward (outward) directed emission
+     796           0 :         particle.setDirection(Vector3d(0, 0, 0) + sign * random.randVectorLamberts(normalVector));
+     797           0 : }
+     798             : 
+     799           0 : void SourceLambertDistributionOnSphere::setDescription() {
+     800           0 :         std::stringstream ss;
+     801           0 :         ss << "SourceLambertDistributionOnSphere: Random position and direction on a Sphere with center ";
+     802           0 :         ss << center / kpc << " kpc and ";
+     803           0 :         ss << radius / kpc << " kpc radius\n";
+     804           0 :         description = ss.str();
+     805           0 : }
+     806             : 
+     807             : // ----------------------------------------------------------------------------
+     808           0 : SourceDirection::SourceDirection(Vector3d direction) :
+     809           0 :                 direction(direction) {
+     810           0 :         setDescription();
+     811           0 : }
+     812             : 
+     813           0 : void SourceDirection::prepareParticle(ParticleState& particle) const {
+     814           0 :         particle.setDirection(direction);
+     815           0 : }
+     816             : 
+     817           0 : void SourceDirection::setDescription() {
+     818           0 :         std::stringstream ss;
+     819           0 :         ss <<  "SourceDirection: Emission direction = " << direction << "\n";
+     820           0 :         description = ss.str();
+     821           0 : }
+     822             : 
+     823             : // ----------------------------------------------------------------------------
+     824           0 : SourceEmissionMap::SourceEmissionMap(EmissionMap *emissionMap) : emissionMap(emissionMap) {
+     825           0 :         setDescription();
+     826           0 : }
+     827             : 
+     828           0 : void SourceEmissionMap::prepareCandidate(Candidate &candidate) const {
+     829           0 :         if (emissionMap) {
+     830           0 :                 bool accept = emissionMap->checkDirection(candidate.source);
+     831           0 :                 candidate.setActive(accept);
+     832             :         }
+     833           0 : }
+     834             : 
+     835           0 : void SourceEmissionMap::setDescription() {
+     836           0 :         description = "SourceEmissionMap: accept only directions from emission map\n";
+     837           0 : }
+     838             : 
+     839           0 : void SourceEmissionMap::setEmissionMap(EmissionMap *emissionMap) {
+     840           0 :         this->emissionMap = emissionMap;
+     841           0 : }
+     842             : 
+     843             : // ----------------------------------------------------------------------------
+     844           1 : SourceEmissionCone::SourceEmissionCone(Vector3d direction, double aperture) :
+     845           1 :         aperture(aperture) {
+     846           1 :         setDirection(direction);
+     847           1 :         setDescription();
+     848             :         
+     849           1 : }
+     850             : 
+     851           1 : void SourceEmissionCone::prepareParticle(ParticleState& particle) const {
+     852           1 :         Random &random = Random::instance();
+     853           1 :         particle.setDirection(random.randConeVector(direction, aperture));
+     854           1 : }
+     855             : 
+     856           1 : void SourceEmissionCone::setDirection(Vector3d dir) {
+     857           1 :         if (dir.getR() == 0) {
+     858           0 :                 throw std::runtime_error("SourceEmissionCone: The direction vector was a null vector.");
+     859             :         } else {
+     860           1 :                 direction = dir.getUnitVector();
+     861             :         }
+     862           1 : }
+     863             : 
+     864           1 : void SourceEmissionCone::setDescription() {
+     865           1 :         std::stringstream ss;
+     866           1 :         ss << "SourceEmissionCone: Jetted emission in ";
+     867           1 :         ss << "direction = " << direction << " with ";
+     868           1 :         ss << "half-opening angle = " << aperture << " rad\n";
+     869           1 :         description = ss.str();
+     870           1 : }
+     871             : 
+     872             : // ----------------------------------------------------------------------------
+     873           1 : SourceRedshift::SourceRedshift(double z) :
+     874           1 :                 z(z) {
+     875           1 :         setDescription();
+     876           1 : }
+     877             : 
+     878           1 : void SourceRedshift::prepareCandidate(Candidate& candidate) const {
+     879           1 :         candidate.setRedshift(z);
+     880           1 : }
+     881             : 
+     882           1 : void SourceRedshift::setDescription() {
+     883           1 :         std::stringstream ss;
+     884           1 :         ss << "SourceRedshift: Redshift z = " << z << "\n";
+     885           1 :         description = ss.str();
+     886           1 : }
+     887             : 
+     888             : // ----------------------------------------------------------------------------
+     889           0 : SourceUniformRedshift::SourceUniformRedshift(double zmin, double zmax) :
+     890           0 :                 zmin(zmin), zmax(zmax) {
+     891           0 :         setDescription();
+     892           0 : }
+     893             : 
+     894           0 : void SourceUniformRedshift::prepareCandidate(Candidate& candidate) const {
+     895           0 :         double z = Random::instance().randUniform(zmin, zmax);
+     896           0 :         candidate.setRedshift(z);
+     897           0 : }
+     898             : 
+     899           0 : void SourceUniformRedshift::setDescription() {
+     900           0 :         std::stringstream ss;
+     901           0 :         ss << "SourceUniformRedshift: Uniform redshift in z = ";
+     902           0 :         ss << zmin << " - " << zmax << "\n";
+     903           0 :         description = ss.str();
+     904           0 : }
+     905             : 
+     906             : // ----------------------------------------------------------------------------
+     907           2 : SourceRedshiftEvolution::SourceRedshiftEvolution(double m, double zmin, double zmax) : m(m), zmin(zmin), zmax(zmax) {
+     908           2 :         std::stringstream ss;
+     909             :         ss << "SourceRedshiftEvolution: (1+z)^m, m = " << m;
+     910           2 :         ss << ", z = " << zmin << " - " << zmax << "\n";
+     911           2 :         description = ss.str();
+     912           2 : }
+     913             : 
+     914         200 : void SourceRedshiftEvolution::prepareCandidate(Candidate& candidate) const {
+     915         200 :         double x = Random::instance().randUniform(0, 1);
+     916             :         double norm, z;
+     917             : 
+     918             :         // special case: m=-1
+     919         200 :         if ((std::abs(m+1)) < std::numeric_limits<double>::epsilon()) {
+     920         100 :                 norm = log1p(zmax) - log1p(zmin);
+     921         100 :                 z = exp(norm*x) * (1+zmin) - 1;
+     922             :         } else {
+     923         100 :                 norm = ( pow(1+zmax, m+1) - pow(1+zmin, m+1) ) / (m+1);
+     924         100 :                 z = pow( norm*(m+1)*x + pow(1+zmin, m+1), 1./(m+1)) - 1;
+     925             :         }
+     926         200 :         candidate.setRedshift(z);
+     927         200 : }
+     928             : 
+     929             : // ----------------------------------------------------------------------------
+     930           1 : SourceRedshift1D::SourceRedshift1D() {
+     931           1 :         setDescription();
+     932           1 : }
+     933             : 
+     934           1 : void SourceRedshift1D::prepareCandidate(Candidate& candidate) const {
+     935           1 :         double d = candidate.source.getPosition().getR();
+     936           1 :         double z = comovingDistance2Redshift(d);
+     937           1 :         candidate.setRedshift(z);
+     938           1 : }
+     939             : 
+     940           1 : void SourceRedshift1D::setDescription() {
+     941           1 :         description = "SourceRedshift1D: Redshift according to source distance\n";
+     942           1 : }
+     943             : 
+     944             : // ----------------------------------------------------------------------------
+     945             : #ifdef CRPROPA_HAVE_MUPARSER
+     946           1 : SourceGenericComposition::SourceGenericComposition(double Emin, double Emax, std::string expression, size_t bins) :
+     947           2 :         Emin(Emin), Emax(Emax), expression(expression), bins(bins) {
+     948             : 
+     949             :         // precalculate energy bins
+     950           1 :         double logEmin = ::log10(Emin);
+     951           1 :         double logEmax = ::log10(Emax);
+     952           1 :         double logStep = (logEmax - logEmin) / bins;
+     953           1 :         energy.resize(bins + 1);
+     954        1026 :         for (size_t i = 0; i <= bins; i++) {
+     955        1025 :                 energy[i] = ::pow(10, logEmin + i * logStep);
+     956             :         }
+     957           1 :         setDescription();
+     958           1 : }
+     959             : 
+     960           2 : void SourceGenericComposition::add(int id, double weight) {
+     961           2 :         int A = massNumber(id);
+     962           2 :         int Z = chargeNumber(id);
+     963             : 
+     964             :         Nucleus n;
+     965           2 :         n.id = id;
+     966             : 
+     967             :         // calculate nuclei cdf
+     968           2 :         mu::Parser p;
+     969             :         double E;
+     970           2 :         p.DefineVar("E", &E);
+     971           2 :         p.DefineConst("Emin", Emin);
+     972           2 :         p.DefineConst("Emax", Emax);
+     973           2 :         p.DefineConst("bins", bins);
+     974           2 :         p.DefineConst("A", (double)A);
+     975           2 :         p.DefineConst("Z", (double)Z);
+     976             : 
+     977           2 :         p.DefineConst("MeV", MeV);
+     978           2 :         p.DefineConst("GeV", GeV);
+     979           2 :         p.DefineConst("TeV", TeV);
+     980           2 :         p.DefineConst("PeV", PeV);
+     981           2 :         p.DefineConst("EeV", EeV);
+     982             : 
+     983           2 :         p.SetExpr(expression);
+     984             : 
+     985             :         // calculate pdf
+     986           2 :         n.cdf.resize(bins + 1);
+     987             : 
+     988        2052 :         for (std::size_t i=0; i<=bins; ++i) {
+     989        2050 :                 E = energy[i];
+     990        2050 :                 n.cdf[i] = p.Eval();
+     991             :         }
+     992             : 
+     993             :         // integrate
+     994        2050 :         for (std::size_t i=bins; i>0; --i) {
+     995        2048 :                 n.cdf[i] = (n.cdf[i-1] + n.cdf[i]) * (energy[i] - energy[i-1]) / 2;
+     996             :         }
+     997           2 :         n.cdf[0] = 0;
+     998             : 
+     999             :         // cumulate
+    1000        2050 :         for (std::size_t i=1; i<=bins; ++i) {
+    1001        2048 :                 n.cdf[i] += n.cdf[i-1];
+    1002             :         }
+    1003             : 
+    1004           2 :         nuclei.push_back(n);
+    1005             : 
+    1006             :         // update composition cdf
+    1007           2 :         if (cdf.size() == 0)
+    1008           1 :                 cdf.push_back(weight * n.cdf.back());
+    1009             :         else
+    1010           1 :                 cdf.push_back(cdf.back() + weight * n.cdf.back());
+    1011           2 : }
+    1012             : 
+    1013           0 : void SourceGenericComposition::add(int A, int Z, double a) {
+    1014           0 :         add(nucleusId(A, Z), a);
+    1015           0 : }
+    1016             : 
+    1017      100000 : void SourceGenericComposition::prepareParticle(ParticleState& particle) const {
+    1018      100000 :         if (nuclei.size() == 0)
+    1019           0 :                 throw std::runtime_error("SourceComposition: No source isotope set");
+    1020             : 
+    1021      100000 :         Random &random = Random::instance();
+    1022             : 
+    1023             : 
+    1024             :         // draw random particle type
+    1025      100000 :         size_t iN = random.randBin(cdf);
+    1026             :         const Nucleus &n = nuclei.at(iN);
+    1027      100000 :         particle.setId(n.id);
+    1028             : 
+    1029             :         // random energy
+    1030      100000 :         double E = interpolate(random.rand() * n.cdf.back(), n.cdf, energy);
+    1031      100000 :         particle.setEnergy(E);
+    1032      100000 : }
+    1033             : 
+    1034           1 : void SourceGenericComposition::setDescription() {
+    1035           1 :         description = "Generice source composition" + expression;
+    1036           1 : }
+    1037             : 
+    1038             : #endif
+    1039             : 
+    1040             : // ----------------------------------------------------------------------------
+    1041             : 
+    1042           1 : SourceTag::SourceTag(std::string tag) {
+    1043           1 :         setTag(tag);
+    1044           1 : }
+    1045             : 
+    1046           1 : void SourceTag::prepareCandidate(Candidate &cand) const {
+    1047           1 :         cand.setTagOrigin(sourceTag);
+    1048           1 : }
+    1049             : 
+    1050           1 : void SourceTag::setDescription() {
+    1051           1 :         description = "SourceTag: " + sourceTag;
+    1052           1 : }
+    1053             : 
+    1054           1 : void SourceTag::setTag(std::string tag) {
+    1055           1 :         sourceTag = tag;
+    1056           1 :         setDescription();
+    1057           1 : }
+    1058             : 
+    1059             : // ----------------------------------------------------------------------------
+    1060             : 
+    1061           0 : SourceMassDistribution::SourceMassDistribution(ref_ptr<Density> density, double max, double x, double y, double z) : 
+    1062           0 :         density(density), maxDensity(max), xMin(-x), xMax(x), yMin(-y), yMax(y), zMin(-z), zMax(z) {}
+    1063             : 
+    1064           0 : void SourceMassDistribution::setMaximalDensity(double maxDensity) {
+    1065           0 :         if (maxDensity <= 0) {
+    1066           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: maximal density must be larger than 0. Nothing changed.\n";
+    1067           0 :                 return;
+    1068             :         }
+    1069           0 :         this->maxDensity = maxDensity;
+    1070             : }
+    1071             : 
+    1072           0 : void SourceMassDistribution::setXrange(double xMin, double xMax) {
+    1073           0 :         if (xMin > xMax) {
+    1074           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: minimal x-value must not exceed the maximal one\n";
+    1075           0 :                 return;
+    1076             :         }
+    1077           0 :         this -> xMin = xMin;
+    1078           0 :         this -> xMax = xMax;
+    1079             : }
+    1080             : 
+    1081           0 : void SourceMassDistribution::setYrange(double yMin, double yMax) {
+    1082           0 :         if (yMin > yMax) {
+    1083           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: minimal y-value must not exceed the maximal one\n";
+    1084           0 :                 return;
+    1085             :         }
+    1086           0 :         this -> yMin = yMin;
+    1087           0 :         this -> yMax = yMax;
+    1088             : }
+    1089             : 
+    1090           0 : void SourceMassDistribution::setZrange(double zMin, double zMax) {
+    1091           0 :         if (zMin > zMax) {
+    1092           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: minimal z-value must not exceed the maximal one\n";
+    1093           0 :                 return;
+    1094             :         }
+    1095           0 :         this -> zMin = zMin;
+    1096           0 :         this -> zMax = zMax;
+    1097             : }
+    1098             : 
+    1099           0 : Vector3d SourceMassDistribution::samplePosition() const {
+    1100             :         Vector3d pos; 
+    1101           0 :         Random &rand = Random::instance();
+    1102             : 
+    1103           0 :         for (int i = 0; i < maxTries; i++) {
+    1104           0 :                 pos.x = rand.randUniform(xMin, xMax);
+    1105           0 :                 pos.y = rand.randUniform(yMin, yMax);
+    1106           0 :                 pos.z = rand.randUniform(zMin, zMax);
+    1107             : 
+    1108           0 :                 double n_density = density->getDensity(pos) / maxDensity;
+    1109           0 :                 double n_test = rand.rand();
+    1110           0 :                 if (n_test < n_density) {
+    1111             :                         return pos;
+    1112             :                 }
+    1113             :         }
+    1114           0 :         KISS_LOG_WARNING << "SourceMassDistribution: sampling a position was not possible within " 
+    1115           0 :                 << maxTries << " tries. Please check the maximum density or increse the number of maximal tries. \n";
+    1116             :         return Vector3d(0.);
+    1117             : }       
+    1118             : 
+    1119           0 : void SourceMassDistribution::prepareParticle(ParticleState &state) const {
+    1120           0 :         Vector3d pos = samplePosition();
+    1121           0 :         state.setPosition(pos);
+    1122           0 : }
+    1123             : 
+    1124           0 : void SourceMassDistribution::setMaximalTries(int tries) {
+    1125           0 :         this -> maxTries = tries;
+    1126           0 : }
+    1127             : 
+    1128           0 : std::string SourceMassDistribution::getDescription() {
+    1129           0 :         std::stringstream ss;
+    1130           0 :         ss << "SourceMassDistribuion: following the density distribution :\n";
+    1131           0 :         ss << "\t" << density -> getDescription();
+    1132           0 :         ss << "with a maximal density of " << maxDensity << " / m^3 \n";
+    1133           0 :         ss << "using the sampling range: \n";
+    1134           0 :         ss << "\t x in [" << xMin / kpc << " ; " << xMax / kpc << "] kpc \n";
+    1135           0 :         ss << "\t y in [" << yMin / kpc << " ; " << yMax / kpc << "] kpc \n";
+    1136           0 :         ss << "\t z in [" << zMin / kpc << " ; " << zMax / kpc << "] kpc \n";
+    1137           0 :         ss << "with maximal number of tries for sampling of " << maxTries << "\n";
+    1138             : 
+    1139           0 :         return ss.str();
+    1140           0 : }
+    1141             : 
+    1142             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Variant.cpp.func-sort-c.html b/doc/coverageReport/src/Variant.cpp.func-sort-c.html new file mode 100644 index 000000000..3bcf5eae5 --- /dev/null +++ b/doc/coverageReport/src/Variant.cpp.func-sort-c.html @@ -0,0 +1,264 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Variant.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Variant.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7151913.7 %
Date:2024-04-08 14:58:22Functions:184837.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Variant11getTypeNameENS0_4TypeE0
_ZN7crpropa7Variant6resizeEm0
_ZN7crpropa7Variant6toTypeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa7VariantC2ENS0_4TypeE0
_ZN7crpropa7VariantcvRSt6vectorIS0_SaIS0_EEEv0
_ZN7crpropa7VariantixEm0
_ZN7crpropalsERSoRKNS_7VariantE0
_ZNK7crpropa7Variant10toVector3cEv0
_ZNK7crpropa7Variant10toVector3dEv0
_ZNK7crpropa7Variant10toVector3fEv0
_ZNK7crpropa7Variant11getTypeNameEv0
_ZNK7crpropa7Variant12toLongDoubleEv0
_ZNK7crpropa7Variant14toComplexFloatEv0
_ZNK7crpropa7Variant15toComplexDoubleEv0
_ZNK7crpropa7Variant4sizeEv0
_ZNK7crpropa7Variant6toCharEv0
_ZNK7crpropa7Variant7getSizeEv0
_ZNK7crpropa7Variant7toFloatEv0
_ZNK7crpropa7Variant7toInt16Ev0
_ZNK7crpropa7Variant7toInt32Ev0
_ZNK7crpropa7Variant7toUCharEv0
_ZNK7crpropa7Variant8toUInt16Ev0
_ZNK7crpropa7Variant8toUInt32Ev0
_ZNK7crpropa7Variant8toUInt64Ev0
_ZNK7crpropa7Variant8toVectorEv0
_ZNK7crpropa7Variant9getSizeOfEv0
_ZNK7crpropa7VariantcvRKSt6vectorIS0_SaIS0_EEEv0
_ZNK7crpropa7VariantixEm0
_ZNK7crpropa7VariantneEPKc0
_ZNK7crpropa7VariantneERKS0_0
_ZN7crpropa7Variant12copyToBufferEPv1
_ZN7crpropa7Variant10fromStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS0_4TypeE2
_ZNK7crpropa7Variant5checkENS0_4TypeE2
_ZNK7crpropa7Variant6toBoolEv2
_ZNK7crpropa7Variant7toInt64Ev2
_ZN7crpropa7VariantC2EPKc3
_ZNK7crpropa7VarianteqERKS0_4
_ZNK7crpropa7Variant8toDoubleEv6
_ZNK7crpropa7Variant8toStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE6
_ZNK7crpropa7Variant7isValidEv8
_ZNK7crpropa7Variant11getTypeInfoEv60
_ZN7crpropa7VariantC2Ev1147
_ZN7crpropa7VariantaSERKS0_1153
_ZN7crpropa7VariantC2ERKS0_2306
_ZN7crpropa7Variant4copyERKS0_3459
_ZN7crpropa7VariantD2Ev4610
_ZN7crpropa7Variant5clearENS0_4TypeE5785
_ZN7crpropa7Variant5checkENS0_4TypeE5793
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Variant.cpp.func.html b/doc/coverageReport/src/Variant.cpp.func.html new file mode 100644 index 000000000..878d842c0 --- /dev/null +++ b/doc/coverageReport/src/Variant.cpp.func.html @@ -0,0 +1,264 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Variant.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Variant.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7151913.7 %
Date:2024-04-08 14:58:22Functions:184837.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Variant10fromStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS0_4TypeE2
_ZN7crpropa7Variant11getTypeNameENS0_4TypeE0
_ZN7crpropa7Variant12copyToBufferEPv1
_ZN7crpropa7Variant4copyERKS0_3459
_ZN7crpropa7Variant5checkENS0_4TypeE5793
_ZN7crpropa7Variant5clearENS0_4TypeE5785
_ZN7crpropa7Variant6resizeEm0
_ZN7crpropa7Variant6toTypeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa7VariantC2ENS0_4TypeE0
_ZN7crpropa7VariantC2EPKc3
_ZN7crpropa7VariantC2ERKS0_2306
_ZN7crpropa7VariantC2Ev1147
_ZN7crpropa7VariantD2Ev4610
_ZN7crpropa7VariantaSERKS0_1153
_ZN7crpropa7VariantcvRSt6vectorIS0_SaIS0_EEEv0
_ZN7crpropa7VariantixEm0
_ZN7crpropalsERSoRKNS_7VariantE0
_ZNK7crpropa7Variant10toVector3cEv0
_ZNK7crpropa7Variant10toVector3dEv0
_ZNK7crpropa7Variant10toVector3fEv0
_ZNK7crpropa7Variant11getTypeInfoEv60
_ZNK7crpropa7Variant11getTypeNameEv0
_ZNK7crpropa7Variant12toLongDoubleEv0
_ZNK7crpropa7Variant14toComplexFloatEv0
_ZNK7crpropa7Variant15toComplexDoubleEv0
_ZNK7crpropa7Variant4sizeEv0
_ZNK7crpropa7Variant5checkENS0_4TypeE2
_ZNK7crpropa7Variant6toBoolEv2
_ZNK7crpropa7Variant6toCharEv0
_ZNK7crpropa7Variant7getSizeEv0
_ZNK7crpropa7Variant7isValidEv8
_ZNK7crpropa7Variant7toFloatEv0
_ZNK7crpropa7Variant7toInt16Ev0
_ZNK7crpropa7Variant7toInt32Ev0
_ZNK7crpropa7Variant7toInt64Ev2
_ZNK7crpropa7Variant7toUCharEv0
_ZNK7crpropa7Variant8toDoubleEv6
_ZNK7crpropa7Variant8toStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE6
_ZNK7crpropa7Variant8toUInt16Ev0
_ZNK7crpropa7Variant8toUInt32Ev0
_ZNK7crpropa7Variant8toUInt64Ev0
_ZNK7crpropa7Variant8toVectorEv0
_ZNK7crpropa7Variant9getSizeOfEv0
_ZNK7crpropa7VariantcvRKSt6vectorIS0_SaIS0_EEEv0
_ZNK7crpropa7VarianteqERKS0_4
_ZNK7crpropa7VariantixEm0
_ZNK7crpropa7VariantneEPKc0
_ZNK7crpropa7VariantneERKS0_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/Variant.cpp.gcov.html b/doc/coverageReport/src/Variant.cpp.gcov.html new file mode 100644 index 000000000..b1925926a --- /dev/null +++ b/doc/coverageReport/src/Variant.cpp.gcov.html @@ -0,0 +1,1200 @@ + + + + + + + LCOV - coverage.info.cleaned - src/Variant.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - Variant.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7151913.7 %
Date:2024-04-08 14:58:22Functions:184837.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : //-------------------------------------------------------------
+       2             : // Based on Variant.cc in the Physics eXtension Library (PXL) -
+       3             : // http://vispa.physik.rwth-aachen.de/                        -
+       4             : // Licensed under a LGPL-2 or later license                   -
+       5             : //-------------------------------------------------------------
+       6             : 
+       7             : #include "crpropa/Variant.h"
+       8             : 
+       9             : 
+      10             : namespace crpropa {
+      11             : 
+      12             : 
+      13        1147 : Variant::Variant() : type(TYPE_NONE) {
+      14        1147 : }
+      15             : 
+      16           0 : Variant::Variant(Type t) : type(TYPE_NONE) {
+      17           0 :         check(t);
+      18           0 : }
+      19             : 
+      20        2306 : Variant::Variant(const Variant& v) : type(TYPE_NONE) {
+      21        2306 :         copy(v);
+      22        2306 : }
+      23             : 
+      24           3 : Variant::Variant(const char* s) {
+      25           3 :         data._t_string = new std::string(s);
+      26           3 :         type = TYPE_STRING;
+      27           3 : }
+      28             : 
+      29        4610 : Variant::~Variant() {
+      30        4610 :         clear();
+      31        4610 : }
+      32             : 
+      33           0 : const char* Variant::getTypeName() const {
+      34           0 :         return getTypeName(type);
+      35             : }
+      36             : 
+      37           0 : const char* Variant::getTypeName(Type t) {
+      38             :         if (t == TYPE_NONE)
+      39             :                 return "none";
+      40             :         else if (t == TYPE_BOOL)
+      41           0 :                 return "bool";
+      42             :         else if (t == TYPE_CHAR)
+      43           0 :                 return "char";
+      44             :         else if (t == TYPE_UCHAR)
+      45           0 :                 return "uchar";
+      46             :         else if (t == TYPE_INT16)
+      47           0 :                 return "int16";
+      48             :         else if (t == TYPE_UINT16)
+      49           0 :                 return "uint16";
+      50             :         else if (t == TYPE_INT32)
+      51           0 :                 return "int32";
+      52             :         else if (t == TYPE_UINT32)
+      53           0 :                 return "uint32";
+      54             :         else if (t == TYPE_INT64)
+      55           0 :                 return "int64";
+      56             :         else if (t == TYPE_UINT64)
+      57           0 :                 return "uint64";
+      58             :         else if (t == TYPE_FLOAT)
+      59           0 :                 return "float";
+      60             :         else if (t == TYPE_DOUBLE)
+      61           0 :                 return "double";
+      62             :         else if (t == TYPE_LONGDOUBLE)
+      63           0 :                 return "ldouble";
+      64             :         else if (t == TYPE_COMPLEXF)
+      65           0 :                 return "complex_f";
+      66             :         else if (t == TYPE_COMPLEXD)
+      67           0 :                 return "complex_d";
+      68             :         else if (t == TYPE_STRING)
+      69           0 :                 return "string";
+      70             :         else if (t == TYPE_VECTOR3F)
+      71           0 :                 return "Vector3f";
+      72             :         else if (t == TYPE_VECTOR3D)
+      73           0 :                 return "Vector3d";
+      74             :         else if (t == TYPE_VECTOR3C)
+      75           0 :                 return "Vector3c";
+      76             :         else if (t == TYPE_VECTOR)
+      77           0 :                 return "vector";
+      78             :         else
+      79           0 :                 return "unknown";
+      80             : }
+      81             : 
+      82          60 : const std::type_info& Variant::getTypeInfo() const {
+      83          60 :         if (type == TYPE_BOOL) {
+      84             :                 const std::type_info& ti = typeid(data._t_bool);
+      85             :                 return ti;
+      86             :         } else if (type == TYPE_CHAR) {
+      87             :                 const std::type_info& ti = typeid(data._t_char);
+      88             :                 return ti;
+      89             :         } else if (type == TYPE_UCHAR) {
+      90             :                 const std::type_info& ti = typeid(data._t_uchar);
+      91           0 :                 return ti;
+      92             :         } else if (type == TYPE_INT16) {
+      93             :                 const std::type_info& ti = typeid(data._t_int16);
+      94           0 :                 return ti;
+      95             :         } else if (type == TYPE_UINT16) {
+      96             :                 const std::type_info& ti = typeid(data._t_uint16);
+      97           0 :                 return ti;
+      98             :         } else if (type == TYPE_INT32) {
+      99             :                 const std::type_info& ti = typeid(data._t_int32);
+     100          12 :                 return ti;
+     101             :         } else if (type == TYPE_UINT32) {
+     102             :                 const std::type_info& ti = typeid(data._t_uint32);
+     103           0 :                 return ti;
+     104             :         } else if (type == TYPE_INT64) {
+     105             :                 const std::type_info& ti = typeid(data._t_int64);
+     106           0 :                 return ti;
+     107             :         } else if (type == TYPE_UINT64) {
+     108             :                 const std::type_info& ti = typeid(data._t_uint64);
+     109           0 :                 return ti;
+     110             :         } else if (type == TYPE_FLOAT) {
+     111             :                 const std::type_info& ti = typeid(data._t_float);
+     112           0 :                 return ti;
+     113             :         } else if (type == TYPE_DOUBLE) {
+     114             :                 const std::type_info& ti = typeid(data._t_double);
+     115          22 :                 return ti;
+     116             :         } else if (type == TYPE_LONGDOUBLE)     {
+     117             :                 const std::type_info& ti = typeid(data._t_ldouble);
+     118           0 :                 return ti;
+     119             :         } else if (type == TYPE_STRING) {
+     120             :                 const std::type_info& ti = typeid(*data._t_string);
+     121          24 :                 return ti;
+     122             :         } else if (type == TYPE_COMPLEXF) { // pointer needed?
+     123             :                 const std::type_info& ti = typeid(*data._t_complex_f);
+     124           0 :                 return ti;
+     125             :         } else if (type == TYPE_COMPLEXD) {
+     126             :                 const std::type_info& ti = typeid(*data._t_complex_d);
+     127           0 :                 return ti;
+     128             :         } else if (type == TYPE_VECTOR3D) {
+     129             :                 const std::type_info& ti = typeid(data._t_vector3d);
+     130           0 :                 return ti;
+     131             :         } else if (type == TYPE_VECTOR3F) {
+     132             :                 const std::type_info& ti = typeid(data._t_vector3f);
+     133           0 :                 return ti;
+     134             :         } else if (type == TYPE_VECTOR) {
+     135             :                 const std::type_info& ti = typeid(*data._t_vector);
+     136           0 :                 return ti;
+     137             :         } else {
+     138             :                 const std::type_info& ti = typeid(0);
+     139           0 :                 return ti;
+     140             :         }
+     141             : }
+     142             : 
+     143           0 : Variant::Type Variant::toType(const std::string& name) {
+     144           0 :         if (name == "none")
+     145             :                 return TYPE_NONE;
+     146           0 :         else if (name == "bool")
+     147             :                 return TYPE_BOOL;
+     148           0 :         else if (name == "char") 
+     149             :                 return TYPE_CHAR;
+     150           0 :         else if (name == "uchar")
+     151             :                 return TYPE_UCHAR;
+     152           0 :         else if (name == "int16")
+     153             :                 return TYPE_INT16;
+     154           0 :         else if (name == "uint16")
+     155             :                 return TYPE_UINT16;
+     156           0 :         else if (name == "int32")
+     157             :                 return TYPE_INT32;
+     158           0 :         else if (name == "uint32")
+     159             :                 return TYPE_UINT32;
+     160           0 :         else if (name == "int64")
+     161             :                 return TYPE_INT64;
+     162           0 :         else if (name == "uint64")
+     163             :                 return TYPE_UINT64;
+     164           0 :         else if (name == "float")
+     165             :                 return TYPE_FLOAT;
+     166           0 :         else if (name == "double")
+     167             :                 return TYPE_DOUBLE;
+     168           0 :         else if (name == "long double")
+     169             :                 return TYPE_LONGDOUBLE;
+     170           0 :         else if (name == "complex_f")
+     171             :                 return TYPE_COMPLEXF;
+     172           0 :         else if (name == "complex_d")
+     173             :                 return TYPE_COMPLEXD;
+     174           0 :          else if (name == "string")
+     175             :                 return TYPE_STRING;
+     176           0 :         else if (name == "Vector3f")
+     177             :                 return TYPE_VECTOR3F;
+     178           0 :         else if (name == "Vector3d")
+     179             :                 return TYPE_VECTOR3D;
+     180           0 :         else if (name == "Vector3c")
+     181             :                 return TYPE_VECTOR3C;
+     182           0 :         else if (name == "vector")
+     183             :                 return TYPE_VECTOR;
+     184             :         else
+     185           0 :                 return TYPE_NONE;
+     186             : }
+     187             : 
+     188           2 : bool Variant::toBool() const {
+     189           2 :         switch (type) {
+     190           2 :                 case TYPE_BOOL:
+     191           2 :                         return data._t_bool;
+     192             :                         break;
+     193           0 :                 case TYPE_CHAR:
+     194           0 :                         return data._t_char != 0;
+     195             :                         break;
+     196           0 :                 case TYPE_UCHAR:
+     197           0 :                         return data._t_uchar != 0;
+     198             :                         break;
+     199           0 :                 case TYPE_INT16:
+     200           0 :                         return data._t_int16 != 0;
+     201             :                         break;
+     202           0 :                 case TYPE_UINT16:
+     203           0 :                         return data._t_uint16 != 0;
+     204             :                         break;
+     205           0 :                 case TYPE_INT32:
+     206           0 :                         return data._t_int32 != 0;
+     207             :                         break;
+     208           0 :                 case TYPE_UINT32:
+     209           0 :                         return data._t_uint32 != 0;
+     210             :                         break;
+     211           0 :                 case TYPE_INT64:
+     212           0 :                         return data._t_int64 != 0;
+     213             :                         break;
+     214           0 :                 case TYPE_UINT64:
+     215           0 :                         return data._t_uint64 != 0;
+     216             :                         break;
+     217           0 :                 case TYPE_STRING: {
+     218           0 :                                 std::string upperstr(*data._t_string);
+     219             :                                 std::transform(upperstr.begin(), upperstr.end(), upperstr.begin(), (int(*) (int)) toupper);
+     220           0 :                                 if (upperstr == "YES" || upperstr == "TRUE" || upperstr == "1")
+     221           0 :                                         return true;
+     222           0 :                                 else if (upperstr == "NO" || upperstr == "FALSE" || upperstr == "0")
+     223           0 :                                         return false;
+     224             :                                 else
+     225           0 :                                         throw bad_conversion(type, TYPE_BOOL);
+     226             :                         }
+     227             :                         break;
+     228           0 :                 case TYPE_COMPLEXF: {
+     229           0 :                                 if (data._t_complex_f->real() == 0 && data._t_complex_f->imag() == 0)
+     230           0 :                                         return true;
+     231             :                                 else
+     232             :                                         return false;
+     233             :                         }
+     234             :                         break;
+     235           0 :                 case TYPE_COMPLEXD: {
+     236           0 :                                 if (data._t_complex_d->real() == 0 && data._t_complex_d->imag() == 0)
+     237           0 :                                         return true;
+     238             :                                 else
+     239             :                                         return false;
+     240             :                         }
+     241             :                         break;
+     242           0 :                 case TYPE_VECTOR:
+     243           0 :                         return data._t_vector->size() != 0;
+     244             :                         break;
+     245           0 :                 case TYPE_FLOAT:
+     246             :                 case TYPE_DOUBLE:
+     247             :                 case TYPE_LONGDOUBLE:
+     248             :                 default:
+     249           0 :                         throw bad_conversion(type, TYPE_BOOL);
+     250             :                         break;
+     251             :         }
+     252             : 
+     253             :         return false;
+     254             : }
+     255             : 
+     256           0 : float Variant::toFloat() const {
+     257           0 :         switch (type) {
+     258           0 :                 case TYPE_BOOL:
+     259           0 :                         return data._t_bool ? (float) 1.0 : (float) 0.0; 
+     260             :                         break;
+     261           0 :                 case TYPE_CHAR:
+     262           0 :                         return static_cast<float>(data._t_char);
+     263             :                         break;
+     264           0 :                 case TYPE_UCHAR:
+     265           0 :                         return static_cast<float>(data._t_uchar);
+     266             :                         break;
+     267           0 :                 case TYPE_INT16:
+     268           0 :                         return static_cast<float>(data._t_int16);
+     269             :                         break;
+     270           0 :                 case TYPE_INT32:
+     271           0 :                         return static_cast<float>(data._t_int32);
+     272             :                         break;
+     273           0 :                 case TYPE_INT64:
+     274           0 :                         return static_cast<float>(data._t_int64);
+     275             :                         break;
+     276           0 :                 case TYPE_UINT16:
+     277           0 :                         return static_cast<float>(data._t_uint16);
+     278             :                         break;
+     279           0 :                 case TYPE_UINT32:
+     280           0 :                         return static_cast<float>(data._t_uint32);
+     281             :                         break;
+     282           0 :                 case TYPE_UINT64:
+     283           0 :                         return static_cast<float>(data._t_uint64);
+     284             :                         break;
+     285           0 :                 case TYPE_FLOAT:
+     286           0 :                         return static_cast<float>(data._t_float);
+     287             :                         break;
+     288           0 :                 case TYPE_DOUBLE:
+     289           0 :                         return static_cast<float>(data._t_double);
+     290             :                         break;
+     291           0 :                 case TYPE_LONGDOUBLE:
+     292           0 :                         return static_cast<float>(data._t_ldouble);
+     293             :                         break;
+     294           0 :                 case TYPE_STRING:
+     295           0 :                         return static_cast<float>(std::atof(data._t_string->c_str()));
+     296             :                         break;
+     297           0 :                 case TYPE_COMPLEXF: {
+     298           0 :                                 if (data._t_complex_f->imag() == 0)
+     299           0 :                                         return static_cast<float>(data._t_complex_f->real());
+     300             :                                 else
+     301           0 :                                         throw bad_conversion(type, TYPE_COMPLEXF);
+     302             :                         }
+     303             :                         break;
+     304           0 :                 case TYPE_COMPLEXD: {
+     305           0 :                                 if (data._t_complex_d->imag() == 0)
+     306           0 :                                         return static_cast<float>(data._t_complex_d->real());
+     307             :                                 else
+     308           0 :                                         throw bad_conversion(type, TYPE_COMPLEXD);
+     309             :                         }
+     310             :                         break;
+     311           0 :                 default:
+     312           0 :                         throw bad_conversion(type, TYPE_FLOAT);
+     313             :                         break;
+     314             :         }
+     315             : 
+     316             :         return 0.;
+     317             : }
+     318             : 
+     319           6 : double Variant::toDouble() const {
+     320           6 :         switch (type) {
+     321           0 :                 case TYPE_BOOL:
+     322           0 :                         return data._t_bool ? (double) 1.0 : (double) 0.0; 
+     323             :                         break;
+     324           0 :                 case TYPE_CHAR:
+     325           0 :                         return static_cast<double>(data._t_char);
+     326             :                         break;
+     327           0 :                 case TYPE_UCHAR:
+     328           0 :                         return static_cast<double>(data._t_uchar);
+     329             :                         break;
+     330           0 :                 case TYPE_INT16:
+     331           0 :                         return static_cast<double>(data._t_int16);
+     332             :                         break;
+     333           0 :                 case TYPE_INT32:
+     334           0 :                         return static_cast<double>(data._t_int32);
+     335             :                         break;
+     336           0 :                 case TYPE_INT64:
+     337           0 :                         return static_cast<double>(data._t_int64);
+     338             :                         break;
+     339           0 :                 case TYPE_UINT16:
+     340           0 :                         return static_cast<double>(data._t_uint16);
+     341             :                         break;
+     342           0 :                 case TYPE_UINT32:
+     343           0 :                         return static_cast<double>(data._t_uint32);
+     344             :                         break;
+     345           0 :                 case TYPE_UINT64:
+     346           0 :                         return static_cast<double>(data._t_uint64);
+     347             :                         break;
+     348           0 :                 case TYPE_FLOAT:
+     349           0 :                         return static_cast<double>(data._t_float);
+     350             :                         break;
+     351           6 :                 case TYPE_DOUBLE:
+     352           6 :                         return static_cast<double>(data._t_double);
+     353             :                         break;
+     354           0 :                 case TYPE_LONGDOUBLE:
+     355           0 :                         return static_cast<double>(data._t_ldouble);
+     356             :                         break;
+     357           0 :                 case TYPE_COMPLEXF: {
+     358           0 :                                 if (data._t_complex_f->imag() == 0)
+     359           0 :                                         return static_cast<double>(data._t_complex_f->real());
+     360             :                                 else
+     361           0 :                                         throw bad_conversion(type, TYPE_COMPLEXF);
+     362             :                         }
+     363             :                         break;
+     364           0 :                 case TYPE_COMPLEXD: {
+     365           0 :                                 if (data._t_complex_d->imag() == 0)
+     366           0 :                                         return static_cast<double>(data._t_complex_d->real());
+     367             :                                 else
+     368           0 :                                         throw bad_conversion(type, TYPE_COMPLEXD);
+     369             :                         }
+     370             :                         break;
+     371           0 :                 case TYPE_STRING:
+     372           0 :                         return static_cast<double>(std::atof(data._t_string->c_str()));
+     373             :                         break;
+     374           0 :                 default:
+     375           0 :                         throw bad_conversion(type, TYPE_DOUBLE);
+     376             :                         break;
+     377             :         }
+     378             : 
+     379             :         return 0.;
+     380             : }
+     381             : 
+     382           0 : long double Variant::toLongDouble() const {
+     383           0 :         switch (type) {
+     384           0 :                 case TYPE_BOOL:
+     385           0 :                         return data._t_bool ? (long double) 1.0 : (long double) 0.0; 
+     386             :                         break;
+     387           0 :                 case TYPE_CHAR:
+     388           0 :                         return static_cast<long double>(data._t_char);
+     389             :                         break;
+     390           0 :                 case TYPE_UCHAR:
+     391           0 :                         return static_cast<long double>(data._t_uchar);
+     392             :                         break;
+     393           0 :                 case TYPE_INT16:
+     394           0 :                         return static_cast<long double>(data._t_int16);
+     395             :                         break;
+     396           0 :                 case TYPE_INT32:
+     397           0 :                         return static_cast<long double>(data._t_int32);
+     398             :                         break;
+     399           0 :                 case TYPE_INT64:
+     400           0 :                         return static_cast<long double>(data._t_int64);
+     401             :                         break;
+     402           0 :                 case TYPE_UINT16:
+     403           0 :                         return static_cast<long double>(data._t_uint16);
+     404             :                         break;
+     405           0 :                 case TYPE_UINT32:
+     406           0 :                         return static_cast<long double>(data._t_uint32);
+     407             :                         break;
+     408           0 :                 case TYPE_UINT64:
+     409           0 :                         return static_cast<long double>(data._t_uint64);
+     410             :                         break;
+     411           0 :                 case TYPE_FLOAT:
+     412           0 :                         return static_cast<long double>(data._t_float);
+     413             :                         break;
+     414           0 :                 case TYPE_DOUBLE:
+     415           0 :                         return static_cast<long double>(data._t_double);
+     416             :                         break;
+     417           0 :                 case TYPE_LONGDOUBLE:
+     418           0 :                         return static_cast<long double>(data._t_ldouble);
+     419             :                         break;
+     420           0 :                 case TYPE_COMPLEXF: {
+     421           0 :                                 if (data._t_complex_f->imag() == 0)
+     422           0 :                                         return static_cast<long double>(data._t_complex_f->real());
+     423             :                                 else
+     424           0 :                                         throw bad_conversion(type, TYPE_COMPLEXF);
+     425             :                         }
+     426             :                         break;
+     427           0 :                 case TYPE_COMPLEXD: {
+     428           0 :                                 if (data._t_complex_d->imag() == 0)
+     429           0 :                                         return static_cast<long double>(data._t_complex_d->real());
+     430             :                                 else
+     431           0 :                                         throw bad_conversion(type, TYPE_COMPLEXD);
+     432             :                         }
+     433             :                         break;
+     434           0 :                 case TYPE_STRING:
+     435           0 :                         return static_cast<double>(std::atof(data._t_string->c_str()));
+     436             :                         break;
+     437           0 :                 default:
+     438           0 :                         throw bad_conversion(type, TYPE_LONGDOUBLE);
+     439             :                         break;
+     440             :         }
+     441             : 
+     442             :         return 0.;
+     443             : }
+     444             : 
+     445           0 : std::complex<float> Variant::toComplexFloat() const {
+     446           0 :         switch (type) {
+     447           0 :                 case TYPE_COMPLEXF:
+     448           0 :                         return static_cast<std::complex<float>>(*data._t_complex_f);
+     449             :                         break;
+     450           0 :                 case TYPE_COMPLEXD:
+     451           0 :                         return static_cast<std::complex<float>>(*data._t_complex_d);
+     452             :                         break;
+     453           0 :                 default:
+     454           0 :                         throw bad_conversion(type, TYPE_COMPLEXF);
+     455             :                         break;
+     456             :         }
+     457             : }  
+     458             : 
+     459           0 : std::complex<double> Variant::toComplexDouble() const {
+     460           0 :         switch (type) {
+     461           0 :                 case TYPE_COMPLEXF:
+     462           0 :                         return static_cast<std::complex<double>>(*data._t_complex_f);
+     463             :                         break;
+     464           0 :                 case TYPE_COMPLEXD:
+     465           0 :                         return static_cast<std::complex<double>>(*data._t_complex_d);
+     466             :                         break;
+     467           0 :                 default:
+     468           0 :                         throw bad_conversion(type, TYPE_COMPLEXD);
+     469             :                         break;
+     470             :         }
+     471             : }  
+     472             : 
+     473           0 : Vector3f Variant::toVector3f() const {
+     474           0 :         switch (type) {
+     475           0 :                 case TYPE_VECTOR3F:
+     476           0 :                         return static_cast<Vector3f>(*data._t_vector3f);
+     477             :                         break;
+     478           0 :                 case TYPE_VECTOR3D:
+     479           0 :                         return static_cast<Vector3f>(*data._t_vector3d);
+     480             :                         break;
+     481           0 :                 default:
+     482           0 :                         throw bad_conversion(type, TYPE_VECTOR3F);
+     483             :                         break;
+     484             :         }
+     485             : }
+     486             : 
+     487           0 : Vector3d Variant::toVector3d() const {
+     488           0 :         switch (type) {
+     489           0 :                 case TYPE_VECTOR3F:
+     490           0 :                         return static_cast<Vector3d>(*data._t_vector3f);
+     491             :                         break;
+     492           0 :                 case TYPE_VECTOR3D:
+     493           0 :                         return static_cast<Vector3d>(*data._t_vector3d);
+     494             :                         break;
+     495           0 :                 default:
+     496           0 :                         throw bad_conversion(type, TYPE_VECTOR3D);
+     497             :                         break;
+     498             :         }
+     499             : }
+     500             : 
+     501           0 : Vector3<std::complex<double>> Variant::toVector3c() const {
+     502           0 :         switch (type) {
+     503           0 :                 case TYPE_VECTOR3C:
+     504           0 :                         return static_cast<Vector3c>(*data._t_vector3c);
+     505             :                         break;
+     506           0 :                 default:
+     507           0 :                         throw bad_conversion(type, TYPE_VECTOR3C);
+     508             :                         break;
+     509             :         }
+     510             : }
+     511             : 
+     512           6 : std::string Variant::toString(const std::string& delimiter) const {
+     513           6 :         if (type == TYPE_STRING)
+     514           3 :                 return *data._t_string;
+     515             : 
+     516           3 :         std::stringstream ss;
+     517             : 
+     518           3 :         if (type == TYPE_BOOL) {
+     519           0 :                 ss << data._t_bool;
+     520             :         } else if (type == TYPE_CHAR) {
+     521           0 :                 ss << data._t_char;
+     522             :         } else if (type == TYPE_UCHAR) {
+     523           0 :                 ss << data._t_uchar;
+     524             :         } else if (type == TYPE_INT16) {
+     525           0 :                 ss << data._t_int16;
+     526             :         } else if (type == TYPE_UINT16) {
+     527           0 :                 ss << data._t_uint16;
+     528             :         } else if (type == TYPE_INT32) {
+     529           1 :                 ss << data._t_int32;
+     530             :         } else if (type == TYPE_UINT32) {
+     531           0 :                 ss << data._t_uint32;
+     532             :         } else if (type == TYPE_INT64) {
+     533           1 :                 ss << data._t_int64;
+     534             :         } else if (type == TYPE_UINT64) {
+     535           0 :                 ss << data._t_uint64;
+     536             :         } else if (type == TYPE_FLOAT) {
+     537           0 :                 ss << std::scientific << data._t_float;
+     538             :         } else if (type == TYPE_DOUBLE) {
+     539           1 :                 ss << std::scientific << data._t_double;
+     540             :         } else if (type == TYPE_LONGDOUBLE) {
+     541           0 :                 ss << std::scientific << data._t_ldouble;
+     542             :         } else if (type == TYPE_COMPLEXF) {
+     543           0 :                 ss << std::scientific << data._t_complex_f->real() << delimiter; 
+     544           0 :                 ss << std::scientific << data._t_complex_f->imag();
+     545             :         } else if (type == TYPE_COMPLEXD) {
+     546           0 :                 ss << std::scientific << data._t_complex_d->real() << delimiter; 
+     547           0 :                 ss << std::scientific << data._t_complex_d->imag();
+     548             :         } else if (type == TYPE_VECTOR3F) {
+     549           0 :                 ss << *data._t_vector3f;
+     550             :         } else if (type == TYPE_VECTOR3D) {
+     551           0 :                 ss << *data._t_vector3d;
+     552             :         } else if (type == TYPE_VECTOR) {
+     553           0 :                 ss << *data._t_vector;
+     554             :         }
+     555             : 
+     556             :         return ss.str();
+     557           3 : }
+     558             : 
+     559           0 : Variant::vector_t Variant::toVector() const {
+     560           0 :         if (type == TYPE_VECTOR)
+     561           0 :                 return *data._t_vector;
+     562             :         else
+     563           0 :                 throw bad_conversion(type, TYPE_VECTOR);
+     564             : }
+     565             : 
+     566           2 : Variant Variant::fromString(const std::string& s, Type t) {
+     567           2 :         std::stringstream ss(s);
+     568             : 
+     569             :         if (t == TYPE_BOOL) {
+     570             :                 std::string upperstr(s);
+     571             :                 std::transform(upperstr.begin(), upperstr.end(), upperstr.begin(), (int (*)(int)) toupper);
+     572           0 :                 if (upperstr == "YES" || upperstr == "TRUE" || upperstr == "1") 
+     573             :                         return Variant(true);
+     574           0 :                 else if (upperstr == "NO" || upperstr == "FALSE" || upperstr == "0")
+     575             :                         return Variant(false);
+     576           0 :                 throw bad_conversion(t, TYPE_BOOL);
+     577             :         } else if (t == TYPE_CHAR) {
+     578             :                 char c;
+     579           0 :                 ss >> c;
+     580             :                 return Variant(c);
+     581             :         } else if (t == TYPE_UCHAR) {
+     582             :                 unsigned char c;
+     583             :                 ss >> c;
+     584             :                 return Variant(c);
+     585             :         } else if (t == TYPE_INT16) {
+     586             :                 int16_t c;
+     587           0 :                 ss >> c;
+     588             :                 return Variant(c);
+     589             :         } else if (t == TYPE_INT32) {
+     590             :                 int32_t c;
+     591           1 :                 ss >> c;
+     592             :                 return Variant(c);
+     593             :         } else if (t == TYPE_INT64) {
+     594             :                 int64_t c;
+     595             :                 ss >> c;
+     596             :                 return Variant(c);
+     597             :         } else if (t == TYPE_UINT16) {
+     598             :                 uint16_t c;
+     599             :                 ss >> c;
+     600             :                 return Variant(c);
+     601             :         } else if (t == TYPE_UINT32) {
+     602             :                 uint32_t c;
+     603             :                 ss >> c;
+     604             :                 return Variant(c);
+     605             :         } else if (t == TYPE_UINT64) {
+     606             :                 uint64_t c;
+     607             :                 ss >> c;
+     608             :                 return Variant(c);
+     609             :         } else if (t == TYPE_FLOAT) {
+     610             :                 float c;
+     611             :                 ss >> c;
+     612             :                 return Variant(c);
+     613             :         } else if (t == TYPE_DOUBLE) {
+     614             :                 double c;
+     615             :                 ss >> c;
+     616             :                 return Variant(c);
+     617             :         } else if (t == TYPE_LONGDOUBLE) {
+     618             :                 long double c;
+     619             :                 ss >> c;
+     620             :                 return Variant(c);
+     621             :         } else if (t == TYPE_STRING) {
+     622           0 :                 return Variant(s);
+     623             :         } else if (t == TYPE_COMPLEXF) {
+     624             :                 float _vr, _vi;
+     625             :                 ss >> _vr >> _vi;
+     626           0 :                 complex_f v(_vr, _vi);
+     627             :                 return Variant(v);
+     628             :         } else if (t == TYPE_COMPLEXD) {
+     629             :                 double _vr, _vi;
+     630             :                 ss >> _vr >> _vi;
+     631           0 :                 complex_d v(_vr, _vi);
+     632             :                 return Variant(v);
+     633             :         } else if (t == TYPE_VECTOR3F) {
+     634             :                 Vector3f v;
+     635             :                 float _val;
+     636             :                 ss >> _val;
+     637           0 :                 v.setX(_val);
+     638             :                 ss >> _val;
+     639           0 :                 v.setY(_val);
+     640             :                 ss >> _val;
+     641           0 :                 v.setZ(_val);
+     642             :                 return Variant(v);
+     643             :         } else if (t == TYPE_VECTOR3D) {
+     644             :                 Vector3d v;
+     645             :                 double _val;
+     646             :                 ss >> _val;
+     647           0 :                 v.setX(_val);
+     648             :                 ss >> _val;
+     649           0 :                 v.setY(_val);
+     650             :                 ss >> _val;
+     651           0 :                 v.setZ(_val);
+     652             :                 return Variant(v);
+     653             :         } else if (t == TYPE_VECTOR3C) {
+     654             :                 Vector3c v;
+     655           0 :                 std::complex<double> _val;
+     656           0 :                 ss >> _val;
+     657             :                 v.setX(_val);
+     658           0 :                 ss >> _val;
+     659             :                 v.setY(_val);
+     660           0 :                 ss >> _val;
+     661             :                 v.setZ(_val);
+     662             :                 return Variant(v);
+     663             :         } else if (t == TYPE_VECTOR) {
+     664             :                 // std::regex useless("(|)|[|]| ");
+     665             :                 vector_t v;
+     666           0 :                 while (ss.good()) {
+     667             :                         std::string s;
+     668           0 :                         v.push_back(s);
+     669             :                 }
+     670           0 :         } else {
+     671             :                 std::string msg; 
+     672             :                 msg += "fromString not implemented for type ";
+     673           0 :         msg += getTypeName(t);
+     674           0 :         throw std::runtime_error("Variant: " + msg);
+     675             :         }
+     676           2 : }
+     677             : 
+     678        5785 : void Variant::clear(Type t) {
+     679             :         if (t == TYPE_STRING)
+     680           0 :                 safeDelete(data._t_string);
+     681             :         else if (t == TYPE_VECTOR3F)
+     682             :                 safeDelete(data._t_vector3f);
+     683             :         else if (t == TYPE_VECTOR3D)
+     684             :                 safeDelete(data._t_vector3d);
+     685             :         else if (t == TYPE_VECTOR3C)
+     686             :                 safeDelete(data._t_vector3c);
+     687             :         else if (t == TYPE_COMPLEXF)
+     688             :                 safeDelete(data._t_complex_f);
+     689             :         else if (t == TYPE_COMPLEXD)
+     690             :                 safeDelete(data._t_complex_d);
+     691             :         else if (t == TYPE_VECTOR)
+     692           0 :                 safeDelete(data._t_vector);
+     693             : 
+     694             :         // set the type to TYPE_NONE which will be used for checks
+     695        5785 :     type = TYPE_NONE;
+     696        5785 :     check(t);
+     697        5785 : }
+     698             : 
+     699        3459 : void Variant::copy(const Variant& v) {
+     700        3459 :         Type t = v.type;
+     701             : 
+     702        3459 :         if (t == TYPE_BOOL) 
+     703             :                 operator = (v.data._t_bool);
+     704             :         else if (t == TYPE_CHAR)
+     705             :                 operator = (v.data._t_char);
+     706             :         else if (t == TYPE_UCHAR)
+     707             :                 operator = (v.data._t_uchar);
+     708             :         else if (t == TYPE_INT16)
+     709             :                 operator = (v.data._t_int16);
+     710             :         else if (t == TYPE_UINT16)
+     711             :                 operator = (v.data._t_uint16);
+     712             :         else if (t == TYPE_INT32)
+     713             :                 operator = (v.data._t_int32);
+     714             :         else if (t == TYPE_UINT32)
+     715             :                 operator = (v.data._t_uint32);
+     716             :         else if (t == TYPE_INT64)
+     717             :                 operator = (v.data._t_int64);
+     718             :         else if (t == TYPE_UINT64)
+     719             :                 operator = (v.data._t_uint64);
+     720             :         else if (t == TYPE_FLOAT)
+     721             :                 operator = (v.data._t_float);
+     722             :         else if (t == TYPE_DOUBLE)
+     723             :                 operator = (v.data._t_double);
+     724             :         else if (t == TYPE_LONGDOUBLE)
+     725             :                 operator = (v.data._t_ldouble);
+     726             :         else if (t == TYPE_STRING)
+     727        1136 :                 operator = (*v.data._t_string);
+     728             :         else if (t == TYPE_COMPLEXF)
+     729           0 :                 operator = (*v.data._t_complex_f);
+     730             :         else if (t == TYPE_COMPLEXD)
+     731           0 :                 operator = (*v.data._t_complex_d);
+     732             :         else if (t == TYPE_VECTOR3F)
+     733           0 :                 operator = (*v.data._t_vector3f);
+     734             :         else if (t == TYPE_VECTOR3D)
+     735           0 :                 operator = (*v.data._t_vector3d);
+     736             :         else if (t == TYPE_VECTOR3C)
+     737           0 :                 operator = (*v.data._t_vector3c);
+     738             :         else if (t == TYPE_VECTOR)
+     739           0 :                 operator = (*v.data._t_vector);
+     740             :         else
+     741        2279 :                 type = TYPE_NONE;
+     742        3459 : }
+     743             : 
+     744           2 : void Variant::check(const Type t) const {
+     745           2 :         if (type != t) {
+     746           0 :                 throw bad_conversion(type, t);
+     747             :         }
+     748           2 : }
+     749             : 
+     750        5793 : void Variant::check(const Type t) {
+     751        5793 :         if (type == TYPE_NONE) {
+     752        5785 :                 memset(&data, 0, sizeof(data));
+     753        5785 :                 if (t == TYPE_VECTOR3F)
+     754           0 :                         data._t_vector3f = new Vector3f(); 
+     755             :                 else if (t == TYPE_VECTOR3D)
+     756           0 :                         data._t_vector3d = new Vector3d(); 
+     757             :                 else if (t == TYPE_VECTOR3C)
+     758           0 :                         data._t_vector3c = new Vector3c(); 
+     759             :                 else if (t == TYPE_COMPLEXF)
+     760           0 :                         data._t_complex_f = new complex_f(); 
+     761             :                 else if (t == TYPE_COMPLEXD)
+     762           0 :                         data._t_complex_d = new complex_d(); 
+     763             :                 else if (t == TYPE_STRING)
+     764           0 :                         data._t_string = new std::string();
+     765             :                 else if (t == TYPE_VECTOR)
+     766           0 :                         data._t_vector = new vector_t();
+     767             :                 else
+     768        5785 :                         type = t;
+     769           8 :         } else if (type != t)  {
+     770           0 :         throw bad_conversion(type, t);
+     771             :         }
+     772        5793 : }
+     773             : 
+     774           8 : bool Variant::isValid() const {
+     775           8 :         return (type != TYPE_NONE);
+     776             : }
+     777             : 
+     778           0 : size_t Variant::size() const {
+     779           0 :         if (type == TYPE_VECTOR) {
+     780           0 :                 return data._t_vector->size();
+     781             :         } else {
+     782             :                 std::string msg; 
+     783             :                 msg += "size() not implemented for type ";
+     784           0 :                 msg += getTypeName(type);
+     785           0 :                 throw std::runtime_error("Variant: " + msg);
+     786             :         }
+     787             : }
+     788             : 
+     789           0 : size_t Variant::getSizeOf() const {
+     790           0 :         switch (type) {
+     791             :                 case TYPE_BOOL:
+     792             :                         return sizeof(data._t_bool);
+     793             :                         break;
+     794             :                 case TYPE_CHAR:
+     795             :                         return sizeof(data._t_char);
+     796             :                         break;
+     797             :                 case TYPE_UCHAR:
+     798             :                         return sizeof(data._t_uchar);
+     799             :                         break;
+     800           0 :                 case TYPE_INT16:
+     801           0 :                         return sizeof(data._t_int16);
+     802             :                         break;
+     803           0 :                 case TYPE_UINT16:
+     804           0 :                         return sizeof(data._t_uint16);
+     805             :                         break;
+     806           0 :                 case TYPE_INT32:
+     807           0 :                         return sizeof(data._t_int32);
+     808             :                         break;
+     809           0 :                 case TYPE_UINT32:
+     810           0 :                         return sizeof(data._t_uint32);
+     811             :                         break;
+     812           0 :                 case TYPE_INT64:
+     813           0 :                         return sizeof(data._t_int64);
+     814             :                         break;
+     815           0 :                 case TYPE_UINT64:
+     816           0 :                         return sizeof(data._t_uint64);
+     817             :                         break;
+     818           0 :                 case TYPE_FLOAT:
+     819           0 :                         return sizeof(data._t_float);
+     820             :                         break;
+     821           0 :                 case TYPE_DOUBLE:
+     822           0 :                         return sizeof(data._t_double);
+     823             :                         break;
+     824           0 :                 case TYPE_LONGDOUBLE:
+     825           0 :                         return sizeof(data._t_ldouble);
+     826             :                         break;
+     827           0 :                 case TYPE_COMPLEXF:
+     828           0 :                         return sizeof(data._t_complex_f);
+     829             :                         break;
+     830           0 :                 case TYPE_COMPLEXD:
+     831           0 :                         return sizeof(data._t_complex_d);
+     832             :                         break;
+     833           0 :                 case TYPE_VECTOR3F:
+     834           0 :                         return sizeof(data._t_vector3f);
+     835             :                         break;
+     836           0 :                 case TYPE_VECTOR3D:
+     837           0 :                         return sizeof(data._t_vector3d);
+     838             :                         break;
+     839           0 :                 case TYPE_VECTOR3C:
+     840           0 :                         return sizeof(data._t_vector3c);
+     841             :                         break;
+     842           0 :                 case TYPE_STRING: {
+     843           0 :                                 size_t len = strlen(data._t_string->c_str() + 1);
+     844           0 :                                 return len;
+     845             :                         }
+     846             :                         break;
+     847           0 :                 case TYPE_NONE:
+     848           0 :                         return 0;
+     849             :                         break;
+     850           0 :                 default:
+     851           0 :                         throw std::runtime_error("Function getSize() cannot handle this type.");
+     852             :         }
+     853             : }
+     854             : 
+     855           0 : size_t Variant::getSize() const {
+     856           0 :         return getSizeOf();
+     857             : }
+     858             : 
+     859           0 : void Variant::resize(size_t i) {
+     860           0 :         check(TYPE_VECTOR);
+     861           0 :         return data._t_vector->resize(i);
+     862             : }
+     863             : 
+     864           1 : size_t Variant::copyToBuffer(void* buffer) {
+     865           1 :         if (type == TYPE_BOOL) {
+     866           0 :                 memcpy(buffer, &data._t_bool, sizeof(bool));
+     867           0 :                 return sizeof(data._t_bool);
+     868             :         } else if (type == TYPE_CHAR) {
+     869           0 :                 memcpy(buffer, &data._t_char, sizeof(char));
+     870           0 :                 return sizeof(data._t_char);
+     871             :         }  else if (type == TYPE_UCHAR) {
+     872           0 :                 memcpy(buffer, &data._t_uchar, sizeof(unsigned char));
+     873           0 :                 return sizeof(data._t_uchar);
+     874             :         } else if (type == TYPE_INT16) {
+     875           0 :                 memcpy(buffer, &data._t_int16, sizeof(int16_t));
+     876           0 :                 return sizeof(data._t_int16);
+     877             :         } else if (type == TYPE_UINT16) {
+     878           0 :                 memcpy(buffer, &data._t_uint16, sizeof(uint16_t));
+     879           0 :                 return sizeof(data._t_uint16);
+     880             :         } else if (type == TYPE_INT32) {
+     881           0 :                 memcpy(buffer, &data._t_int32, sizeof(int32_t));
+     882           0 :                 return sizeof(data._t_int32);
+     883             :         } else if (type == TYPE_UINT32) {
+     884           0 :                 memcpy(buffer, &data._t_uint32, sizeof(uint32_t));
+     885           0 :                 return sizeof(data._t_uint32);
+     886             :         } else if (type == TYPE_INT64) {
+     887           0 :                 memcpy(buffer, &data._t_int64, sizeof(int64_t));
+     888           0 :                 return sizeof(data._t_int64);
+     889             :         } else if (type == TYPE_UINT64) {
+     890           0 :                 memcpy(buffer, &data._t_uint64, sizeof(uint64_t));
+     891           0 :                 return sizeof(data._t_uint64);
+     892             :         } else if (type == TYPE_FLOAT) {
+     893           0 :                 memcpy(buffer, &data._t_float, sizeof(float));
+     894           0 :                 return sizeof(data._t_float);
+     895             :         } else if (type == TYPE_DOUBLE) {
+     896           1 :                 memcpy(buffer, &data._t_double, sizeof(double));
+     897           1 :                 return sizeof(data._t_double);
+     898             :         } else if (type == TYPE_LONGDOUBLE) {
+     899           0 :                 memcpy(buffer, &data._t_ldouble, sizeof(long double));
+     900           0 :                 return sizeof(data._t_ldouble);
+     901             :         }  else if (type == TYPE_STRING) {
+     902           0 :                 size_t len = data._t_string->size();
+     903             :                 memcpy(buffer, data._t_string->c_str(), len);
+     904           0 :                 return len;
+     905             :         } else if (type == TYPE_NONE) {
+     906             :                 return 0;
+     907             :         } else {
+     908           0 :                 throw std::runtime_error("This type cannot be handled by copyToBuffer().");
+     909             :         }
+     910             : }
+     911             : 
+     912        1153 : Variant& Variant::operator=(const Variant &v) {
+     913        1153 :         copy(v);
+     914        1153 :         return *this;
+     915             : }
+     916             : 
+     917           4 : bool Variant::operator==(const Variant& v) const {
+     918           4 :         if (type != v.type)
+     919             :                 return false;
+     920             : 
+     921             :         if (type == TYPE_BOOL) {
+     922           0 :                 return (data._t_bool == v.data._t_bool);
+     923             :         } else if (type == TYPE_CHAR) {
+     924           0 :                 return (data._t_char == v.data._t_char);
+     925             :         } else if (type == TYPE_UCHAR) {
+     926           0 :                 return (data._t_uchar == v.data._t_uchar);
+     927             :         } else if (type == TYPE_INT16) {
+     928           0 :                 return (data._t_int16 == v.data._t_int16);
+     929             :         } else if (type == TYPE_UINT16) {
+     930           0 :                 return (data._t_uint16 == v.data._t_uint16);
+     931             :         } else if (type == TYPE_INT32) {
+     932           0 :                 return (data._t_int32 == v.data._t_int32);
+     933             :         } else if (type == TYPE_UINT32) {
+     934           0 :                 return (data._t_uint32 == v.data._t_uint32);
+     935             :         } else if (type == TYPE_INT64) {
+     936           0 :                 return (data._t_int64 == v.data._t_int64);
+     937             :         } else if (type == TYPE_UINT64) {
+     938           0 :                 return (data._t_uint64 == v.data._t_uint64);
+     939             :         } else if (type == TYPE_FLOAT) {
+     940           0 :                 return (data._t_float == v.data._t_float);
+     941             :         } else if (type == TYPE_DOUBLE) {
+     942           4 :                 return (data._t_double == v.data._t_double);
+     943             :         } else if (type == TYPE_LONGDOUBLE) {
+     944           0 :                 return (data._t_ldouble == v.data._t_ldouble);
+     945             :         } else if (type == TYPE_STRING) {
+     946           0 :                 return (*data._t_string == *v.data._t_string);
+     947             :         } else if (type == TYPE_COMPLEXF) {
+     948           0 :                 return (*data._t_complex_f == *v.data._t_complex_f);
+     949             :         } else if (type == TYPE_COMPLEXD) {
+     950           0 :                 return (*data._t_complex_d == *v.data._t_complex_d);
+     951             :         } else if (type == TYPE_VECTOR3F) {
+     952           0 :                 return (*data._t_vector3f == *v.data._t_vector3f);
+     953             :         } else if (type == TYPE_VECTOR3D) {
+     954           0 :                 return (*data._t_vector3d == *v.data._t_vector3d);
+     955             :         } else if (type == TYPE_VECTOR3C) {
+     956           0 :                 return (*data._t_vector3c == *v.data._t_vector3c);
+     957             :         } else if (type == TYPE_VECTOR) {
+     958           0 :                 return (*data._t_vector == *v.data._t_vector);
+     959             :         } else {
+     960           0 :                 throw std::runtime_error("compare operator not implemented");
+     961             :         }
+     962             : }
+     963             : 
+     964           0 : bool Variant::operator!=(const Variant& v) const {
+     965           0 :         if (type != v.type)
+     966             :                 return true;
+     967             :         
+     968           0 :         if (*this == v)
+     969             :                 return false;
+     970             :         else
+     971           0 :                 return true;
+     972             : }
+     973             : 
+     974           0 : bool Variant::operator!=(const char* v) const {
+     975           0 :         check(TYPE_STRING);
+     976           0 :         return data._t_string->compare(v) != 0;
+     977             : }
+     978             : 
+     979           0 : Variant& Variant::operator[](size_t i) {
+     980           0 :         check(TYPE_VECTOR);
+     981           0 :         return (*data._t_vector)[i];
+     982             : }
+     983             : 
+     984           0 : const Variant& Variant::operator[](size_t i) const {
+     985           0 :         check(TYPE_VECTOR);
+     986           0 :         return (*data._t_vector)[i];
+     987             : }
+     988             : 
+     989           0 : Variant::operator std::vector<Variant>&() {
+     990           0 :         check(TYPE_VECTOR);
+     991           0 :         return *data._t_vector;
+     992             : }
+     993             : 
+     994           0 : Variant::operator const std::vector<Variant>&() const {
+     995           0 :         check(TYPE_VECTOR);
+     996           0 :         return *data._t_vector;
+     997             : }
+     998             : 
+     999             : 
+    1000             : 
+    1001             : #define INT_CASE(from_var, from_type, to_type, to)                                                                                                                         \
+    1002             :     case Variant::from_type: {                                                                                         \
+    1003             :                 if (data._t_##from_var <std::numeric_limits<to>::min() || data._t_##from_var> std::numeric_limits<to>::max())  \
+    1004             :                         throw bad_conversion(type, to_type);                                                                       \
+    1005             :                 else                                                                                                           \
+    1006             :                         return static_cast<to>(data._t_##from_var);                                                                \
+    1007             :                 }                                                                                                              \
+    1008             :         break;                                                                                                         \
+    1009             : 
+    1010             : #define INT_FUNCTION(to_type, fun, to)                                                                                 \
+    1011             :         to Variant::fun() const {                                                                                          \
+    1012             :                 switch (type) {                                                                                                \
+    1013             :                         case Variant::TYPE_BOOL:                                                                                   \
+    1014             :                                 return data._t_bool ? 1 : 0;                                                                           \
+    1015             :                                 break;                                                                                                 \
+    1016             :                                 INT_CASE(char, TYPE_CHAR, to_type, to)                                                                 \
+    1017             :                                 INT_CASE(uchar, TYPE_UCHAR, to_type, to)                                                               \
+    1018             :                                 INT_CASE(int16, TYPE_INT16, to_type, to)                                                               \
+    1019             :                                 INT_CASE(uint16, TYPE_UINT16, to_type, to)                                                             \
+    1020             :                                 INT_CASE(int32, TYPE_INT32, to_type, to)                                                               \
+    1021             :                                 INT_CASE(uint32, TYPE_UINT32, to_type, to)                                                             \
+    1022             :                                 INT_CASE(int64, TYPE_INT64, to_type, to)                                                               \
+    1023             :                                 INT_CASE(uint64, TYPE_UINT64, to_type, to)                                                             \
+    1024             :                                 INT_CASE(float, TYPE_FLOAT, to_type, to)                                                               \
+    1025             :                                 INT_CASE(double, TYPE_DOUBLE, to_type, to)                                                             \
+    1026             :                                 INT_CASE(ldouble, TYPE_LONGDOUBLE, to_type, to)                                                        \
+    1027             :                         case Variant::TYPE_STRING: {                                                                               \
+    1028             :                                 long l = atol(data._t_string->c_str());                                                                \
+    1029             :                                 if (l <std::numeric_limits<to>::min() || l > std::numeric_limits<to>::max())                           \
+    1030             :                                         throw bad_conversion(type, to_type);                                                               \
+    1031             :                                 else                                                                                                   \
+    1032             :                                         return l;                                                                                          \
+    1033             :                                 }                                                                                                      \
+    1034             :                                 break;                                                                                                 \
+    1035             :                         case Variant::TYPE_COMPLEXF:                                                                               \
+    1036             :                         case Variant::TYPE_COMPLEXD:                                                                               \
+    1037             :                         case Variant::TYPE_VECTOR3F:                                                                               \
+    1038             :                         case Variant::TYPE_VECTOR3D:                                                                               \
+    1039             :                         case Variant::TYPE_VECTOR3C:                                                                               \
+    1040             :                         case Variant::TYPE_VECTOR:                                                                                 \
+    1041             :                         case Variant::TYPE_NONE:                                                                                   \
+    1042             :                                 throw bad_conversion(type, to_type);                                                                   \
+    1043             :                                 break;                                                                                                 \
+    1044             :                 }                                                                                                              \
+    1045             :                 return 0;                                                                                                      \
+    1046             :         } 
+    1047             : 
+    1048           0 : INT_FUNCTION(TYPE_CHAR, toChar, char)
+    1049           0 : INT_FUNCTION(TYPE_UCHAR, toUChar, unsigned char)
+    1050           0 : INT_FUNCTION(TYPE_INT16, toInt16, int16_t)
+    1051           0 : INT_FUNCTION(TYPE_UINT16, toUInt16, uint16_t)
+    1052           0 : INT_FUNCTION(TYPE_INT32, toInt32, int32_t)
+    1053           0 : INT_FUNCTION(TYPE_UINT32, toUInt32, uint32_t)
+    1054           2 : INT_FUNCTION(TYPE_INT64, toInt64, int64_t)
+    1055           0 : INT_FUNCTION(TYPE_UINT64, toUInt64, uint64_t)
+    1056             : 
+    1057             : 
+    1058             : 
+    1059           0 : std::ostream& operator <<(std::ostream& os, const Variant& v) {
+    1060           0 :         switch (v.getType()) {
+    1061             :                 case Variant::TYPE_BOOL:
+    1062           0 :                         os << v.asBool();
+    1063             :                         break;
+    1064             :                 case Variant::TYPE_CHAR:
+    1065           0 :                         os << v.asChar();
+    1066           0 :                         break;
+    1067             :                 case Variant::TYPE_UCHAR:
+    1068           0 :                         os << v.asUChar();
+    1069             :                         break;
+    1070             :                 case Variant::TYPE_INT16:
+    1071           0 :                         os << v.asInt16();
+    1072           0 :                         break;
+    1073             :                 case Variant::TYPE_UINT16:
+    1074           0 :                         os << v.asUInt16();
+    1075             :                         break;
+    1076             :                 case Variant::TYPE_INT32:
+    1077           0 :                         os << v.asInt32();
+    1078           0 :                         break;
+    1079             :                 case Variant::TYPE_UINT32:
+    1080           0 :                         os << v.asUInt32();
+    1081             :                         break;
+    1082             :                 case Variant::TYPE_INT64:
+    1083           0 :                         os << v.asInt64();
+    1084             :                         break;
+    1085             :                 case Variant::TYPE_UINT64:
+    1086           0 :                         os << v.asUInt64();
+    1087             :                         break;
+    1088             :                 case Variant::TYPE_FLOAT:
+    1089           0 :                         os << v.asFloat();
+    1090             :                         break;
+    1091             :                 case Variant::TYPE_DOUBLE:
+    1092           0 :                         os << v.asDouble();
+    1093             :                         break;
+    1094             :                 case Variant::TYPE_LONGDOUBLE:
+    1095           0 :                         os << v.asLongDouble();
+    1096             :                         break;
+    1097             :                 case Variant::TYPE_COMPLEXF:
+    1098           0 :                         os << v.asComplexFloat();
+    1099           0 :                         break;
+    1100             :                 case Variant::TYPE_COMPLEXD:
+    1101           0 :                         os << v.asComplexDouble();
+    1102           0 :                         break;
+    1103             :                 case Variant::TYPE_STRING:
+    1104             :                         os << v.asString();
+    1105             :                         break;
+    1106             :                 case Variant::TYPE_VECTOR3F:
+    1107           0 :                         os << v.asVector3f();
+    1108           0 :                         break;
+    1109             :                 case Variant::TYPE_VECTOR3D:
+    1110           0 :                         os << v.asVector3d();
+    1111           0 :                         break;
+    1112             :                 case Variant::TYPE_VECTOR3C:
+    1113           0 :                         os << v.asVector3c();
+    1114           0 :                         break;
+    1115             :                 default:
+    1116             :                         break;
+    1117             :         }
+    1118             : 
+    1119           0 :         return os;
+    1120             : }
+    1121             : 
+    1122             : 
+    1123             : 
+    1124             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html b/doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html new file mode 100644 index 000000000..39a908092 --- /dev/null +++ b/doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html @@ -0,0 +1,408 @@ + + + + + + + LCOV - coverage.info.cleaned - src/advectionField/AdvectionField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/advectionField - AdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ObliqueAdvectionShock13setShockwidthEd0
_ZN7crpropa21ObliqueAdvectionShock5setVyEd0
_ZN7crpropa21ObliqueAdvectionShock6setVupEd0
_ZN7crpropa21ObliqueAdvectionShock7setCompEd0
_ZN7crpropa21ObliqueAdvectionShockC2Edddd0
_ZN7crpropa28OneDimensionalCartesianShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalCartesianShock6setVupEd0
_ZN7crpropa28OneDimensionalCartesianShock7setCompEd0
_ZN7crpropa28OneDimensionalCartesianShockC2Eddd0
_ZN7crpropa28OneDimensionalSphericalShock10setCoolingEb0
_ZN7crpropa28OneDimensionalSphericalShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalSphericalShock14setShockRadiusEd0
_ZN7crpropa28OneDimensionalSphericalShock6setVupEd0
_ZN7crpropa28OneDimensionalSphericalShock7setCompEd0
_ZN7crpropa28OneDimensionalSphericalShockC2Eddddb0
_ZNK7crpropa21ObliqueAdvectionShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa21ObliqueAdvectionShock13getShockwidthEv0
_ZNK7crpropa21ObliqueAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObliqueAdvectionShock5getVyEv0
_ZNK7crpropa21ObliqueAdvectionShock6getVupEv0
_ZNK7crpropa21ObliqueAdvectionShock7getCompEv0
_ZNK7crpropa21ObliqueAdvectionShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa21UniformAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalCartesianShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalCartesianShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalCartesianShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalCartesianShock6getVupEv0
_ZNK7crpropa28OneDimensionalCartesianShock7getCompEv0
_ZNK7crpropa28OneDimensionalCartesianShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock10getCoolingEv0
_ZNK7crpropa28OneDimensionalSphericalShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalSphericalShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalSphericalShock14getShockRadiusEv0
_ZNK7crpropa28OneDimensionalSphericalShock6getVupEv0
_ZNK7crpropa28OneDimensionalSphericalShock7getCompEv0
_ZNK7crpropa28OneDimensionalSphericalShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa31ConstantSphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZN7crpropa23SphericalAdvectionField6setTauEd1
_ZN7crpropa23SphericalAdvectionField7setVMaxEd1
_ZN7crpropa23SphericalAdvectionField8setAlphaEd1
_ZN7crpropa23SphericalAdvectionField9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionField9setRadiusEd1
_ZN7crpropa23SphericalAdvectionFieldC2ENS_7Vector3IdEEdddd1
_ZN7crpropa23SphericalAdvectionShock5setR0Ed1
_ZN7crpropa23SphericalAdvectionShock5setV0Ed1
_ZN7crpropa23SphericalAdvectionShock9setLambdaEd1
_ZN7crpropa23SphericalAdvectionShock9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionShockC2ENS_7Vector3IdEEddd1
_ZNK7crpropa18AdvectionFieldList13getDivergenceERKNS_7Vector3IdEE1
_ZNK7crpropa18AdvectionFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa23SphericalAdvectionField6getTauEv1
_ZNK7crpropa23SphericalAdvectionField7getVMaxEv1
_ZNK7crpropa23SphericalAdvectionField8getAlphaEv1
_ZNK7crpropa23SphericalAdvectionField9getRadiusEv1
_ZNK7crpropa23SphericalAdvectionShock5getR0Ev1
_ZNK7crpropa23SphericalAdvectionShock5getV0Ev1
_ZNK7crpropa23SphericalAdvectionShock9getLambdaEv1
_ZNK7crpropa31ConstantSphericalAdvectionField8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa31ConstantSphericalAdvectionField8getVWindEv1
_ZN7crpropa23SphericalAdvectionShock17setAzimuthalSpeedEd2
_ZN7crpropa23SphericalAdvectionShock7setRRotEd2
_ZN7crpropa31ConstantSphericalAdvectionField8setVWindEd2
_ZN7crpropa31ConstantSphericalAdvectionField9setOriginENS_7Vector3IdEE2
_ZN7crpropa31ConstantSphericalAdvectionFieldC2ENS_7Vector3IdEEd2
_ZNK7crpropa23SphericalAdvectionField4getVERKd2
_ZNK7crpropa23SphericalAdvectionShock13getDivergenceERKNS_7Vector3IdEE2
_ZNK7crpropa23SphericalAdvectionShock17getAzimuthalSpeedEv2
_ZNK7crpropa23SphericalAdvectionShock7g_primeEd2
_ZNK7crpropa23SphericalAdvectionShock7getRRotEv2
_ZNK7crpropa31ConstantSphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE2
_ZN7crpropa18AdvectionFieldList8addFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZNK7crpropa23SphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField9getOriginEv3
_ZNK7crpropa23SphericalAdvectionShock8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionShock9getOriginEv3
_ZNK7crpropa31ConstantSphericalAdvectionField9getOriginEv3
_ZNK7crpropa21UniformAdvectionField13getDivergenceERKNS_7Vector3IdEE5
_ZNK7crpropa23SphericalAdvectionShock1gEd5
_ZN7crpropa21UniformAdvectionFieldC2ERKNS_7Vector3IdEE8
_ZNK7crpropa21UniformAdvectionField8getFieldERKNS_7Vector3IdEE120005
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html b/doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html new file mode 100644 index 000000000..c7c1f546f --- /dev/null +++ b/doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html @@ -0,0 +1,408 @@ + + + + + + + LCOV - coverage.info.cleaned - src/advectionField/AdvectionField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/advectionField - AdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18AdvectionFieldList8addFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZN7crpropa21ObliqueAdvectionShock13setShockwidthEd0
_ZN7crpropa21ObliqueAdvectionShock5setVyEd0
_ZN7crpropa21ObliqueAdvectionShock6setVupEd0
_ZN7crpropa21ObliqueAdvectionShock7setCompEd0
_ZN7crpropa21ObliqueAdvectionShockC2Edddd0
_ZN7crpropa21UniformAdvectionFieldC2ERKNS_7Vector3IdEE8
_ZN7crpropa23SphericalAdvectionField6setTauEd1
_ZN7crpropa23SphericalAdvectionField7setVMaxEd1
_ZN7crpropa23SphericalAdvectionField8setAlphaEd1
_ZN7crpropa23SphericalAdvectionField9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionField9setRadiusEd1
_ZN7crpropa23SphericalAdvectionFieldC2ENS_7Vector3IdEEdddd1
_ZN7crpropa23SphericalAdvectionShock17setAzimuthalSpeedEd2
_ZN7crpropa23SphericalAdvectionShock5setR0Ed1
_ZN7crpropa23SphericalAdvectionShock5setV0Ed1
_ZN7crpropa23SphericalAdvectionShock7setRRotEd2
_ZN7crpropa23SphericalAdvectionShock9setLambdaEd1
_ZN7crpropa23SphericalAdvectionShock9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionShockC2ENS_7Vector3IdEEddd1
_ZN7crpropa28OneDimensionalCartesianShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalCartesianShock6setVupEd0
_ZN7crpropa28OneDimensionalCartesianShock7setCompEd0
_ZN7crpropa28OneDimensionalCartesianShockC2Eddd0
_ZN7crpropa28OneDimensionalSphericalShock10setCoolingEb0
_ZN7crpropa28OneDimensionalSphericalShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalSphericalShock14setShockRadiusEd0
_ZN7crpropa28OneDimensionalSphericalShock6setVupEd0
_ZN7crpropa28OneDimensionalSphericalShock7setCompEd0
_ZN7crpropa28OneDimensionalSphericalShockC2Eddddb0
_ZN7crpropa31ConstantSphericalAdvectionField8setVWindEd2
_ZN7crpropa31ConstantSphericalAdvectionField9setOriginENS_7Vector3IdEE2
_ZN7crpropa31ConstantSphericalAdvectionFieldC2ENS_7Vector3IdEEd2
_ZNK7crpropa18AdvectionFieldList13getDivergenceERKNS_7Vector3IdEE1
_ZNK7crpropa18AdvectionFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa21ObliqueAdvectionShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa21ObliqueAdvectionShock13getShockwidthEv0
_ZNK7crpropa21ObliqueAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObliqueAdvectionShock5getVyEv0
_ZNK7crpropa21ObliqueAdvectionShock6getVupEv0
_ZNK7crpropa21ObliqueAdvectionShock7getCompEv0
_ZNK7crpropa21ObliqueAdvectionShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa21UniformAdvectionField13getDivergenceERKNS_7Vector3IdEE5
_ZNK7crpropa21UniformAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa21UniformAdvectionField8getFieldERKNS_7Vector3IdEE120005
_ZNK7crpropa23SphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionField4getVERKd2
_ZNK7crpropa23SphericalAdvectionField6getTauEv1
_ZNK7crpropa23SphericalAdvectionField7getVMaxEv1
_ZNK7crpropa23SphericalAdvectionField8getAlphaEv1
_ZNK7crpropa23SphericalAdvectionField8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField9getOriginEv3
_ZNK7crpropa23SphericalAdvectionField9getRadiusEv1
_ZNK7crpropa23SphericalAdvectionShock13getDivergenceERKNS_7Vector3IdEE2
_ZNK7crpropa23SphericalAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionShock17getAzimuthalSpeedEv2
_ZNK7crpropa23SphericalAdvectionShock1gEd5
_ZNK7crpropa23SphericalAdvectionShock5getR0Ev1
_ZNK7crpropa23SphericalAdvectionShock5getV0Ev1
_ZNK7crpropa23SphericalAdvectionShock7g_primeEd2
_ZNK7crpropa23SphericalAdvectionShock7getRRotEv2
_ZNK7crpropa23SphericalAdvectionShock8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionShock9getLambdaEv1
_ZNK7crpropa23SphericalAdvectionShock9getOriginEv3
_ZNK7crpropa28OneDimensionalCartesianShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalCartesianShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalCartesianShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalCartesianShock6getVupEv0
_ZNK7crpropa28OneDimensionalCartesianShock7getCompEv0
_ZNK7crpropa28OneDimensionalCartesianShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock10getCoolingEv0
_ZNK7crpropa28OneDimensionalSphericalShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalSphericalShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalSphericalShock14getShockRadiusEv0
_ZNK7crpropa28OneDimensionalSphericalShock6getVupEv0
_ZNK7crpropa28OneDimensionalSphericalShock7getCompEv0
_ZNK7crpropa28OneDimensionalSphericalShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa31ConstantSphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE2
_ZNK7crpropa31ConstantSphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa31ConstantSphericalAdvectionField8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa31ConstantSphericalAdvectionField8getVWindEv1
_ZNK7crpropa31ConstantSphericalAdvectionField9getOriginEv3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html b/doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html new file mode 100644 index 000000000..69ab19d58 --- /dev/null +++ b/doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html @@ -0,0 +1,610 @@ + + + + + + + LCOV - coverage.info.cleaned - src/advectionField/AdvectionField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/advectionField - AdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/advectionField/AdvectionField.h"
+       2             : 
+       3             : 
+       4             : namespace crpropa {
+       5             : 
+       6             : 
+       7             : 
+       8           3 : void AdvectionFieldList::addField(ref_ptr<AdvectionField> field) {
+       9           3 :         fields.push_back(field);
+      10           3 : }
+      11             : 
+      12           1 : Vector3d AdvectionFieldList::getField(const Vector3d &position) const {
+      13             :         Vector3d b(0.);
+      14           4 :         for (int i = 0; i < fields.size(); i++)
+      15           3 :                 b += fields[i]->getField(position);
+      16           1 :         return b;
+      17             : }
+      18             : 
+      19           1 : double AdvectionFieldList::getDivergence(const Vector3d &position) const {
+      20             :         double D=0.;
+      21             :         // Work on default values for divergence or an error handling
+      22           4 :         for (int i = 0; i < fields.size(); i++)
+      23           3 :                 D += fields[i]->getDivergence(position);
+      24           1 :         return D;
+      25             : }
+      26             : 
+      27             : 
+      28             : //----------------------------------------------------------------
+      29           8 : UniformAdvectionField::UniformAdvectionField(const Vector3d &value) :
+      30           8 :                         value(value) {
+      31           8 :         }
+      32             : 
+      33      120005 : Vector3d UniformAdvectionField::getField(const Vector3d &position) const {
+      34      120005 :         return value;
+      35             :         }
+      36             : 
+      37           5 : double UniformAdvectionField::getDivergence(const Vector3d &position) const {
+      38           5 :         return 0.;
+      39             :         }
+      40             : 
+      41           0 : std::string UniformAdvectionField::getDescription() const {
+      42           0 :         std::stringstream s;
+      43           0 :         s << "v0: " << value / km * sec << " km/s, ";
+      44           0 :         return s.str();
+      45           0 : }
+      46             : 
+      47             : //----------------------------------------------------------------
+      48             : 
+      49           2 : ConstantSphericalAdvectionField::ConstantSphericalAdvectionField(const Vector3d origin, double vWind) {
+      50           2 :         setOrigin(origin);
+      51           2 :         setVWind(vWind);
+      52           2 : }
+      53             : 
+      54           1 : Vector3d ConstantSphericalAdvectionField::getField(const Vector3d &position) const {
+      55             :         Vector3d Pos = position-origin;
+      56           1 :         return vWind * Pos.getUnitVector();
+      57             : }
+      58             : 
+      59           2 : double ConstantSphericalAdvectionField::getDivergence(const Vector3d &position) const {
+      60             :         double R = (position-origin).getR();    
+      61           2 :         return 2*vWind/R;
+      62             : }
+      63             : 
+      64           2 : void ConstantSphericalAdvectionField::setOrigin(const Vector3d o) {
+      65             :         origin=o;
+      66           2 :         return;
+      67             : }
+      68             : 
+      69           2 : void ConstantSphericalAdvectionField::setVWind(double v) {
+      70           2 :         vWind = v;
+      71           2 :         return;
+      72             : }
+      73             : 
+      74           3 : Vector3d ConstantSphericalAdvectionField::getOrigin() const {
+      75           3 :         return origin;
+      76             : }
+      77             : 
+      78           1 : double ConstantSphericalAdvectionField::getVWind() const {
+      79           1 :         return vWind;
+      80             : }
+      81             : 
+      82           0 : std::string ConstantSphericalAdvectionField::getDescription() const {
+      83           0 :         std::stringstream s;
+      84           0 :         s << "Origin: " << origin / kpc  << " kpc, ";
+      85           0 :         s << "v0: " << vWind / km * sec << " km/s, ";
+      86           0 :         return s.str();
+      87           0 : }
+      88             : 
+      89             : 
+      90             : 
+      91             : //----------------------------------------------------------------
+      92             : 
+      93           1 : SphericalAdvectionField::SphericalAdvectionField(const Vector3d origin, double radius, double vMax, double tau, double alpha) {
+      94           1 :         setOrigin(origin);
+      95           1 :         setRadius(radius);
+      96           1 :         setVMax(vMax);
+      97           1 :         setTau(tau);
+      98           1 :         setAlpha(alpha);
+      99           1 : }
+     100             : 
+     101           3 : Vector3d SphericalAdvectionField::getField(const Vector3d &position) const {
+     102             :         Vector3d Pos = position-origin;
+     103           3 :         double R = Pos.getR();
+     104           3 :         if (R>radius) {
+     105             :                 return Vector3d(0.);
+     106             :         }
+     107           2 :         double v_R = getV(R);
+     108           2 :         return v_R * Pos.getUnitVector();
+     109             : }
+     110             : 
+     111           3 : double SphericalAdvectionField::getDivergence(const Vector3d &position) const {
+     112             :         double R = (position-origin).getR();
+     113           3 :         if (R>radius) {
+     114             :                 return 0.;
+     115             :         }
+     116           2 :         double D = 2*vMax/R * ( 1-( 1-alpha*(pow(R, alpha)/(2*tau)) )*exp(-( pow(R, alpha)/tau )) );
+     117           2 :         return D;
+     118             : }
+     119             : 
+     120           2 : double SphericalAdvectionField::getV(const double &r) const {
+     121           2 :         double f = vMax * (1-exp(-(pow(r, alpha)/tau)));
+     122           2 :         return f;
+     123             : }
+     124             : 
+     125           1 : void SphericalAdvectionField::setOrigin(const Vector3d o) {
+     126             :         origin = o;
+     127           1 :         return;
+     128             : }
+     129             : 
+     130           1 : void SphericalAdvectionField::setRadius(double r) {
+     131           1 :         radius = r;
+     132           1 :         return;
+     133             : }
+     134             : 
+     135           1 : void SphericalAdvectionField::setVMax(double v) {
+     136           1 :         vMax = v;
+     137           1 :         return;
+     138             : }
+     139             : 
+     140           1 : void SphericalAdvectionField::setTau(double t) {
+     141           1 :         tau = t;
+     142           1 :         return;
+     143             : }
+     144             : 
+     145           1 : void SphericalAdvectionField::setAlpha(double a) {
+     146           1 :         alpha = a;
+     147           1 :         return;
+     148             : }
+     149             : 
+     150           3 : Vector3d SphericalAdvectionField::getOrigin() const {
+     151           3 :         return origin;
+     152             : }
+     153             : 
+     154           1 : double SphericalAdvectionField::getRadius() const {
+     155           1 :         return radius;
+     156             : }
+     157             : 
+     158           1 : double SphericalAdvectionField::getVMax() const {
+     159           1 :         return vMax;
+     160             : }
+     161             : 
+     162           1 : double SphericalAdvectionField::getTau() const {
+     163           1 :         return tau;
+     164             : }
+     165             : 
+     166           1 : double SphericalAdvectionField::getAlpha() const {
+     167           1 :         return alpha;
+     168             : }
+     169             : 
+     170           0 : std::string SphericalAdvectionField::getDescription() const {
+     171           0 :         std::stringstream s;
+     172           0 :         s << "Origin: " << origin / kpc  << " kpc, ";
+     173           0 :         s << "Radius: " << radius / kpc  << " kpc, ";
+     174           0 :         s << "vMax: " << vMax / km * sec << " km/s, ";
+     175           0 :         s << "tau: " << tau << ", ";
+     176           0 :         s << "alpha: " << alpha << "\n";
+     177           0 :         return s.str();
+     178           0 : }
+     179             : 
+     180             : //----------------------------------------------------------------
+     181             : 
+     182           0 : OneDimensionalCartesianShock::OneDimensionalCartesianShock(double compressionRatio, double vUp, double lShock){
+     183           0 :         setComp(compressionRatio);
+     184           0 :         setVup(vUp);
+     185           0 :         setShockwidth(lShock);
+     186           0 :         }
+     187             : 
+     188           0 : Vector3d OneDimensionalCartesianShock::getField(const Vector3d &position) const {
+     189           0 :         double x = position.x;
+     190           0 :         double vDown = vUp / compressionRatio;
+     191             : 
+     192           0 :         double a = (vUp + vDown) * 0.5;
+     193           0 :         double b = (vUp - vDown) * 0.5;
+     194             : 
+     195             :         Vector3d v(0.);
+     196           0 :         v.x = a - b * tanh(x / lShock);
+     197           0 :         return v;
+     198             : 
+     199             : }
+     200             : 
+     201           0 : double OneDimensionalCartesianShock::getDivergence(const Vector3d &position) const {
+     202           0 :         double x = position.x;
+     203           0 :         double vDown = vUp / compressionRatio;
+     204             : 
+     205             :         double a = (vUp + vDown) * 0.5;
+     206           0 :         double b = (vUp - vDown) * 0.5;
+     207           0 :         return -b / lShock * (1 - tanh(x / lShock) * tanh(x / lShock));
+     208             : }
+     209             : 
+     210           0 : void OneDimensionalCartesianShock::setComp(double r) {
+     211           0 :         compressionRatio = r;
+     212           0 :         return;
+     213             : }
+     214             : 
+     215           0 : void OneDimensionalCartesianShock::setVup(double v) {
+     216           0 :         vUp = v;
+     217           0 :         return;
+     218             : }
+     219           0 : void OneDimensionalCartesianShock::setShockwidth(double w) {
+     220           0 :         lShock = w;
+     221           0 :         return;
+     222             : }
+     223             : 
+     224           0 : double OneDimensionalCartesianShock::getComp() const {
+     225           0 :         return compressionRatio;
+     226             : }
+     227             : 
+     228           0 : double OneDimensionalCartesianShock::getVup() const {
+     229           0 :         return vUp;
+     230             : }
+     231             : 
+     232           0 : double OneDimensionalCartesianShock::getShockwidth() const {
+     233           0 :         return lShock;
+     234             : }
+     235             : 
+     236           0 : std::string OneDimensionalCartesianShock::getDescription() const {
+     237           0 :         std::stringstream s;
+     238           0 :         s << "Shock width: " << lShock / km  << " km, ";
+     239           0 :         s << "Vup: " << vUp / km * sec << " km/s, ";
+     240           0 :         s << "Compression: " << compressionRatio;
+     241           0 :         return s.str();
+     242           0 : }
+     243             : 
+     244             : //----------------------------------------------------------------
+     245             : 
+     246           0 : OneDimensionalSphericalShock::OneDimensionalSphericalShock(double rShock, double vUp, double compressionRatio, double lShock, bool coolUpstream ){
+     247           0 :         setComp(compressionRatio);
+     248           0 :         setVup(vUp);
+     249           0 :         setShockwidth(lShock);
+     250           0 :         setShockRadius(rShock);
+     251           0 :         setCooling(coolUpstream);
+     252           0 :         }
+     253             : 
+     254           0 : Vector3d OneDimensionalSphericalShock::getField(const Vector3d &position) const {
+     255             :         double r = position.getR();
+     256           0 :         Vector3d e_r = position.getUnitVector();
+     257             : 
+     258           0 :         double vDown = vUp / compressionRatio;
+     259           0 :         double a = (vUp + vDown) * 0.5;
+     260           0 :         double b = (vUp - vDown) * 0.5;
+     261             : 
+     262             :         double v;
+     263           0 :         if (coolUpstream == true){
+     264             :         
+     265           0 :                 if (r <= rShock)
+     266           0 :                 v = a - b * tanh((r-rShock) / lShock);
+     267             :                 else
+     268           0 :                         v = (a - b * tanh((r-rShock) / lShock)) * (rShock / r) * (rShock / r);
+     269             : 
+     270             :         }
+     271             :         else
+     272           0 :                 v = (a - b * tanh((r-rShock) / lShock)) * (rShock / r) * (rShock / r);
+     273             : 
+     274           0 :         return v * e_r;
+     275             :         }
+     276             : 
+     277           0 : double OneDimensionalSphericalShock::getDivergence(const Vector3d &position) const {
+     278             :         double r = position.getR();
+     279             :         
+     280           0 :         double vDown = vUp / compressionRatio;
+     281           0 :         double a = (vUp + vDown) * 0.5;
+     282           0 :         double b = (vUp - vDown) * 0.5;
+     283             : 
+     284           0 :         double c = tanh((r-rShock) / lShock);
+     285             : 
+     286           0 :         if (coolUpstream == true){
+     287           0 :                 if (r <= rShock)
+     288           0 :                         return 2 * a / r - 2 * b / r * c - b / lShock * (1 - c * c);
+     289             :                 else
+     290           0 :                         return -(rShock / r) * (rShock / r) * b / lShock * (1 - c * c);
+     291             :         }
+     292             :         else 
+     293           0 :                 return -(rShock / r) * (rShock / r) *  b / lShock * (1 - c * c);
+     294             : 
+     295             : }
+     296             : 
+     297           0 : void OneDimensionalSphericalShock::setComp(double r) {
+     298           0 :         compressionRatio = r;
+     299           0 :         return;
+     300             : }
+     301             : 
+     302           0 : void OneDimensionalSphericalShock::setVup(double v) {
+     303           0 :         vUp = v;
+     304           0 :         return;
+     305             : }
+     306           0 : void OneDimensionalSphericalShock::setShockwidth(double w) {
+     307           0 :         lShock = w;
+     308           0 :         return;
+     309             : }
+     310             : 
+     311           0 : void OneDimensionalSphericalShock::setShockRadius(double r) {
+     312           0 :         rShock = r;
+     313           0 :         return;
+     314             : }
+     315             : 
+     316           0 : void OneDimensionalSphericalShock::setCooling(bool c) {
+     317           0 :         coolUpstream = c;
+     318           0 :         return;
+     319             : }
+     320             : 
+     321           0 : double OneDimensionalSphericalShock::getComp() const {
+     322           0 :         return compressionRatio;
+     323             : }
+     324             : 
+     325           0 : double OneDimensionalSphericalShock::getVup() const {
+     326           0 :         return vUp;
+     327             : }
+     328             : 
+     329           0 : double OneDimensionalSphericalShock::getShockwidth() const {
+     330           0 :         return lShock;
+     331             : }
+     332             : 
+     333           0 : double OneDimensionalSphericalShock::getShockRadius() const {
+     334           0 :         return rShock;
+     335             : }
+     336             : 
+     337           0 : bool OneDimensionalSphericalShock::getCooling() const {
+     338           0 :         return coolUpstream;
+     339             : }
+     340             : 
+     341           0 : std::string OneDimensionalSphericalShock::getDescription() const {
+     342           0 :         std::stringstream s;
+     343           0 :         s << "Shock width: " << lShock / km  << " km, ";
+     344           0 :         s << "Shock radius: " << rShock / km  << " km, ";
+     345           0 :         s << "Vup: " << vUp / km * sec << " km/s, ";
+     346           0 :         s << "Comp: " << compressionRatio;
+     347             : 
+     348           0 :         return s.str();
+     349           0 : }
+     350             : 
+     351             : //----------------------------------------------------------------
+     352             : 
+     353           0 : ObliqueAdvectionShock::ObliqueAdvectionShock(double compressionRatio, double vXUp, double vY, double lShock) {
+     354           0 :         setComp(compressionRatio);
+     355           0 :         setVup(vXUp);
+     356           0 :         setVy(vY);
+     357           0 :         setShockwidth(lShock);
+     358           0 :         }
+     359             : 
+     360           0 : Vector3d ObliqueAdvectionShock::getField(const Vector3d &position) const {
+     361           0 :         double x = position.x;
+     362           0 :         double vXDown = vXUp / compressionRatio;
+     363             : 
+     364           0 :         double a = (vXUp + vXDown) * 0.5;
+     365           0 :         double b = (vXUp - vXDown) * 0.5;
+     366             : 
+     367             :         Vector3d v(0.);
+     368           0 :         v.x = a - b * tanh(x / lShock);
+     369           0 :         v.y = vY;
+     370             : 
+     371           0 :         return v;
+     372             :         }
+     373             : 
+     374           0 : double ObliqueAdvectionShock::getDivergence(const Vector3d &position) const {
+     375           0 :         double x = position.x;
+     376           0 :         double vXDown = vXUp / compressionRatio;
+     377             :         // vy = const
+     378             : 
+     379             :         double a = (vXUp + vXDown) * 0.5;
+     380           0 :         double b = (vXUp - vXDown) * 0.5;
+     381             : 
+     382           0 :         return -b / lShock * (1 - tanh(x / lShock) * tanh(x / lShock));
+     383             :         }
+     384             : 
+     385           0 : void ObliqueAdvectionShock::setComp(double r) {
+     386           0 :         compressionRatio = r;
+     387           0 :         return;
+     388             : }
+     389             : 
+     390           0 : void ObliqueAdvectionShock::setVup(double v) {
+     391           0 :         vXUp = v;
+     392           0 :         return;
+     393             : } 
+     394             : 
+     395           0 : void ObliqueAdvectionShock::setVy(double v) {
+     396           0 :         vY = v;
+     397           0 :         return;
+     398             : } 
+     399           0 : void ObliqueAdvectionShock::setShockwidth(double w) {
+     400           0 :         lShock = w;
+     401           0 :         return;
+     402             : }
+     403             : 
+     404           0 : double ObliqueAdvectionShock::getComp() const {
+     405           0 :         return compressionRatio;
+     406             : }
+     407             : 
+     408           0 : double ObliqueAdvectionShock::getVup() const {
+     409           0 :         return vXUp;
+     410             : }
+     411             : 
+     412           0 : double ObliqueAdvectionShock::getVy() const {
+     413           0 :         return vY;
+     414             : }
+     415             : 
+     416           0 : double ObliqueAdvectionShock::getShockwidth() const {
+     417           0 :         return lShock;
+     418             : }
+     419             : 
+     420           0 : std::string ObliqueAdvectionShock::getDescription() const {
+     421           0 :         std::stringstream s;
+     422           0 :         s << "Shock width: " << lShock / km  << " km, ";
+     423           0 :         s << "Vx_up: " << vXUp / km * sec << " km/s, ";
+     424           0 :         s << "Vy: " << vY / km * sec << " km/s, ";
+     425           0 :         s << "Comp: " << compressionRatio;
+     426             :         
+     427           0 :         return s.str();
+     428           0 : }
+     429             : 
+     430             : //-----------------------------------------------------------------
+     431             : 
+     432           1 : SphericalAdvectionShock::SphericalAdvectionShock(const Vector3d origin, double r_0, double v_0, double l) {
+     433           1 :         setOrigin(origin);
+     434           1 :         setR0(r_0);
+     435           1 :         setV0(v_0);
+     436           1 :         setLambda(l);
+     437           1 :         setRRot(r_0);
+     438           1 :         setAzimuthalSpeed(0.);
+     439           1 : }
+     440             : 
+     441             : 
+     442           3 : Vector3d SphericalAdvectionShock::getField(const Vector3d &pos) const {
+     443             :         Vector3d R = pos-origin;
+     444           3 :         Vector3d e_r = R.getUnitVector();
+     445           3 :         Vector3d e_phi = R.getUnitVectorPhi();
+     446             :         double r = R.getR();
+     447             : 
+     448           3 :         double v_r = v_0 * ( 1 + (pow(r_0/(2*r), 2.) -1 ) * g(r));
+     449           3 :         double v_p = v_phi * (r_rot/r); 
+     450             : 
+     451           3 :         return v_r * e_r + v_p * e_phi;
+     452             : }
+     453             : 
+     454             : 
+     455           2 : double SphericalAdvectionShock::getDivergence(const Vector3d &pos) const {
+     456             :         double r = (pos-origin).getR();
+     457             : 
+     458           2 :         double d1 = 2./r*(1-g(r));
+     459           2 :         double d2 = (pow(r_0/(2*r), 2.)-1)*g_prime(r);
+     460             : 
+     461           2 :         return v_0 * (d1+d2);
+     462             : }
+     463             : 
+     464             : 
+     465           5 : double SphericalAdvectionShock::g(double r) const {
+     466           5 :         double a = (r-r_0)/lambda;
+     467           5 :         return 1. / (1+exp(-a));
+     468             : }
+     469             : 
+     470           2 : double SphericalAdvectionShock::g_prime(double r) const {
+     471           2 :         double a = (r-r_0)/lambda;
+     472           2 :         return 1. / (2*lambda*(1+cosh(-a)));
+     473             : }       
+     474             : 
+     475           1 : void SphericalAdvectionShock::setOrigin(const Vector3d o) {
+     476             :         origin = o;
+     477           1 : }
+     478             : 
+     479           1 : void SphericalAdvectionShock::setR0(double r) {
+     480           1 :         r_0 = r;
+     481           1 : }
+     482             : 
+     483           1 : void SphericalAdvectionShock::setV0(double v) {
+     484           1 :         v_0 = v;
+     485           1 : }
+     486             : 
+     487           1 : void SphericalAdvectionShock::setLambda(double l) {
+     488           1 :         lambda = l;
+     489           1 : }
+     490             : 
+     491           2 : void SphericalAdvectionShock::setRRot(double r) {
+     492           2 :         r_rot = r;
+     493           2 : }
+     494             : 
+     495           2 : void SphericalAdvectionShock::setAzimuthalSpeed(double v) {
+     496           2 :         v_phi = v;
+     497           2 : }
+     498             : 
+     499           3 : Vector3d SphericalAdvectionShock::getOrigin() const {
+     500           3 :         return origin;
+     501             : }
+     502             : 
+     503           1 : double SphericalAdvectionShock::getR0() const {
+     504           1 :         return r_0;
+     505             : }
+     506             : 
+     507           1 : double SphericalAdvectionShock::getV0() const {
+     508           1 :         return v_0;
+     509             : }
+     510             : 
+     511           1 : double SphericalAdvectionShock::getLambda() const {
+     512           1 :         return lambda;
+     513             : }
+     514             : 
+     515           2 : double SphericalAdvectionShock::getRRot() const {
+     516           2 :         return r_rot;
+     517             : }
+     518             : 
+     519           2 : double SphericalAdvectionShock::getAzimuthalSpeed() const {
+     520           2 :         return v_phi;
+     521             : }
+     522             : 
+     523           0 : std::string SphericalAdvectionShock::getDescription() const {
+     524           0 :         std::stringstream s;
+     525           0 :         s << "Origin: " << origin / kpc  << " kpc, ";
+     526           0 :         s << "r0 (shock radius): " << r_0 / kpc  << " kpc, ";
+     527           0 :         s << "r_rot (norm. azimuthal velocity): " << r_rot / kpc  << " kpc, ";
+     528           0 :         s << "v0 (maximum radial speed): " << v_0 / km * sec << " km/s, ";
+     529           0 :         s << "v_phi (azimuthal speed @ r_rot): " << v_phi / km * sec << " km/s, ";
+     530           0 :         s << "lambda: " << lambda / pc << " pc";
+     531           0 :         return s.str();
+     532           0 : }
+     533             : 
+     534             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/advectionField/index-sort-f.html b/doc/coverageReport/src/advectionField/index-sort-f.html new file mode 100644 index 000000000..54baddead --- /dev/null +++ b/doc/coverageReport/src/advectionField/index-sort-f.html @@ -0,0 +1,93 @@ + + + + + + + LCOV - coverage.info.cleaned - src/advectionField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.cpp +
42.5%42.5%
+
42.5 %131 / 30852.4 %44 / 84
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/advectionField/index-sort-l.html b/doc/coverageReport/src/advectionField/index-sort-l.html new file mode 100644 index 000000000..5eed79af6 --- /dev/null +++ b/doc/coverageReport/src/advectionField/index-sort-l.html @@ -0,0 +1,93 @@ + + + + + + + LCOV - coverage.info.cleaned - src/advectionField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.cpp +
42.5%42.5%
+
42.5 %131 / 30852.4 %44 / 84
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/advectionField/index.html b/doc/coverageReport/src/advectionField/index.html new file mode 100644 index 000000000..c4f7d0da9 --- /dev/null +++ b/doc/coverageReport/src/advectionField/index.html @@ -0,0 +1,93 @@ + + + + + + + LCOV - coverage.info.cleaned - src/advectionField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.cpp +
42.5%42.5%
+
42.5 %131 / 30852.4 %44 / 84
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/base64.cpp.func-sort-c.html b/doc/coverageReport/src/base64.cpp.func-sort-c.html new file mode 100644 index 000000000..6dfadfd29 --- /dev/null +++ b/doc/coverageReport/src/base64.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/base64.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - base64.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:454991.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Base646encodeB5cxx11EPKhm99
_ZN7crpropa6Base646decodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE100
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/base64.cpp.func.html b/doc/coverageReport/src/base64.cpp.func.html new file mode 100644 index 000000000..d68b507b6 --- /dev/null +++ b/doc/coverageReport/src/base64.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/base64.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - base64.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:454991.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Base646decodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE100
_ZN7crpropa6Base646encodeB5cxx11EPKhm99
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/base64.cpp.gcov.html b/doc/coverageReport/src/base64.cpp.gcov.html new file mode 100644 index 000000000..3e0cc494c --- /dev/null +++ b/doc/coverageReport/src/base64.cpp.gcov.html @@ -0,0 +1,205 @@ + + + + + + + LCOV - coverage.info.cleaned - src/base64.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src - base64.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:454991.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : // base64 encodig and decoding.
+       2             : //
+       3             : // Based on the implementations by
+       4             : // Jouni Malinen <j@w1.fi> and contributors from wpa_supplicant and hostapd in
+       5             : // http://web.mit.edu/freebsd/head/contrib/wpa/ and
+       6             : // http://web.mit.edu/freebsd/head/contrib/wpa/src/utils/base64.c and
+       7             : // http://web.mit.edu/freebsd/head/contrib/wpa/src/utils/base64.h
+       8             : //
+       9             : // Published under a 3-clause BSD license
+      10             : //
+      11             : 
+      12             : #include <string>
+      13             : #include <cstring>
+      14             : #include <stdexcept>
+      15             : 
+      16             : #include "crpropa/base64.h"
+      17             : 
+      18             : namespace crpropa
+      19             : {
+      20             : 
+      21             : //Alphabet used
+      22             : static const unsigned char encode_alphabet[65] =
+      23             : "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+      24             : static int decode_alphabet[256] = {-1};
+      25             : 
+      26             : /// Encodes data
+      27          99 : std::string Base64::encode(const unsigned char *src, size_t len)
+      28             : {
+      29          99 :                 size_t olen = 4*((len + 2) / 3); /* 3-byte blocks to 4-byte */
+      30             : 
+      31          99 :                 if (olen < len)
+      32           0 :                         throw std::runtime_error("Integer overflow in Base64::encoding, data to large!");
+      33             : 
+      34             :                 std::string outStr;
+      35             :                 outStr.resize(olen);
+      36             : 
+      37             :                 unsigned char *out = (unsigned char*) outStr.c_str();
+      38             :                 unsigned char *pos = out;
+      39             :                 const unsigned char *end, *in;
+      40             : 
+      41          99 :                 end = src + len;
+      42             :                 in = src;
+      43        6666 :                 while (end - in >= 3) {
+      44        6567 :                                 *pos++ = encode_alphabet[in[0] >> 2];
+      45        6567 :                                 *pos++ = encode_alphabet[((in[0] & 0x03) << 4) | (in[1] >> 4)];
+      46        6567 :                                 *pos++ = encode_alphabet[((in[1] & 0x0f) << 2) | (in[2] >> 6)];
+      47        6567 :                                 *pos++ = encode_alphabet[in[2] & 0x3f];
+      48        6567 :                                 in += 3;
+      49             :                 }
+      50             : 
+      51          99 :                 if (end - in) {
+      52          66 :                                 *pos++ = encode_alphabet[in[0] >> 2];
+      53          66 :                                 if (end - in == 1) {
+      54          33 :                                                 *pos++ = encode_alphabet[(in[0] & 0x03) << 4];
+      55          33 :                                                 *pos++ = '=';
+      56             :                                 }
+      57             :                                 else {
+      58          33 :                                                 *pos++ = encode_alphabet[((in[0] & 0x03) << 4) |
+      59          33 :                                                                 (in[1] >> 4)];
+      60          33 :                                                 *pos++ = encode_alphabet[(in[1] & 0x0f) << 2];
+      61             :                                 }
+      62          66 :                                 *pos++ = '=';
+      63             :                 }
+      64             : 
+      65          99 :                 return outStr;
+      66             : }
+      67             : 
+      68             : 
+      69         100 : std::string Base64::decode(const std::string &data)
+      70             : {
+      71             : const unsigned char *src = (unsigned char*) data.c_str();
+      72             : size_t len = data.size();
+      73             : 
+      74         100 : if (decode_alphabet[0] == -1)
+      75             : { // build decode alphabet
+      76             :         std::memset(decode_alphabet, 0x80, 256);
+      77          65 :         for (size_t i = 0; i < sizeof(encode_alphabet) - 1; i++)
+      78          64 :                 decode_alphabet[encode_alphabet[i]] = (unsigned char) i;
+      79           1 :         decode_alphabet['='] = 0;
+      80             : }
+      81             : 
+      82             : size_t olen = 0;
+      83       26656 : for (size_t i = 0; i < len; i++) {
+      84       26556 :         if (decode_alphabet[src[i]] != 0x80)
+      85       26556 :                 olen++;
+      86             : }
+      87             : 
+      88         100 : if (olen == 0 || olen % 4)
+      89           0 :                         throw std::runtime_error("Base64 decode, invalid input size");
+      90             : 
+      91         100 : olen = olen / 4 * 3;
+      92             : std::string str;
+      93             : str.resize(olen);
+      94             : 
+      95             : unsigned char *out = (unsigned char*) str.c_str();
+      96             : unsigned char *pos = out;
+      97             : 
+      98             : size_t count = 0;
+      99             : int pad = 0;
+     100             : unsigned char block[4];
+     101       26589 : for (size_t i = 0; i < len; i++) {
+     102       26556 :         unsigned char tmp = decode_alphabet[src[i]];
+     103       26556 :         if (tmp == 0x80)
+     104           0 :                 continue;
+     105             : 
+     106       26556 :         if (src[i] == '=')
+     107         101 :                 pad++;
+     108       26556 :         block[count] = tmp;
+     109       26556 :         count++;
+     110       26556 :         if (count == 4) {
+     111        6639 :                 *pos++ = (block[0] << 2) | (block[1] >> 4);
+     112        6639 :                 *pos++ = (block[1] << 4) | (block[2] >> 2);
+     113        6639 :                 *pos++ = (block[2] << 6) | block[3];
+     114             :                 count = 0;
+     115        6639 :                 if (pad) {
+     116          67 :                         if (pad == 1)
+     117             :                                 pos--;
+     118          34 :                         else if (pad == 2)
+     119             :                                 pos -= 2;
+     120             :                         else {
+     121           0 :                                 throw std::runtime_error("Base64 decode, invalid padding");
+     122             :                         }
+     123             :                         break;
+     124             :                 }
+     125             :         }
+     126             : }
+     127         100 : return str;
+     128             : }
+     129             : };
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/index-sort-f.html b/doc/coverageReport/src/index-sort-f.html new file mode 100644 index 000000000..b4c3a6afb --- /dev/null +++ b/doc/coverageReport/src/index-sort-f.html @@ -0,0 +1,253 @@ + + + + + + + LCOV - coverage.info.cleaned - src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - srcHitTotalCoverage
Test:coverage.info.cleanedLines:1361270750.3 %
Date:2024-04-08 14:58:22Functions:25142958.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Clock.cpp +
0.0%
+
0.0 %0 / 270.0 %0 / 8
GridTools.cpp +
27.3%27.3%
+
27.3 %67 / 24536.8 %7 / 19
Variant.cpp +
13.7%13.7%
+
13.7 %71 / 51937.5 %18 / 48
Cosmology.cpp +
47.8%47.8%
+
47.8 %44 / 9240.0 %6 / 15
Geometry.cpp +
36.0%36.0%
+
36.0 %18 / 5046.2 %6 / 13
EmissionMap.cpp +
53.2%53.2%
+
53.2 %83 / 15654.5 %18 / 33
Source.cpp +
58.5%58.5%
+
58.5 %459 / 78455.5 %81 / 146
Random.cpp +
57.7%57.7%
+
57.7 %139 / 24156.5 %26 / 46
Module.cpp +
77.1%77.1%
+
77.1 %37 / 4875.0 %9 / 12
ParticleID.cpp +
53.3%53.3%
+
53.3 %16 / 3080.0 %4 / 5
ProgressBar.cpp +
78.0%78.0%
+
78.0 %39 / 5080.0 %4 / 5
PhotonBackground.cpp +
73.3%73.3%
+
73.3 %88 / 12080.0 %12 / 15
Common.cpp +
77.4%77.4%
+
77.4 %48 / 6283.3 %5 / 6
ParticleState.cpp +
85.7%85.7%
+
85.7 %48 / 5694.1 %16 / 17
Candidate.cpp +
87.8%87.8%
+
87.8 %129 / 14794.3 %33 / 35
base64.cpp +
91.8%91.8%
+
91.8 %45 / 49100.0 %2 / 2
ParticleMass.cpp +
96.8%96.8%
+
96.8 %30 / 31100.0 %4 / 4
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/index-sort-l.html b/doc/coverageReport/src/index-sort-l.html new file mode 100644 index 000000000..f65520a55 --- /dev/null +++ b/doc/coverageReport/src/index-sort-l.html @@ -0,0 +1,253 @@ + + + + + + + LCOV - coverage.info.cleaned - src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - srcHitTotalCoverage
Test:coverage.info.cleanedLines:1361270750.3 %
Date:2024-04-08 14:58:22Functions:25142958.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Clock.cpp +
0.0%
+
0.0 %0 / 270.0 %0 / 8
Variant.cpp +
13.7%13.7%
+
13.7 %71 / 51937.5 %18 / 48
GridTools.cpp +
27.3%27.3%
+
27.3 %67 / 24536.8 %7 / 19
Geometry.cpp +
36.0%36.0%
+
36.0 %18 / 5046.2 %6 / 13
Cosmology.cpp +
47.8%47.8%
+
47.8 %44 / 9240.0 %6 / 15
EmissionMap.cpp +
53.2%53.2%
+
53.2 %83 / 15654.5 %18 / 33
ParticleID.cpp +
53.3%53.3%
+
53.3 %16 / 3080.0 %4 / 5
Random.cpp +
57.7%57.7%
+
57.7 %139 / 24156.5 %26 / 46
Source.cpp +
58.5%58.5%
+
58.5 %459 / 78455.5 %81 / 146
PhotonBackground.cpp +
73.3%73.3%
+
73.3 %88 / 12080.0 %12 / 15
Module.cpp +
77.1%77.1%
+
77.1 %37 / 4875.0 %9 / 12
Common.cpp +
77.4%77.4%
+
77.4 %48 / 6283.3 %5 / 6
ProgressBar.cpp +
78.0%78.0%
+
78.0 %39 / 5080.0 %4 / 5
ParticleState.cpp +
85.7%85.7%
+
85.7 %48 / 5694.1 %16 / 17
Candidate.cpp +
87.8%87.8%
+
87.8 %129 / 14794.3 %33 / 35
base64.cpp +
91.8%91.8%
+
91.8 %45 / 49100.0 %2 / 2
ParticleMass.cpp +
96.8%96.8%
+
96.8 %30 / 31100.0 %4 / 4
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/index.html b/doc/coverageReport/src/index.html new file mode 100644 index 000000000..6e1fed226 --- /dev/null +++ b/doc/coverageReport/src/index.html @@ -0,0 +1,253 @@ + + + + + + + LCOV - coverage.info.cleaned - src + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - srcHitTotalCoverage
Test:coverage.info.cleanedLines:1361270750.3 %
Date:2024-04-08 14:58:22Functions:25142958.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Candidate.cpp +
87.8%87.8%
+
87.8 %129 / 14794.3 %33 / 35
Clock.cpp +
0.0%
+
0.0 %0 / 270.0 %0 / 8
Common.cpp +
77.4%77.4%
+
77.4 %48 / 6283.3 %5 / 6
Cosmology.cpp +
47.8%47.8%
+
47.8 %44 / 9240.0 %6 / 15
EmissionMap.cpp +
53.2%53.2%
+
53.2 %83 / 15654.5 %18 / 33
Geometry.cpp +
36.0%36.0%
+
36.0 %18 / 5046.2 %6 / 13
GridTools.cpp +
27.3%27.3%
+
27.3 %67 / 24536.8 %7 / 19
Module.cpp +
77.1%77.1%
+
77.1 %37 / 4875.0 %9 / 12
ParticleID.cpp +
53.3%53.3%
+
53.3 %16 / 3080.0 %4 / 5
ParticleMass.cpp +
96.8%96.8%
+
96.8 %30 / 31100.0 %4 / 4
ParticleState.cpp +
85.7%85.7%
+
85.7 %48 / 5694.1 %16 / 17
PhotonBackground.cpp +
73.3%73.3%
+
73.3 %88 / 12080.0 %12 / 15
ProgressBar.cpp +
78.0%78.0%
+
78.0 %39 / 5080.0 %4 / 5
Random.cpp +
57.7%57.7%
+
57.7 %139 / 24156.5 %26 / 46
Source.cpp +
58.5%58.5%
+
58.5 %459 / 78455.5 %81 / 146
Variant.cpp +
13.7%13.7%
+
13.7 %71 / 51937.5 %18 / 48
base64.cpp +
91.8%91.8%
+
91.8 %45 / 49100.0 %2 / 2
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html new file mode 100644 index 000000000..a7bc79210 --- /dev/null +++ b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/ArchimedeanSpiralField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - ArchimedeanSpiralField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0420.0 %
Date:2024-04-08 14:58:22Functions:0100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ArchimedeanSpiralField5setB0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setR0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setVwEd0
_ZN7crpropa22ArchimedeanSpiralField8setOmegaEd0
_ZN7crpropa22ArchimedeanSpiralFieldC2Edddd0
_ZNK7crpropa22ArchimedeanSpiralField5getB0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getR0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getVwEv0
_ZNK7crpropa22ArchimedeanSpiralField8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa22ArchimedeanSpiralField8getOmegaEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html new file mode 100644 index 000000000..547d3e58d --- /dev/null +++ b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/ArchimedeanSpiralField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - ArchimedeanSpiralField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0420.0 %
Date:2024-04-08 14:58:22Functions:0100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ArchimedeanSpiralField5setB0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setR0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setVwEd0
_ZN7crpropa22ArchimedeanSpiralField8setOmegaEd0
_ZN7crpropa22ArchimedeanSpiralFieldC2Edddd0
_ZNK7crpropa22ArchimedeanSpiralField5getB0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getR0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getVwEv0
_ZNK7crpropa22ArchimedeanSpiralField8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa22ArchimedeanSpiralField8getOmegaEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html new file mode 100644 index 000000000..0b5c7b362 --- /dev/null +++ b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html @@ -0,0 +1,162 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/ArchimedeanSpiralField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - ArchimedeanSpiralField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0420.0 %
Date:2024-04-08 14:58:22Functions:0100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/ArchimedeanSpiralField.h"
+       2             : 
+       3             : namespace crpropa {
+       4             : 
+       5           0 : ArchimedeanSpiralField::ArchimedeanSpiralField(double B_0, double R_0, double Omega, double V_w) {
+       6           0 :         setB0(B_0);
+       7           0 :         setR0(R_0);
+       8           0 :         setOmega(Omega);
+       9           0 :         setVw(V_w);
+      10           0 : }
+      11             : 
+      12           0 : Vector3d ArchimedeanSpiralField::getField(const Vector3d &pos) const {
+      13             :         
+      14             :         double r = pos.getR();
+      15           0 :         double theta = pos.getTheta();
+      16           0 :         double phi =pos.getPhi();
+      17             :         
+      18           0 :         double cos_phi = cos(phi);
+      19           0 :         double sin_phi = sin(phi);
+      20           0 :         double cos_theta = cos(theta);
+      21           0 :         double sin_theta = sin(theta);
+      22             : 
+      23             :         Vector3d B(0.);
+      24             : 
+      25             :         // radial direction
+      26           0 :         double C1 = R_0*R_0/r/r;
+      27           0 :         B.x += C1 * cos_phi * sin_theta;
+      28           0 :         B.y += C1 * sin_phi * sin_theta;
+      29           0 :         B.z += C1 * cos_theta;
+      30             :         
+      31             :         // azimuthal direction  
+      32           0 :         double C2 = - (Omega*R_0*R_0*sin_theta) / (r*V_w);
+      33           0 :         B.x += C2 * (-sin_phi);
+      34           0 :         B.y += C2 * cos_phi;
+      35             : 
+      36             :         // magnetic field switch at z = 0
+      37           0 :         if (pos.z<0.) {
+      38             :                 B *= -1;
+      39             :         }
+      40             : 
+      41             :         // overall scaling
+      42             :         B *= B_0;
+      43             :         
+      44             : 
+      45           0 :         return B;
+      46             : }
+      47             : 
+      48           0 : void ArchimedeanSpiralField::setR0(double R) {
+      49           0 :         R_0 = R;
+      50           0 :         return;
+      51             : }
+      52             : 
+      53           0 : void ArchimedeanSpiralField::setB0(double B) {
+      54           0 :         B_0 = B;
+      55           0 :         return;
+      56             : }
+      57             : 
+      58           0 : void ArchimedeanSpiralField::setOmega(double Om) {
+      59           0 :         Omega = Om;
+      60           0 :         return;
+      61             : }
+      62             : 
+      63           0 : void ArchimedeanSpiralField::setVw(double v) {
+      64           0 :         V_w = v;
+      65           0 :         return;
+      66             : }
+      67             : 
+      68             : 
+      69           0 : double ArchimedeanSpiralField::getR0() const {
+      70           0 :         return R_0;
+      71             : }
+      72             : 
+      73           0 : double ArchimedeanSpiralField::getB0() const{
+      74           0 :         return B_0;
+      75             : }
+      76             : 
+      77           0 : double ArchimedeanSpiralField::getOmega() const{
+      78           0 :         return Omega;
+      79             : }
+      80             : 
+      81           0 : double ArchimedeanSpiralField::getVw() const {
+      82           0 :         return V_w;
+      83             : }
+      84             : 
+      85             : 
+      86             : } //end namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html new file mode 100644 index 000000000..57aca7fcf --- /dev/null +++ b/doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html @@ -0,0 +1,144 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/CMZField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - CMZField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10310796.3 %
Date:2024-04-08 14:58:22Functions:1818100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8CMZField13setUseICFieldEb1
_ZN7crpropa8CMZField13setUseMCFieldEb1
_ZN7crpropa8CMZField14setUseNTFFieldEb1
_ZN7crpropa8CMZField14setUseRadioArcEb1
_ZNK7crpropa8CMZField10getICFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField10getMCFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField11getNTFFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField16getRadioArcFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField13getUseICFieldEv2
_ZNK7crpropa8CMZField13getUseMCFieldEv2
_ZNK7crpropa8CMZField14getUseNTFFieldEv2
_ZNK7crpropa8CMZField14getUseRadioArcEv2
_ZN7crpropa8CMZFieldC2Ev5
_ZNK7crpropa8CMZField4getAEd8
_ZNK7crpropa8CMZField4getLEd8
_ZNK7crpropa8CMZField4BPolERKNS_7Vector3IdEES4_ddd9
_ZNK7crpropa8CMZField3BAzERKNS_7Vector3IdEES4_ddd14
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/CMZField.cpp.func.html b/doc/coverageReport/src/magneticField/CMZField.cpp.func.html new file mode 100644 index 000000000..d0edc51bc --- /dev/null +++ b/doc/coverageReport/src/magneticField/CMZField.cpp.func.html @@ -0,0 +1,144 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/CMZField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - CMZField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10310796.3 %
Date:2024-04-08 14:58:22Functions:1818100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8CMZField13setUseICFieldEb1
_ZN7crpropa8CMZField13setUseMCFieldEb1
_ZN7crpropa8CMZField14setUseNTFFieldEb1
_ZN7crpropa8CMZField14setUseRadioArcEb1
_ZN7crpropa8CMZFieldC2Ev5
_ZNK7crpropa8CMZField10getICFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField10getMCFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField11getNTFFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField13getUseICFieldEv2
_ZNK7crpropa8CMZField13getUseMCFieldEv2
_ZNK7crpropa8CMZField14getUseNTFFieldEv2
_ZNK7crpropa8CMZField14getUseRadioArcEv2
_ZNK7crpropa8CMZField16getRadioArcFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField3BAzERKNS_7Vector3IdEES4_ddd14
_ZNK7crpropa8CMZField4BPolERKNS_7Vector3IdEES4_ddd9
_ZNK7crpropa8CMZField4getAEd8
_ZNK7crpropa8CMZField4getLEd8
_ZNK7crpropa8CMZField8getFieldERKNS_7Vector3IdEE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html b/doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html new file mode 100644 index 000000000..20cf216cb --- /dev/null +++ b/doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html @@ -0,0 +1,382 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/CMZField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - CMZField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10310796.3 %
Date:2024-04-08 14:58:22Functions:1818100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/CMZField.h"
+       2             : #include "crpropa/Units.h"
+       3             : 
+       4             : namespace crpropa {
+       5             : 
+       6           5 : CMZField::CMZField() {
+       7           5 :     useMCField = false;
+       8           5 :     useICField = true;
+       9           5 :     useNTFField = false;
+      10           5 :     useRadioArc = false;
+      11           5 : }
+      12             : 
+      13           8 : double CMZField::getA(double a1) const {
+      14           8 :     return 4*log(2)/a1/a1;  
+      15             : }
+      16             : 
+      17           8 : double CMZField::getL(double a2) const {
+      18           8 :     return a2/2*log(2);
+      19             : }
+      20             : 
+      21           9 : Vector3d CMZField::BPol(const Vector3d& position,const Vector3d& mid, double B1, double a, double L) const{
+      22             :     // cylindircal coordinates
+      23             :     Vector3d pos = position - mid;
+      24           9 :     double r = sqrt(pos.x*pos.x + pos.y*pos.y);
+      25           9 :     double phi = std::atan2(pos.y, pos.x);
+      26             : 
+      27           9 :     double r1 = 1/(1+a*pos.z*pos.z);
+      28           9 :     double Bs = B1*exp(-r1*r/L);
+      29           9 :     double Br = 2*a*pow_integer<3>(r1)*r*pos.z*Bs;
+      30             :     
+      31             :     Vector3d b = Vector3d(0.);
+      32           9 :     b.z = r1*r1*Bs;
+      33             :     // transform to cartesian coordinates
+      34           9 :     b.x = Br*cos(phi);
+      35           9 :     b.y = Br*sin(phi);
+      36           9 :     return b;
+      37             : }
+      38             : 
+      39          14 : Vector3d CMZField::BAz(const Vector3d& position, const Vector3d& mid, double B1, double eta, double R) const {
+      40             :     // cylindrical coordinates
+      41             :     Vector3d pos = position - mid;
+      42          14 :     double r = sqrt(pos.x*pos.x + pos.y*pos.y);
+      43          14 :     double phi = std::atan2(pos.y,pos.x);
+      44             : 
+      45             :     Vector3d bVec(0.);
+      46          14 :     double Hc = R/sqrt(log(2));
+      47             :     double b = 1.;
+      48             :     double m = 1;
+      49          14 :     double r1 = R/10;
+      50          14 :     double v = m/eta*log((r+b)/(R+b));
+      51          14 :     double cosV = cos(v + m*phi);
+      52             : 
+      53             :     double Br=0;
+      54             :     double Bphi=0;
+      55             :     
+      56          14 :     if(r>r1){
+      57          13 :         double Pre = B1*cosV*exp(-pos.z*pos.z/Hc/Hc);
+      58          13 :         Br = Pre*R/r;
+      59          13 :         Bphi=-Pre/eta*R/(r+b);
+      60             :     }
+      61             :     else{
+      62           1 :         double Pre = B1*exp(-pos.z*pos.z/Hc/Hc)*R/r1*(3*r/r1 - 2*r*r/r1/r1)*cosV;
+      63             :         Br = Pre;
+      64           1 :         Bphi = 1 + 6*(r-r1)/(2*r-3*r1)*(sin(v+m*phi)-sin(v))/cosV;
+      65           1 :         Bphi *= -Pre*r/eta/(r+b);
+      66             :     }
+      67             : 
+      68          14 :     bVec.x = Br*cos(phi) - Bphi*sin(phi);
+      69          14 :     bVec.y = Br*sin(phi) + Bphi*cos(phi);
+      70             : 
+      71          14 :     return bVec;
+      72             : }
+      73             : 
+      74           2 : bool CMZField::getUseMCField() const {
+      75           2 :     return useMCField;
+      76             : }
+      77           2 : bool CMZField::getUseICField() const {
+      78           2 :     return useICField;
+      79             : }
+      80           2 : bool CMZField::getUseNTFField() const {
+      81           2 :     return useNTFField;
+      82             : }
+      83           2 : bool CMZField::getUseRadioArc() const {
+      84           2 :     return useRadioArc;
+      85             : }
+      86             : 
+      87           1 : void CMZField::setUseMCField(bool use) {
+      88           1 :     useMCField = use;
+      89           1 : }
+      90           1 : void CMZField::setUseICField(bool use) {
+      91           1 :     useICField = use;
+      92           1 : }
+      93           1 : void CMZField::setUseNTFField(bool use) {
+      94           1 :     useNTFField = use;
+      95           1 : }
+      96           1 : void CMZField::setUseRadioArc(bool use) {
+      97           1 :     useRadioArc = use;
+      98           1 : }
+      99             : 
+     100           1 : Vector3d CMZField::getMCField(const Vector3d& pos) const {//Field in molecular clouds
+     101             :     Vector3d b(0.);
+     102             :     double eta=0.01;
+     103             :     double N=59; // normalization factor, depends on eta
+     104             : 
+     105             :         // azimuthal component in dense clouds
+     106             :     //A=SgrC 
+     107             :     Vector3d mid(0,-81.59*pc, -16.32*pc);
+     108             :     double R = 1.7*pc; 
+     109             :     double B1=2.1e-3/N;
+     110           1 :     b += BAz(pos, mid, B1, eta, R);
+     111             : 
+     112             :     // A=G0.253+0.016 Dust Ridge A
+     113             :     mid = Vector3d(0, 37.53*pc, -2.37*pc);
+     114             :     R=2.4*pc; 
+     115             :     B1=2.5e-3/N;
+     116           1 :     b += BAz(pos, mid, B1, eta, R);
+     117             : 
+     118             :     //A=Dust Ridge B
+     119             :     mid = Vector3d(0, 50.44, 8.16)*pc;
+     120             :     R=1.9*pc; 
+     121             :     B1=0.9e-3/N;
+     122           1 :     b += BAz(pos, mid, B1, eta, R);
+     123             :     
+     124             :     //A=Dust Ridge C
+     125             :     mid = Vector3d(0,56.37,7.71)*pc;
+     126             :     R=1.9*pc; 
+     127             :     B1=1.2e-3/N;
+     128           1 :     b += BAz(pos, mid, B1, eta, R);
+     129             : 
+     130             :     //A=Dust Ridge D
+     131             :     mid = Vector3d(0, 60.82, 7.42)*pc;
+     132             :     R=3.3*pc; 
+     133             :     B1=1.7e-3/N;
+     134           1 :     b += BAz(pos, mid, B1, eta, R);
+     135             :     
+     136             :     //A=Dust Ridge E
+     137             :     mid = Vector3d(0, 70.91, 0.74)*pc;
+     138             :     R=3.5*pc; 
+     139             :     B1=4.1e-3/N;
+     140           1 :     b += BAz(pos, mid, B1, eta, R);
+     141             :         
+     142             :     //A=Dust Ridge F
+     143             :     mid = Vector3d(0, 73.58, 2.97)*pc;
+     144             :     R=2.4*pc; 
+     145             :     B1=3.9e-3/N;
+     146           1 :     b += BAz(pos, mid, B1, eta, R);
+     147             : 
+     148             :     //Sgr D
+     149             :     mid = Vector3d(0, 166.14, -10.38)*pc;
+     150             :     R=1.8*pc;
+     151             :     B1=0.8e-3/N;
+     152           1 :     b += BAz(pos, mid, B1, eta, R);
+     153             : 
+     154             :     //Sgr B2
+     155             :     mid = Vector3d(0, 97.01, -5.93)*pc;
+     156             :     R=14*pc; 
+     157             :     B1=1.0e-3/N;
+     158           1 :     b += BAz(pos, mid, B1, eta, R);
+     159             :         
+     160             :     //A=Inner R=5pc
+     161             :     mid = Vector3d(0, -8.3, -6.9)*pc;
+     162             :     R=5*pc; 
+     163             :     B1=3.0e-3/0.91;    
+     164           1 :     b += BAz(pos, mid, B1, 0.77, R); // different eta value!
+     165             : 
+     166             :     //20 km s^-1
+     167             :     mid = Vector3d(0, -19.29,-11.87)*pc;
+     168             :     R=9.4*pc; 
+     169             :     B1=2.7e-3/N;
+     170           1 :     b += BAz(pos, mid, B1, eta, R);    
+     171             :     
+     172             :     //50 km s^-1
+     173             :     mid = Vector3d(0, -2.97, -10.38)*pc;
+     174             :     R=9.4*pc; 
+     175             :     B1=3.7e-3/N;
+     176           1 :     b += BAz(pos, mid, B1, eta, R);    
+     177             :     
+     178             :     //SgrA* is different orrientated! 
+     179             :     //only phi component
+     180           1 :     double x = pos.x;
+     181           1 :     double y = pos.y + 8.3*pc;
+     182           1 :     double z = pos.z + 6.9*pc;
+     183             :     R=1.2e12; 
+     184             :     B1=65./3.07;
+     185             :     double Hc = R/sqrt(log(2));
+     186           1 :     double r = sqrt(x*x + y*y);
+     187             :     double r1 = R/10;
+     188           1 :     double phi= std::atan2(y,x);
+     189             :     double Bphi;
+     190             : 
+     191           1 :     if(r>r1){
+     192           1 :         Bphi = - B1*exp(-z*z/Hc/Hc)*R/r;
+     193             :     }
+     194             :     else{
+     195           0 :         - B1*exp(-z*z/Hc/Hc)*R/r1*(3*r/r1- 2*r*r/r1*r1);
+     196             :     }
+     197             : 
+     198           1 :     b.x -= Bphi*sin(phi);
+     199           1 :     b.y += Bphi*cos(phi);
+     200             : 
+     201           1 :     return b*gauss;
+     202             : } 
+     203             : 
+     204           1 : Vector3d CMZField::getICField(const Vector3d& pos) const {//Field in intercloud medium--> poloidal field
+     205             :     Vector3d mid(0.,-8.3*pc,-6.9*pc);
+     206             : 
+     207             :     double eta = 0.85;
+     208             :     double B1 = 1e-5*gauss;
+     209             :     double B2 = B1/eta;
+     210             :     double a = 4*log(2)/pow(70*pc, 2); 
+     211             :     double L = 158*pc/log(2);
+     212             : 
+     213           1 :     return BPol(pos, mid, B2, a, L);
+     214             : }                                                         
+     215             :   
+     216           1 : Vector3d CMZField::getNTFField(const Vector3d& pos) const {//Field in the non-thermal filaments--> predominantly poloidal field (except "pelical"-> azimuthal)
+     217             :     Vector3d b(0.); 
+     218             :     Vector3d mid(0.);
+     219             : 
+     220             :     //A=SgrC
+     221             :     mid = Vector3d(0., -81.59,-1.48)*pc;
+     222             :     double a1=27.44*pc;
+     223             :     double a2=1.73*pc;
+     224             :     double eta=0.48;
+     225             :     double B1=1.e-4;
+     226           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
+     227             : 
+     228             :     //A=G359.15-0.2 The Snake
+     229             :     mid = Vector3d(0, -126.1,-25.22)*pc;
+     230             :     a1=12.86*pc;
+     231             :     a2=2.22*pc;
+     232             :     B1=88.e-6;
+     233           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
+     234             : 
+     235             :     //A=G359.54+0.18 Nonthermal Filament
+     236             :     mid = Vector3d(0, -68.24,25.22)*pc;
+     237             :     a1=15.08*pc;
+     238             :     a2=2.72;
+     239             :     B1=1.e-3;
+     240           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
+     241             : 
+     242             :     //A=G359.79 +17 Nonthermal Filament
+     243             :     mid = Vector3d(0,-31.15,23.74)*pc;
+     244             :     a1=16.07*pc;
+     245             :     a2=3.46*pc;
+     246             :     B1=1.e-3;
+     247           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
+     248             : 
+     249             :     //A=G359.96 +0.09  Nonthermal Filament Southern Thread
+     250             :     mid = Vector3d(0, 5.93, 16.32)*pc;
+     251             :     a1=28.68*pc;
+     252             :     a2=1.73*pc;
+     253             :     B1=1.e-4;
+     254           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
+     255             : 
+     256             :     //A=G0.09 +0.17  Nonthermal Filament Northern thread
+     257             :     mid = Vector3d(0, 13.35, 25.22)*pc;
+     258             :     a1=29.42*pc;
+     259             :     a2=2.23*pc;
+     260             :     B1=140.e-6;
+     261           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
+     262             : 
+     263             :     //A=G359.85+0.47  Nonthermal Filament The Pelican  is not poloidal but azimuthal
+     264             :     mid = Vector3d(0, -22.25, 69.73)*pc;
+     265             :     a1=11.37*pc;
+     266             :     a2=2.23*pc;
+     267             :     B1=70.e-6 /eta;
+     268             :     // by and bz switched because pelican is differently oriented
+     269           1 :     Vector3d bPelican = BPol(pos, mid, B1/eta, getA(a1), getL(a2));
+     270           1 :     b.x += bPelican.x;
+     271           1 :     b.y += bPelican.z;
+     272           1 :     b.z += bPelican.y;
+     273             :     
+     274           1 :         return b*gauss;
+     275             : }
+     276             :   
+     277           1 : Vector3d CMZField::getRadioArcField(const Vector3d& pos) const {//Field in the non-thermal filaments--> predominantly poloidal field
+     278             :     //poloidal field in the non-thermal filament region A=RadioArc
+     279             :     double eta=0.48;
+     280             :     Vector3d mid(0,26.7*pc,10.38*pc);
+     281             :     double a1=70.47*pc;// arcmin-> deg->cm
+     282             :     double a2=9.89*pc;// arcmin-> deg-> cm
+     283             :     double B1=1.e-3;
+     284           1 :     return BPol(pos, mid, B1/eta, getA(a1), getL(a2))*gauss;
+     285             : }
+     286             : 
+     287           1 : Vector3d CMZField::getField(const Vector3d& pos) const{
+     288             :     Vector3d b(0.);
+     289             : 
+     290           1 :     if(useMCField){
+     291           0 :         b += getMCField(pos);
+     292             :     }
+     293           1 :     if(useICField){
+     294           1 :         b += getICField(pos);
+     295             :     }
+     296           1 :     if(useNTFField){
+     297           0 :         b += getNTFField(pos);
+     298             :     }
+     299           1 :     if(useRadioArc){
+     300           0 :         b += getRadioArcField(pos);
+     301             :     }
+     302             : 
+     303           1 :     return b;
+     304             : }
+     305             : 
+     306             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html new file mode 100644 index 000000000..4cfb03c01 --- /dev/null +++ b/doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html @@ -0,0 +1,188 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/JF12Field.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - JF12Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:02310.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16PlanckJF12bFieldC2Ev0
_ZN7crpropa9JF12Field12setUseXFieldEb0
_ZN7crpropa9JF12Field13isUsingXFieldEv0
_ZN7crpropa9JF12Field14randomStriatedEi0
_ZN7crpropa9JF12Field15getStriatedGridEv0
_ZN7crpropa9JF12Field15randomTurbulentEi0
_ZN7crpropa9JF12Field15setStriatedGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa9JF12Field15setUseDiskFieldEb0
_ZN7crpropa9JF12Field16getTurbulentGridEv0
_ZN7crpropa9JF12Field16isUsingDiskFieldEv0
_ZN7crpropa9JF12Field16setTurbulentGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa9JF12Field18setUseRegularFieldEb0
_ZN7crpropa9JF12Field19isUsingRegularFieldEv0
_ZN7crpropa9JF12Field19setUseStriatedFieldEb0
_ZN7crpropa9JF12Field20isUsingStriatedFieldEv0
_ZN7crpropa9JF12Field20setUseTurbulentFieldEb0
_ZN7crpropa9JF12Field21isUsingTurbulentFieldEv0
_ZN7crpropa9JF12Field23setUseToroidalHaloFieldEb0
_ZN7crpropa9JF12Field24isUsingToroidalHaloFieldEv0
_ZN7crpropa9JF12FieldC2Ev0
_ZNK7crpropa9JF12Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9JF12Field15getRegularFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16getStriatedFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16logisticFunctionERKdS2_S2_0
_ZNK7crpropa9JF12Field17getTurbulentFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field20getToroidalHaloFieldERKdS2_S2_S2_0
_ZNK7crpropa9JF12Field20getTurbulentStrengthERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field9getXFieldERKdS2_S2_S2_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/JF12Field.cpp.func.html b/doc/coverageReport/src/magneticField/JF12Field.cpp.func.html new file mode 100644 index 000000000..f4e99fdd5 --- /dev/null +++ b/doc/coverageReport/src/magneticField/JF12Field.cpp.func.html @@ -0,0 +1,188 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/JF12Field.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - JF12Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:02310.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16PlanckJF12bFieldC2Ev0
_ZN7crpropa9JF12Field12setUseXFieldEb0
_ZN7crpropa9JF12Field13isUsingXFieldEv0
_ZN7crpropa9JF12Field14randomStriatedEi0
_ZN7crpropa9JF12Field15getStriatedGridEv0
_ZN7crpropa9JF12Field15randomTurbulentEi0
_ZN7crpropa9JF12Field15setStriatedGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa9JF12Field15setUseDiskFieldEb0
_ZN7crpropa9JF12Field16getTurbulentGridEv0
_ZN7crpropa9JF12Field16isUsingDiskFieldEv0
_ZN7crpropa9JF12Field16setTurbulentGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa9JF12Field18setUseRegularFieldEb0
_ZN7crpropa9JF12Field19isUsingRegularFieldEv0
_ZN7crpropa9JF12Field19setUseStriatedFieldEb0
_ZN7crpropa9JF12Field20isUsingStriatedFieldEv0
_ZN7crpropa9JF12Field20setUseTurbulentFieldEb0
_ZN7crpropa9JF12Field21isUsingTurbulentFieldEv0
_ZN7crpropa9JF12Field23setUseToroidalHaloFieldEb0
_ZN7crpropa9JF12Field24isUsingToroidalHaloFieldEv0
_ZN7crpropa9JF12FieldC2Ev0
_ZNK7crpropa9JF12Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9JF12Field15getRegularFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16getStriatedFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16logisticFunctionERKdS2_S2_0
_ZNK7crpropa9JF12Field17getTurbulentFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field20getToroidalHaloFieldERKdS2_S2_S2_0
_ZNK7crpropa9JF12Field20getTurbulentStrengthERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field9getXFieldERKdS2_S2_S2_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html b/doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html new file mode 100644 index 000000000..71e09d723 --- /dev/null +++ b/doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html @@ -0,0 +1,452 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/JF12Field.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - JF12Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:02310.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/JF12Field.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
+       4             : #include "crpropa/Random.h"
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           0 : JF12Field::JF12Field() {
+       9           0 :         useRegularField = true;
+      10           0 :         useStriatedField = false;
+      11           0 :         useTurbulentField = false;
+      12           0 :         useDiskField = true;
+      13           0 :         useToroidalHaloField = true;
+      14           0 :         useXField = true;
+      15             : 
+      16             :         // spiral arm parameters
+      17           0 :         pitch = 11.5 * M_PI / 180;
+      18           0 :         sinPitch = sin(pitch);
+      19           0 :         cosPitch = cos(pitch);
+      20           0 :         tanPitch = tan(pitch);
+      21           0 :         cotPitch =  1. / tanPitch;
+      22           0 :         tan90MinusPitch = tan(M_PI / 2 - pitch);
+      23             : 
+      24           0 :         rArms[0] = 5.1 * kpc;
+      25           0 :         rArms[1] = 6.3 * kpc;
+      26           0 :         rArms[2] = 7.1 * kpc;
+      27           0 :         rArms[3] = 8.3 * kpc;
+      28           0 :         rArms[4] = 9.8 * kpc;
+      29           0 :         rArms[5] = 11.4 * kpc;
+      30           0 :         rArms[6] = 12.7 * kpc;
+      31           0 :         rArms[7] = 15.5 * kpc;
+      32             : 
+      33             :         // regular field parameters
+      34           0 :         bRing = 0.1 * muG;
+      35           0 :         hDisk = 0.40 * kpc;
+      36           0 :         wDisk = 0.27 * kpc;
+      37             : 
+      38           0 :         bDisk[0] = 0.1 * muG;
+      39           0 :         bDisk[1] = 3.0 * muG;
+      40           0 :         bDisk[2] = -0.9 * muG;
+      41           0 :         bDisk[3] = -0.8 * muG;
+      42           0 :         bDisk[4] = -2.0 * muG;
+      43           0 :         bDisk[5] = -4.2 * muG;
+      44           0 :         bDisk[6] = 0.0 * muG;
+      45           0 :         bDisk[7] = 2.7 * muG;
+      46             : 
+      47           0 :         bNorth = 1.4 * muG;
+      48           0 :         bSouth = -1.1 * muG;
+      49           0 :         rNorth = 9.22 * kpc;
+      50           0 :         rSouth = 17 * kpc;
+      51           0 :         wHalo = 0.20 * kpc;
+      52           0 :         z0 = 5.3 * kpc;
+      53             : 
+      54           0 :         bX = 4.6 * muG;
+      55           0 :         thetaX0 = 49.0 * M_PI / 180;
+      56           0 :         sinThetaX0 = sin(thetaX0);
+      57           0 :         cosThetaX0 = cos(thetaX0);
+      58           0 :         tanThetaX0 = tan(thetaX0);
+      59           0 :         cotThetaX0 = 1. / tanThetaX0;
+      60           0 :         rXc = 4.8 * kpc;
+      61           0 :         rX = 2.9 * kpc;
+      62             : 
+      63             :         // striated field parameter
+      64           0 :         sqrtbeta = sqrt(1.36);
+      65             : 
+      66             :         // turbulent field parameters
+      67           0 :         bDiskTurb[0] = 10.81 * muG;
+      68           0 :         bDiskTurb[1] = 6.96 * muG;
+      69           0 :         bDiskTurb[2] = 9.59 * muG;
+      70           0 :         bDiskTurb[3] = 6.96 * muG;
+      71           0 :         bDiskTurb[4] = 1.96 * muG;
+      72           0 :         bDiskTurb[5] = 16.34 * muG;
+      73           0 :         bDiskTurb[6] = 37.29 * muG;
+      74           0 :         bDiskTurb[7] = 10.35 * muG;
+      75             : 
+      76           0 :         bDiskTurb5 = 7.63 * muG;
+      77           0 :         zDiskTurb = 0.61 * kpc;
+      78             : 
+      79           0 :         bHaloTurb = 4.68 * muG;
+      80           0 :         rHaloTurb = 10.97 * kpc;
+      81           0 :         zHaloTurb = 2.84 * kpc;
+      82           0 : }
+      83             : 
+      84           0 : void JF12Field::randomStriated(int seed) {
+      85           0 :         useStriatedField = true;
+      86             :         int N = 100;
+      87           0 :         striatedGrid = new Grid1f(Vector3d(0.), N, 0.1 * kpc);
+      88             : 
+      89           0 :         Random random;
+      90           0 :         if (seed != 0)
+      91           0 :                 random.seed(seed);
+      92             : 
+      93           0 :         for (int ix = 0; ix < N; ix++)
+      94           0 :                 for (int iy = 0; iy < N; iy++)
+      95           0 :                         for (int iz = 0; iz < N; iz++) {
+      96           0 :                                 float &f = striatedGrid->get(ix, iy, iz);
+      97           0 :                                 f = round(random.rand()) * 2 - 1;
+      98             :                         }
+      99           0 : }
+     100             : 
+     101             : #ifdef CRPROPA_HAVE_FFTW3F
+     102           0 : void JF12Field::randomTurbulent(int seed) {
+     103           0 :         useTurbulentField = true;
+     104             :         // turbulent field with Kolmogorov spectrum, B_rms = 1 (will be scaled) and Lc = 60 parsec, and 256 grid points.
+     105             :         // Note that the inertial range of the turbulence is less than 2 orders of magnitude.
+     106             :     const double lMin = 8 * parsec;
+     107             :     const double lMax = 272 * parsec;
+     108             :     const double Brms = 1;
+     109             :     const double spacing = 4 * parsec;
+     110             :     const double grid_n = 256;
+     111             : 
+     112             :     auto spectrum = SimpleTurbulenceSpectrum(Brms, lMin, lMax);
+     113             :     auto gp = GridProperties(Vector3d(0.), grid_n, spacing);
+     114           0 :     auto tf = SimpleGridTurbulence(spectrum, gp, seed);
+     115           0 :     turbulentGrid = tf.getGrid();
+     116             : 
+     117           0 : }
+     118             : #endif
+     119             : 
+     120           0 : void JF12Field::setStriatedGrid(ref_ptr<Grid1f> grid) {
+     121           0 :         useStriatedField = true;
+     122           0 :         striatedGrid = grid;
+     123           0 : }
+     124             : 
+     125           0 : void JF12Field::setTurbulentGrid(ref_ptr<Grid3f> grid) {
+     126           0 :         useTurbulentField = true;
+     127           0 :         turbulentGrid = grid;
+     128           0 : }
+     129             : 
+     130           0 : ref_ptr<Grid1f> JF12Field::getStriatedGrid() {
+     131           0 :         return striatedGrid;
+     132             : }
+     133             : 
+     134           0 : ref_ptr<Grid3f> JF12Field::getTurbulentGrid() {
+     135           0 :         return turbulentGrid;
+     136             : }
+     137             : 
+     138           0 : void JF12Field::setUseRegularField(bool use) {
+     139           0 :         useRegularField = use;
+     140           0 : }
+     141             : 
+     142           0 : void JF12Field::setUseDiskField(bool use) {
+     143           0 :         useDiskField = use;
+     144           0 : }
+     145             : 
+     146           0 : void JF12Field::setUseToroidalHaloField(bool use) {
+     147           0 :         useToroidalHaloField = use;
+     148           0 : }
+     149             : 
+     150           0 : void JF12Field::setUseXField(bool use) {
+     151           0 :         useXField = use;
+     152           0 : }
+     153             : 
+     154           0 : void JF12Field::setUseStriatedField(bool use) {
+     155           0 :         if ((use) and !(striatedGrid)) {
+     156           0 :                 KISS_LOG_WARNING << "JF12Field: No striated field set: ignored. Run e.g. randomStriated().";
+     157           0 :                 return;
+     158             :         }
+     159           0 :         useStriatedField = use;
+     160             : }
+     161             : 
+     162           0 : void JF12Field::setUseTurbulentField(bool use) {
+     163           0 :         if ((use) and !(turbulentGrid)) {
+     164           0 :                 KISS_LOG_WARNING << "JF12Field: No turbulent field set: ignored. Run e.g. randomTurbulent().";
+     165           0 :                 return;
+     166             :         }
+     167           0 :         useTurbulentField = use;
+     168             : }
+     169             : 
+     170           0 : bool JF12Field::isUsingRegularField() {
+     171           0 :         return useRegularField;
+     172             : }
+     173             : 
+     174           0 : bool JF12Field::isUsingDiskField() {
+     175           0 :         return useDiskField;
+     176             : }
+     177             : 
+     178           0 : bool JF12Field::isUsingToroidalHaloField() {
+     179           0 :         return useToroidalHaloField;
+     180             : }
+     181             : 
+     182           0 : bool JF12Field::isUsingXField() {
+     183           0 :         return useXField;
+     184             : }
+     185             : 
+     186           0 : bool JF12Field::isUsingStriatedField() {
+     187           0 :         return useStriatedField;
+     188             : }
+     189             : 
+     190           0 : bool JF12Field::isUsingTurbulentField() {
+     191           0 :         return useTurbulentField;
+     192             : }
+     193             : 
+     194           0 : double JF12Field::logisticFunction(const double& x, const double& x0, const double& w) const {
+     195           0 :         return 1. / (1. + exp(-2. * (fabs(x) - x0) / w));
+     196             : }
+     197             : 
+     198           0 : Vector3d JF12Field::getRegularField(const Vector3d& pos) const {
+     199             :         Vector3d b(0.);
+     200             : 
+     201             :         double d = pos.getR(); // distance to galactic center
+     202             : 
+     203           0 :         if (d < 20 * kpc) {
+     204           0 :                 double r = sqrt(pos.x * pos.x + pos.y * pos.y); // in-plane radius
+     205           0 :                 double phi = pos.getPhi(); // azimuth
+     206           0 :                 double sinPhi = sin(phi);
+     207           0 :                 double cosPhi = cos(phi);
+     208             : 
+     209           0 :                 b += getDiskField(r, pos.z, phi, sinPhi, cosPhi);
+     210           0 :                 b += getToroidalHaloField(r, pos.z, sinPhi, cosPhi);
+     211           0 :                 b += getXField(r, pos.z, sinPhi, cosPhi);
+     212             :         }
+     213             : 
+     214           0 :         return b;
+     215             : }
+     216             : 
+     217           0 : Vector3d JF12Field::getDiskField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
+     218             :         Vector3d b(0.);
+     219           0 :         if (useDiskField) {
+     220           0 :                 double lfDisk = logisticFunction(z, hDisk, wDisk);
+     221           0 :                 if (r > 3 * kpc) {
+     222             :                         double bMag;
+     223           0 :                         if (r < 5 * kpc) {
+     224             :                                 // molecular ring
+     225           0 :                                 bMag = bRing * (5 * kpc / r) * (1 - lfDisk);
+     226           0 :                                 b.x += -bMag * sinPhi;
+     227           0 :                                 b.y += bMag * cosPhi;
+     228             :                         } else {
+     229             :                                 // spiral region
+     230           0 :                                 double r_negx = r * exp(-(phi - M_PI) / tan90MinusPitch);
+     231           0 :                                 if (r_negx > rArms[7])
+     232           0 :                                         r_negx = r * exp(-(phi + M_PI) / tan90MinusPitch);
+     233           0 :                                 if (r_negx > rArms[7])
+     234           0 :                                         r_negx = r * exp(-(phi + 3 * M_PI) / tan90MinusPitch);
+     235             : 
+     236           0 :                                 for (int i = 7; i >= 0; i--)
+     237           0 :                                         if (r_negx < rArms[i])
+     238           0 :                                                 bMag = bDisk[i];
+     239             : 
+     240           0 :                                 bMag *= (5 * kpc / r) * (1 - lfDisk);
+     241           0 :                                 b.x += bMag * (sinPitch * cosPhi - cosPitch * sinPhi);
+     242           0 :                                 b.y += bMag * (sinPitch * sinPhi + cosPitch * cosPhi);
+     243             :                         }
+     244             :                 }
+     245             :         }
+     246           0 :         return b;
+     247             : }
+     248             : 
+     249           0 : Vector3d JF12Field::getToroidalHaloField(const double& r, const double& z, const double& sinPhi, const double& cosPhi) const {
+     250             :         Vector3d b(0.);
+     251             : 
+     252           0 :         if (useToroidalHaloField && (r * r + z * z > 1 * kpc * kpc)){
+     253             : 
+     254           0 :                 double lfDisk = logisticFunction(z, hDisk, wDisk);
+     255           0 :                 double bMagH = exp(-fabs(z) / z0) * lfDisk;
+     256             : 
+     257           0 :                 if (z >= 0)
+     258           0 :                         bMagH *= bNorth * (1 - logisticFunction(r, rNorth, wHalo));
+     259             :                 else
+     260           0 :                         bMagH *= bSouth * (1 - logisticFunction(r, rSouth, wHalo));
+     261           0 :                 b.x += -bMagH * sinPhi;
+     262           0 :                 b.y += bMagH * cosPhi;
+     263             :         }
+     264           0 :         return b;
+     265             : }
+     266             : 
+     267           0 : Vector3d JF12Field::getXField(const double& r, const double& z, const double& sinPhi, const double& cosPhi) const {
+     268             :         Vector3d b(0.);
+     269             : 
+     270           0 :         if (useXField && (r * r + z * z > 1 * kpc * kpc)){
+     271             :                 double bMagX;
+     272             :                 double sinThetaX, cosThetaX;
+     273             :                 double rp;
+     274           0 :                 double rc = rXc + fabs(z) / tanThetaX0;
+     275           0 :                 if (r < rc) {
+     276             :                         // varying elevation region
+     277           0 :                         rp = r * rXc / rc;
+     278           0 :                         bMagX = bX * exp(-1 * rp / rX) * pow(rXc / rc, 2.);
+     279           0 :                         double thetaX = atan2(fabs(z), (r - rp));
+     280           0 :                         if (z == 0)
+     281             :                                 thetaX = M_PI / 2.;
+     282           0 :                         sinThetaX = sin(thetaX);
+     283           0 :                         cosThetaX = cos(thetaX);
+     284             :                 } else {
+     285             :                         // constant elevation region
+     286           0 :                         rp = r - fabs(z) / tanThetaX0;
+     287           0 :                         bMagX = bX * exp(-rp / rX) * (rp / r);
+     288           0 :                         sinThetaX = sinThetaX0;
+     289           0 :                         cosThetaX = cosThetaX0;
+     290             :                 }
+     291           0 :                 double zsign = z < 0 ? -1 : 1;
+     292           0 :                 b.x += zsign * bMagX * cosThetaX * cosPhi;
+     293           0 :                 b.y += zsign * bMagX * cosThetaX * sinPhi;
+     294           0 :                 b.z += bMagX * sinThetaX;
+     295             :         }
+     296           0 :         return b;
+     297             : }
+     298             : 
+     299           0 : Vector3d JF12Field::getStriatedField(const Vector3d& pos) const {
+     300           0 :         return (getRegularField(pos)
+     301           0 :                         * (1. + sqrtbeta * striatedGrid->closestValue(pos)));
+     302             : }
+     303             : 
+     304           0 : double JF12Field::getTurbulentStrength(const Vector3d& pos) const {
+     305           0 :         if (pos.getR() > 20 * kpc)
+     306             :                 return 0;
+     307             : 
+     308           0 :         double r = sqrt(pos.x * pos.x + pos.y * pos.y); // in-plane radius
+     309           0 :         double phi = pos.getPhi(); // azimuth
+     310             : 
+     311             :         // disk
+     312             :         double bDisk = 0;
+     313           0 :         if (r < 5 * kpc) {
+     314           0 :                 bDisk = bDiskTurb5;
+     315             :         } else {
+     316             :                 // spiral region
+     317           0 :                 double r_negx = r * exp(-(phi - M_PI) / tan90MinusPitch);
+     318           0 :                 if (r_negx > rArms[7])
+     319           0 :                         r_negx = r * exp(-(phi + M_PI) / tan90MinusPitch);
+     320           0 :                 if (r_negx > rArms[7])
+     321           0 :                         r_negx = r * exp(-(phi + 3 * M_PI) / tan90MinusPitch);
+     322             : 
+     323           0 :                 for (int i = 7; i >= 0; i--)
+     324           0 :                         if (r_negx < rArms[i])
+     325           0 :                                 bDisk = bDiskTurb[i];
+     326             : 
+     327           0 :                 bDisk *= (5 * kpc) / r;
+     328             :         }
+     329           0 :         bDisk *= exp(-0.5 * pow(pos.z / zDiskTurb, 2));
+     330             : 
+     331             :         // halo
+     332           0 :         double bHalo = bHaloTurb * exp(-r / rHaloTurb)
+     333           0 :                         * exp(-0.5 * pow(pos.z / zHaloTurb, 2));
+     334             : 
+     335             :         // modulate turbulent field
+     336           0 :         return sqrt(pow(bDisk, 2) + pow(bHalo, 2));
+     337             : }
+     338             : 
+     339           0 : Vector3d JF12Field::getTurbulentField(const Vector3d& pos) const {
+     340           0 :         return (turbulentGrid->interpolate(pos) * getTurbulentStrength(pos));
+     341             : }
+     342             : 
+     343           0 : Vector3d JF12Field::getField(const Vector3d& pos) const {
+     344             :         Vector3d b(0.);
+     345           0 :         if (useTurbulentField)
+     346           0 :                 b += getTurbulentField(pos);
+     347           0 :         if (useStriatedField)
+     348           0 :                 b += getStriatedField(pos);
+     349           0 :         else if (useRegularField)
+     350           0 :                 b += getRegularField(pos);
+     351           0 :         return b;
+     352             : }
+     353             : 
+     354             : 
+     355             : 
+     356           0 : PlanckJF12bField::PlanckJF12bField() : JF12Field::JF12Field(){
+     357             :         // regular field parameters
+     358           0 :         bDisk[5] = -3.5 * muG;
+     359           0 :         bX = 1.8 * muG;
+     360             : 
+     361             :         // turbulent field parameters;
+     362           0 :         bDiskTurb[0] = 3.12 * muG;
+     363           0 :         bDiskTurb[1] = 6.24 * muG;
+     364           0 :         bDiskTurb[2] = 3.12 * muG;
+     365           0 :         bDiskTurb[3] = 6.24 * muG;
+     366           0 :         bDiskTurb[4] = 3.12 * muG;
+     367           0 :         bDiskTurb[5] = 6.24 * muG;
+     368           0 :         bDiskTurb[6] = 3.12 * muG;
+     369           0 :         bDiskTurb[7] = 6.24 * muG;
+     370             : 
+     371           0 :         bDiskTurb5 = 3.90 * muG;
+     372             : 
+     373           0 :         bHaloTurb = 7.332 * muG;
+     374           0 : }
+     375             : 
+     376             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html new file mode 100644 index 000000000..5057574e8 --- /dev/null +++ b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/JF12FieldSolenoidal.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - JF12FieldSolenoidal.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01420.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19JF12FieldSolenoidal15setXScaleHeightEd0
_ZN7crpropa19JF12FieldSolenoidal19setUseStriatedFieldEb0
_ZN7crpropa19JF12FieldSolenoidal20setUseTurbulentFieldEb0
_ZN7crpropa19JF12FieldSolenoidal22setDiskTransitionWidthEd0
_ZN7crpropa19JF12FieldSolenoidal25deactivateOuterTransitionEv0
_ZN7crpropa19JF12FieldSolenoidalC2Edd0
_ZNK7crpropa19JF12FieldSolenoidal12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa19JF12FieldSolenoidal15getHPhiIntegralERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal15getXScaleHeightEv0
_ZNK7crpropa19JF12FieldSolenoidal22getDiskTransitionWidthEv0
_ZNK7crpropa19JF12FieldSolenoidal27getDiskTransitionPolynomialERKd0
_ZNK7crpropa19JF12FieldSolenoidal30getSpiralFieldStrengthConstantERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal37getDiskTransitionPolynomialDerivativeERKd0
_ZNK7crpropa19JF12FieldSolenoidal9getXFieldERKdS2_S2_S2_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html new file mode 100644 index 000000000..539e7551e --- /dev/null +++ b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/JF12FieldSolenoidal.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - JF12FieldSolenoidal.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01420.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19JF12FieldSolenoidal15setXScaleHeightEd0
_ZN7crpropa19JF12FieldSolenoidal19setUseStriatedFieldEb0
_ZN7crpropa19JF12FieldSolenoidal20setUseTurbulentFieldEb0
_ZN7crpropa19JF12FieldSolenoidal22setDiskTransitionWidthEd0
_ZN7crpropa19JF12FieldSolenoidal25deactivateOuterTransitionEv0
_ZN7crpropa19JF12FieldSolenoidalC2Edd0
_ZNK7crpropa19JF12FieldSolenoidal12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa19JF12FieldSolenoidal15getHPhiIntegralERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal15getXScaleHeightEv0
_ZNK7crpropa19JF12FieldSolenoidal22getDiskTransitionWidthEv0
_ZNK7crpropa19JF12FieldSolenoidal27getDiskTransitionPolynomialERKd0
_ZNK7crpropa19JF12FieldSolenoidal30getSpiralFieldStrengthConstantERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal37getDiskTransitionPolynomialDerivativeERKd0
_ZNK7crpropa19JF12FieldSolenoidal9getXFieldERKdS2_S2_S2_0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html new file mode 100644 index 000000000..ae5d894a4 --- /dev/null +++ b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html @@ -0,0 +1,378 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/JF12FieldSolenoidal.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - JF12FieldSolenoidal.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01420.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/JF12FieldSolenoidal.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/GridTools.h"
+       4             : #include "crpropa/Random.h"
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           0 : JF12FieldSolenoidal::JF12FieldSolenoidal(double delta, double zs) {
+       9           0 :         zS = zs; // set scale heigth for the parabolic X field lines
+      10           0 :         r1 = 5 * kpc; // inner boundary of the disk field
+      11           0 :         r2 = 20 * kpc; // outer boudary of the disk field
+      12           0 :         r1s = r1 + delta; // the magnetic flux of the spirals is redirected for r in [r1,r1s]
+      13           0 :         r2s = r2 - delta; // same here at outer boundary between r2s and r2
+      14           0 :         phi0 = 0.; // somewhat arbitrary choice, has to be chosen in [-pi,pi]
+      15             : 
+      16           0 :         for (int i = 1;i < 9; i++){
+      17             :                 // fill the array with angles in [-pi,pi] where the 8 spiral arms intersect the r1 - ring
+      18             :                 // indexing starts at 1 to match the indexing in the papers on the JF12 field!
+      19           0 :                 phi0Arms[i] = M_PI - cotPitch * log(rArms[i-1] / r1);
+      20             :         }
+      21             : 
+      22             :         // cyclic closure of the array, with next values periodically continued
+      23             :         // outside [-pi,pi] to simplify looping and searching for correct spiral arms
+      24           0 :         phi0Arms[0] = phi0Arms[8] + 2 * M_PI;
+      25           0 :         phi0Arms[9] = phi0Arms[1] - 2 * M_PI;
+      26           0 :         phi0Arms[10] = phi0Arms[2] - 2 *M_PI;
+      27             : 
+      28             :         // determine the position of phi0 in the array, i.e. find the correct spiral arm.
+      29             :         int idx0 = 1; // corresponding index in phi0Arms such that phi0Arms[idx0] < phi0 < phi0Arms[idx0-1]
+      30           0 :         while (phi0 < phi0Arms[idx0]){
+      31           0 :                 idx0 += 1; // search clockwise, starting with the check if phi0Arms[1] < phi0 < phi0Arms[0]
+      32             :         }
+      33             : 
+      34             :         // fill the bDisk array with spiral field strengths at r = r1.
+      35             :         // note the indexing starting with 1 here to match the indexing in the JF12 papers!
+      36             :         // for a position (r1,phi), phi in [-pi,pi], the correct field strength is given by
+      37             :         // bDisk[i] if phi0Arms[i] < phi0 < phi0Arms[i-1].
+      38           0 :         bDisk[1] = 0.1 * muG;
+      39           0 :         bDisk[2] = 3.0 * muG;
+      40           0 :         bDisk[3] = -0.9 * muG;
+      41           0 :         bDisk[4] = -0.8 * muG;
+      42           0 :         bDisk[5] = -2.0 * muG;
+      43           0 :         bDisk[6] = -4.2 * muG;
+      44           0 :         bDisk[7] = 0.0 * muG;
+      45             : 
+      46             :         // re-compute b_8 for actual (net flux = 0)-correction of the spiral field with minimal round-off errors
+      47             :         double flux1to7 = 0.;
+      48           0 :         for (int i = 1; i < 8; i++){
+      49           0 :                 flux1to7 += (phi0Arms[i-1] - phi0Arms[i]) * bDisk[i];
+      50             :         }
+      51           0 :         bDisk[8] = -flux1to7 / (phi0Arms[7] - phi0Arms[8]);
+      52             : 
+      53           0 :         bDisk[0] = bDisk[8]; // again close the array periodically
+      54           0 :         bDisk[9] = bDisk[1];
+      55           0 :         bDisk[10] = bDisk[2];
+      56             : 
+      57             :         // set coefficients for the evaluation of the phi-integral over the piecewise constant field strengths at r=r1
+      58             :         // such that it may be evaluated as H(phi) = phiCoeff[j] + bDisk[j] * phi later on
+      59             :         // start integration at phi0Arms[0] first, shift to lower integration boundary phi0 later
+      60           0 :         phiCoeff[0] = 0;
+      61           0 :         for (int i = 1; i < 10; i++){
+      62           0 :                 phiCoeff[i] = phiCoeff[i-1] + (bDisk[i-1] - bDisk[i]) * phi0Arms[i-1];
+      63             :         }
+      64             : 
+      65             :         // correct for H(phi0) = 0
+      66           0 :         corr = phiCoeff[idx0] + bDisk[idx0] * phi0;
+      67           0 :         for (int i = 1; i < 10; i++){
+      68           0 :                 phiCoeff[i] = phiCoeff[i] - corr;
+      69             :         }
+      70           0 : }
+      71             : 
+      72           0 : void JF12FieldSolenoidal::setDiskTransitionWidth(double delta) {
+      73           0 :         r1s = r1 + delta;
+      74           0 :         r2s = r2 - delta;
+      75           0 : }
+      76             : 
+      77           0 : void JF12FieldSolenoidal::setXScaleHeight(double zs) {
+      78           0 :         zS = zs;
+      79           0 : }
+      80             : 
+      81           0 : double JF12FieldSolenoidal::getDiskTransitionWidth() const {
+      82           0 :         return (r1s - r1);
+      83             : }
+      84             : 
+      85           0 : double JF12FieldSolenoidal::getXScaleHeight() const {
+      86           0 :         return zS;
+      87             : }
+      88             : 
+      89           0 : void JF12FieldSolenoidal::deactivateOuterTransition() {
+      90           0 :         r2s = r2;
+      91           0 : }
+      92             : 
+      93           0 : void JF12FieldSolenoidal::setUseStriatedField(bool use) {
+      94           0 :         if ((use) and (striatedGrid)) {
+      95           0 :                 KISS_LOG_WARNING << "JF12FieldSolenoidal: No striated field set: ignored.";
+      96           0 :                 return;
+      97             :         }
+      98           0 :         useStriatedField = use;
+      99             : }
+     100             : 
+     101           0 : void JF12FieldSolenoidal::setUseTurbulentField(bool use) {
+     102           0 :         if ((use) and (turbulentGrid)) {
+     103           0 :                 KISS_LOG_WARNING << "JF12FieldSolenoidal: No turbulent field set: ignored.";
+     104           0 :                 return;
+     105             :         }
+     106           0 :         useTurbulentField = use;
+     107             : }
+     108             : 
+     109           0 : Vector3d JF12FieldSolenoidal::getDiskField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
+     110             :         Vector3d b(0.);
+     111             : 
+     112           0 :         if (useDiskField){
+     113           0 :                 double lfDisk = logisticFunction(z, hDisk, wDisk); // for vertical scaling as in initial JF12
+     114             : 
+     115           0 :                 double hint = getHPhiIntegral(r, phi); // phi integral to restore solenoidality in transition region, only enters if r is in [r1,r1s] or [r2s,r2]
+     116           0 :                 double mag1 = getSpiralFieldStrengthConstant(r, phi); // returns bDisk[j] for the current spiral arm
+     117             : 
+     118           0 :                 if ((r1 < r) && (r < r2)) {
+     119           0 :                         double pdelta = getDiskTransitionPolynomial(r);
+     120           0 :                         double qdelta = getDiskTransitionPolynomialDerivative(r);
+     121           0 :                         double br = pdelta * mag1 * sinPitch;
+     122           0 :                         double bphi = pdelta * mag1 * cosPitch - qdelta * hint * sinPitch;
+     123             : 
+     124           0 :                         b.x += br * cosPhi - bphi * sinPhi;
+     125           0 :                         b.y += br * sinPhi + bphi * cosPhi;
+     126             : 
+     127           0 :                         b *= (1 - lfDisk);
+     128             :                 }
+     129             :         }
+     130           0 :         return b;
+     131             : }
+     132             : 
+     133           0 : Vector3d JF12FieldSolenoidal::getXField(const double& r, const double& z, const double& sinPhi, const double& cosPhi) const {
+     134             :         Vector3d b(0.);
+     135             : 
+     136           0 :         if (useXField){
+     137             :                 double bMagX;
+     138             :                 double sinThetaX, cosThetaX;
+     139             :                 double rp; // radius where current intial field line passes z = 0
+     140           0 :                 double rc = rXc + fabs(z) / tanThetaX0;
+     141           0 :                 double r0c = rXc + zS / tanThetaX0; // radius where field line through rXc passes z = zS
+     142             :                 double f, r0, br0, bz0;
+     143             :                 bool inner = true; // distinguish between inner and outer region
+     144             : 
+     145             :                 // return intial field if z>=zS
+     146           0 :                 if (fabs(z) > zS){
+     147           0 :                         if ((r == 0.)){
+     148           0 :                                 b.z = bX / ((1. + fabs(z) * cotThetaX0 / rXc) * (1. + fabs(z) * cotThetaX0 / rXc));
+     149           0 :                                 return b;
+     150             :                         }
+     151             : 
+     152           0 :                         if (r < rc) {
+     153             :                         // inner varying elevation region
+     154           0 :                                 rp = r * rXc / rc;
+     155           0 :                                 bMagX = bX * exp(-1 * rp / rX) * (rXc / rc) * (rXc / rc);
+     156             : 
+     157           0 :                                 double thetaX = atan(fabs(z) / (r - rp));
+     158             : 
+     159           0 :                                 if (z == 0)
+     160             :                                         thetaX = M_PI / 2.;
+     161             : 
+     162           0 :                                 sinThetaX = sin(thetaX);
+     163           0 :                                 cosThetaX = cos(thetaX);
+     164             :                         }
+     165             :                         else {
+     166             :                         // outer constant elevation region
+     167           0 :                                 rp = r - fabs(z) / tanThetaX0;
+     168           0 :                                 bMagX = bX * exp(-rp / rX) * (rp / r);
+     169             : 
+     170           0 :                                 sinThetaX = sinThetaX0;
+     171           0 :                                 cosThetaX = cosThetaX0;
+     172             :                         }
+     173           0 :                         double zsign = z < 0 ? -1 : 1;
+     174           0 :                         b.x += zsign * bMagX * cosThetaX * cosPhi;
+     175           0 :                         b.y += zsign * bMagX * cosThetaX * sinPhi;
+     176           0 :                         b.z += bMagX * sinThetaX;
+     177             :                 }
+     178             :                 // parabolic field lines for z<zS
+     179             :                 else {
+     180             :                                 // determine r at which parabolic field line through (r,z) passes z = zS
+     181           0 :                                 r0 = r * 1. / (1.- 1./ (2. * (zS + rXc * tanThetaX0)) * (zS - z * z / zS));
+     182             : 
+     183             :                                 // determine correct region (inner/outer)
+     184             :                                 // and compute factor F for solenoidality
+     185           0 :                                 if (r0 >= r0c){
+     186           0 :                                         r0 = r + 1. / (2. * tanThetaX0) * (zS - z * z / zS);
+     187           0 :                                         f = 1. + 1/ (2 * r * tanThetaX0/ zS) * (1. - (z / zS) * (z / zS));
+     188             :                                 }
+     189             :                                 else
+     190             :                                 {
+     191           0 :                                          f = 1. / ((1. - 1./( 2. + 2. * (rXc * tanThetaX0/ zS)) * (1. - (z / zS) * (z / zS))) * (1. - 1./( 2. + 2. * (rXc * tanThetaX0/ zS)) * (1. - (z / zS) * (z / zS))));
+     192             :                                 }
+     193             : 
+     194             :                                 // field strength at that position
+     195           0 :                                 if (r0 < r0c){
+     196           0 :                                          rp = r0 * rXc / r0c;
+     197           0 :                                          double thetaX = atan(zS / (r0 - rp));
+     198             : 
+     199             :                                          // field strength at (r0,zS) for inner region
+     200           0 :                                          br0 = bX * exp(- rp / rX) * (rXc/ r0c) * (rXc/ r0c) * cos(thetaX);
+     201           0 :                                          bz0 = bX * exp(- rp / rX) * (rXc/ r0c) * (rXc/ r0c) * sin(thetaX);
+     202             :                                  }
+     203             :                                  else {
+     204             :                                          // field strength at (r0,zS) for outer region
+     205           0 :                                          rp = r0 - zS / tanThetaX0;
+     206           0 :                                          br0 =  bX * exp(- rp / rX) * (rp/r0) * cosThetaX0;
+     207           0 :                                          bz0 =  bX * exp(- rp / rX) * (rp/r0) * sinThetaX0;
+     208             :                                  }
+     209             : 
+     210           0 :                                  double br = z / zS * f * br0;
+     211           0 :                                  double bz = bz0 * f;
+     212             : 
+     213           0 :                                  b.x += br * cosPhi;
+     214           0 :                                  b.y += br * sinPhi;
+     215           0 :                                  b.z += bz;
+     216             :                 }
+     217             :         }
+     218             :         return b;
+     219             : }
+     220             : 
+     221           0 : double JF12FieldSolenoidal::getDiskTransitionPolynomial(const double& r) const {
+     222             :         // 0 disk field outside
+     223           0 :         if ((r < r1) || (r > r2)) {
+     224             :                 return 0.;
+     225             :         }
+     226             :         // unchanged field
+     227           0 :         if ((r > r1s) && (r < r2s)) {
+     228           0 :                 return r1/r;
+     229             :         }
+     230             :         // transitions region parameters
+     231             :         double r_a = r1;
+     232             :         double r_b = r1s;
+     233             : 
+     234           0 :         if (r >= r2s) {
+     235             :                 r_a = r2;
+     236             :                 r_b = r2s;
+     237             :         }
+     238             :         // differentiable transition at r_s, continous at r_a
+     239           0 :         double fakt = (r_a / r_b - 2.) / ((r_a - r_b) *  (r_a - r_b));
+     240           0 :         return (r1/r_b) * (2. - r / r_b + fakt * (r-r_b) * (r-r_b));
+     241             : }
+     242             : 
+     243           0 : double JF12FieldSolenoidal::getDiskTransitionPolynomialDerivative(const double& r) const {
+     244             :         // 0 disk field outside
+     245           0 :         if ((r < r1) || (r > r2)) {
+     246             :                 return 0.;
+     247             :         }
+     248             :         // unchanged field
+     249           0 :         if ((r > r1s) && (r < r2s)) {
+     250             :                 return 0.;
+     251             :         }
+     252             :         // transitions region parameters
+     253             :         double r_a = r1;
+     254             :         double r_b = r1s;
+     255             : 
+     256           0 :         if (r >= r2s) {
+     257             :                 r_a = r2;
+     258             :                 r_b = r2s;
+     259             :         }
+     260             :         // differentiable transition polynomial at r_s, continous at r_a
+     261           0 :         double fakt = (r_a / r_b - 2.) / ((r_a - r_b) * (r_a - r_b));
+     262           0 :         return (r1/r_b) * (2. - 2. * r/r_b + fakt * (3. * r * r - 4. * r * r_b + r_b * r_b));
+     263             : }
+     264             : 
+     265           0 : double JF12FieldSolenoidal::getHPhiIntegral(const double& r, const double& phi) const {
+     266             :         // Evaluates the H(phi1) integral for solenoidality for the position (r,phi) which is mapped back to (r1=5kpc,phi1)
+     267             :         // along the spiral field line.
+     268             :         double H_ret = 0.;
+     269             : 
+     270           0 :         if ((r1 < r) && (r < r2)){
+     271             :                 // find index of the correct spiral arm for (r1,phi1) just like in getSpiralFieldStrengthConstant
+     272             :                 int idx = 1;
+     273           0 :                 double phi1 = phi - log(r/r1) * cotPitch;
+     274           0 :                 phi1 = atan2(sin(phi1), cos(phi1));
+     275           0 :                 while (phi1 < phi0Arms[idx]){
+     276           0 :                         idx += 1;
+     277             :                 }
+     278           0 :                 H_ret = phi1 * bDisk[idx] + phiCoeff[idx];
+     279             :         }
+     280           0 :         return H_ret;
+     281             : }
+     282             : 
+     283           0 : double JF12FieldSolenoidal::getSpiralFieldStrengthConstant(const double& r, const double& phi) const {
+     284             :         // For a given position (r, phi) in polar coordinates, this method returns the field strength
+     285             :         // of the spiral field at r1 = 5 kpc for the magnetic spiral arm where (r, phi) is located.
+     286             :         // The method first computes the angle phi1 at which the spiral field line passing through (r, phi) intersects
+     287             :         // the circle with radius r1 = 5 kpc. Afterwards, the correct spiral arm is found by searching the index idx
+     288             :         // such that phi0Arms[idx] < phi1 < phi0Arms[idx-1]. The correct field strength of the respective spiral arm
+     289             :         // where (r, phi) is located is then given as bDisk[idx].
+     290             :         double b_ret = 0.;
+     291             :         int idx = 1;
+     292           0 :         if ((r1 < r) && (r < r2)){
+     293           0 :                 double phi1 = phi - log(r/r1) * cotPitch; // map the position (r, phi) to (5 kpc, phi1) along the logarithmic spiral field line
+     294           0 :                 phi1 = atan2(sin(phi1), cos(phi1)); // map this angle to [-pi,+pi]
+     295           0 :                 while (phi1 < phi0Arms[idx]){
+     296           0 :                         idx += 1; // run clockwise through the spiral arms; the cyclic closure of phi0Arms[9] = phi0Arms[1] - 2 pi is needed if -pi <= phi1 <= phi0Arms[8].
+     297             :                 }
+     298           0 :                 b_ret = bDisk[idx];
+     299             :         }
+     300           0 :         return b_ret;
+     301             : }
+     302             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html new file mode 100644 index 000000000..b8384f639 --- /dev/null +++ b/doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/MagneticField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - MagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486672.7 %
Date:2024-04-08 14:58:22Functions:91656.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21PeriodicMagneticField10getExtendsEv0
_ZN7crpropa21PeriodicMagneticField10setExtendsERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticField12isReflectiveEv0
_ZN7crpropa21PeriodicMagneticField13setReflectiveEb0
_ZN7crpropa21PeriodicMagneticField9getOriginEv0
_ZN7crpropa21PeriodicMagneticField9setOriginERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEES7_b1
_ZN7crpropa22MagneticFieldEvolutionC2ENS_7ref_ptrINS_13MagneticFieldEEEd1
_ZN7crpropa24RenormalizeMagneticField8getFieldERKNS_7Vector3IdEE1
_ZN7crpropa24RenormalizeMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17MagneticFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa19MagneticDipoleField8getFieldERKNS_7Vector3IdEE2
_ZNK7crpropa22MagneticFieldEvolution8getFieldERKNS_7Vector3IdEEd2
_ZN7crpropa17MagneticFieldList8addFieldENS_7ref_ptrINS_13MagneticFieldEEE3
_ZNK7crpropa21PeriodicMagneticField8getFieldERKNS_7Vector3IdEE3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/MagneticField.cpp.func.html b/doc/coverageReport/src/magneticField/MagneticField.cpp.func.html new file mode 100644 index 000000000..2a5f1bfd3 --- /dev/null +++ b/doc/coverageReport/src/magneticField/MagneticField.cpp.func.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/MagneticField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - MagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486672.7 %
Date:2024-04-08 14:58:22Functions:91656.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17MagneticFieldList8addFieldENS_7ref_ptrINS_13MagneticFieldEEE3
_ZN7crpropa21PeriodicMagneticField10getExtendsEv0
_ZN7crpropa21PeriodicMagneticField10setExtendsERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticField12isReflectiveEv0
_ZN7crpropa21PeriodicMagneticField13setReflectiveEb0
_ZN7crpropa21PeriodicMagneticField9getOriginEv0
_ZN7crpropa21PeriodicMagneticField9setOriginERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEES7_b1
_ZN7crpropa22MagneticFieldEvolutionC2ENS_7ref_ptrINS_13MagneticFieldEEEd1
_ZN7crpropa24RenormalizeMagneticField8getFieldERKNS_7Vector3IdEE1
_ZN7crpropa24RenormalizeMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17MagneticFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa19MagneticDipoleField8getFieldERKNS_7Vector3IdEE2
_ZNK7crpropa21PeriodicMagneticField8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa22MagneticFieldEvolution8getFieldERKNS_7Vector3IdEEd2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html b/doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html new file mode 100644 index 000000000..086759e57 --- /dev/null +++ b/doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html @@ -0,0 +1,188 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/MagneticField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - MagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486672.7 %
Date:2024-04-08 14:58:22Functions:91656.2 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/MagneticField.h"
+       2             : 
+       3             : namespace crpropa {
+       4             : 
+       5           0 : PeriodicMagneticField::PeriodicMagneticField(ref_ptr<MagneticField> field,
+       6           0 :                 const Vector3d &extends) :
+       7           0 :                 field(field), extends(extends), origin(0, 0, 0), reflective(false) {
+       8             : 
+       9           0 : }
+      10             : 
+      11           1 : PeriodicMagneticField::PeriodicMagneticField(ref_ptr<MagneticField> field,
+      12           1 :                 const Vector3d &extends, const Vector3d &origin, bool reflective) :
+      13           1 :                 field(field), extends(extends), origin(origin), reflective(reflective) {
+      14             : 
+      15           1 : }
+      16             : 
+      17           0 : Vector3d &PeriodicMagneticField::getOrigin() {
+      18           0 :         return origin;
+      19             : }
+      20             : 
+      21           0 : void PeriodicMagneticField::setOrigin(const Vector3d &origin) {
+      22             :         this->origin = origin;
+      23           0 : }
+      24             : 
+      25           0 : Vector3d &PeriodicMagneticField::getExtends() {
+      26           0 :         return extends;
+      27             : }
+      28             : 
+      29           0 : void PeriodicMagneticField::setExtends(const Vector3d &origin) {
+      30             :         this->extends = extends;
+      31           0 : }
+      32             : 
+      33           0 : bool PeriodicMagneticField::isReflective() {
+      34           0 :         return reflective;
+      35             : }
+      36             : 
+      37           0 : void PeriodicMagneticField::setReflective(bool reflective) {
+      38           0 :         this->reflective = reflective;
+      39           0 : }
+      40             : 
+      41           3 : Vector3d PeriodicMagneticField::getField(const Vector3d &position) const {
+      42           3 :         Vector3d n = ((position - origin) / extends).floor();
+      43             :         Vector3d p = position - origin - n * extends;
+      44             : 
+      45           3 :         if (reflective) {
+      46           3 :                 long mx = (long) ::fabs(n.x) % 2;
+      47           3 :                 if (mx == 1)
+      48           2 :                         p.x = extends.x - p.x;
+      49           3 :                 long my = (long) ::fabs(n.y) % 2;
+      50           3 :                 if (my == 1)
+      51           0 :                         p.y = extends.y - p.y;
+      52           3 :                 long mz = (long) ::fabs(n.z) % 2;
+      53           3 :                 if (mz == 1)
+      54           2 :                         p.z = extends.z - p.z;
+      55             :         }
+      56             : 
+      57           3 :         return field->getField(p);
+      58             : }
+      59             : 
+      60           3 : void MagneticFieldList::addField(ref_ptr<MagneticField> field) {
+      61           3 :         fields.push_back(field);
+      62           3 : }
+      63             : 
+      64           1 : Vector3d MagneticFieldList::getField(const Vector3d &position) const {
+      65             :         Vector3d b;
+      66           4 :         for (int i = 0; i < fields.size(); i++)
+      67           3 :                 b += fields[i]->getField(position);
+      68           1 :         return b;
+      69             : }
+      70             : 
+      71           1 : MagneticFieldEvolution::MagneticFieldEvolution(ref_ptr<MagneticField> field,
+      72           1 :         double m) :
+      73           1 :         field(field), m(m) {
+      74           1 : }
+      75             : 
+      76           2 : Vector3d MagneticFieldEvolution::getField(const Vector3d &position,
+      77             :         double z) const {
+      78           2 :         return field->getField(position) * pow(1+z, m);
+      79             : }
+      80             : 
+      81           2 : Vector3d MagneticDipoleField::getField(const Vector3d &position) const {
+      82             :                 Vector3d r = (position - origin);
+      83           2 :                 Vector3d unit_r = r.getUnitVector();
+      84             :                 
+      85           2 :                 if (r.getR() == 0) { // singularity
+      86             :                         return moment * 2 * mu0 / 3;
+      87             :                 }
+      88           2 :                 return (unit_r * (unit_r.dot(moment)) * 3 - moment) / pow(r.getR() / radius, 3) * mu0 / (4*M_PI);
+      89             : }
+      90             : 
+      91             : #ifdef CRPROPA_HAVE_MUPARSER
+      92           1 : RenormalizeMagneticField::RenormalizeMagneticField(ref_ptr<MagneticField> field,
+      93           1 :                 std::string expression) :
+      94           2 :                 field(field), expression(expression) {
+      95             : 
+      96           1 :         p =  new mu::Parser();
+      97           1 :         p->DefineVar("B", &Bmag);
+      98           1 :         p->DefineConst("tesla", tesla);
+      99           1 :         p->DefineConst("gauss", gauss);
+     100           1 :         p->DefineConst("muG", muG);
+     101           1 :         p->DefineConst("nG", nG);
+     102           1 :         p->SetExpr(expression);
+     103           1 : }
+     104             : 
+     105           1 : Vector3d RenormalizeMagneticField::getField(const Vector3d &position) {
+     106           1 :         Vector3d B = field->getField(position);
+     107           1 :         Bmag = B.getR();
+     108           1 :         return B * p->Eval();
+     109             : }
+     110             : #endif
+     111             : 
+     112             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html new file mode 100644 index 000000000..6c98862d1 --- /dev/null +++ b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/MagneticFieldGrid.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - MagneticFieldGrid.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0310.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17MagneticFieldGrid7getGridEv0
_ZN7crpropa17MagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17MagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid13setReflectiveEbb0
_ZN7crpropa26ModulatedMagneticFieldGrid17getModulationGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid17setModulationGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid7getGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS1_INS2_IfEEEE0
_ZNK7crpropa17MagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa26ModulatedMagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html new file mode 100644 index 000000000..10a3651e7 --- /dev/null +++ b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/MagneticFieldGrid.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - MagneticFieldGrid.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0310.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17MagneticFieldGrid7getGridEv0
_ZN7crpropa17MagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17MagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid13setReflectiveEbb0
_ZN7crpropa26ModulatedMagneticFieldGrid17getModulationGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid17setModulationGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid7getGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS1_INS2_IfEEEE0
_ZNK7crpropa17MagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa26ModulatedMagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html new file mode 100644 index 000000000..9a3f969fb --- /dev/null +++ b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html @@ -0,0 +1,133 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/MagneticFieldGrid.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - MagneticFieldGrid.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0310.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/MagneticFieldGrid.h"
+       2             : 
+       3             : namespace crpropa {
+       4             : 
+       5           0 : MagneticFieldGrid::MagneticFieldGrid(ref_ptr<Grid3f> grid) {
+       6           0 :         setGrid(grid);
+       7           0 : }
+       8             : 
+       9           0 : void MagneticFieldGrid::setGrid(ref_ptr<Grid3f> grid) {
+      10           0 :         this->grid = grid;
+      11           0 : }
+      12             : 
+      13           0 : ref_ptr<Grid3f> MagneticFieldGrid::getGrid() {
+      14           0 :         return grid;
+      15             : }
+      16             : 
+      17           0 : Vector3d MagneticFieldGrid::getField(const Vector3d &pos) const {
+      18           0 :         return grid->interpolate(pos);
+      19             : }
+      20             : 
+      21           0 : ModulatedMagneticFieldGrid::ModulatedMagneticFieldGrid(ref_ptr<Grid3f> grid,
+      22           0 :                 ref_ptr<Grid1f> modGrid) {
+      23             :         grid->setReflective(false);
+      24             :         modGrid->setReflective(true);
+      25           0 :         setGrid(grid);
+      26           0 :         setModulationGrid(modGrid);
+      27           0 : }
+      28             : 
+      29           0 : void ModulatedMagneticFieldGrid::setGrid(ref_ptr<Grid3f> g) {
+      30           0 :         grid = g;
+      31           0 : }
+      32             : 
+      33           0 : ref_ptr<Grid3f> ModulatedMagneticFieldGrid::getGrid() {
+      34           0 :         return grid;
+      35             : }
+      36             : 
+      37           0 : void ModulatedMagneticFieldGrid::setModulationGrid(ref_ptr<Grid1f> g) {
+      38           0 :         modGrid = g;
+      39           0 : }
+      40             : 
+      41           0 : ref_ptr<Grid1f> ModulatedMagneticFieldGrid::getModulationGrid() {
+      42           0 :         return modGrid;
+      43             : }
+      44             : 
+      45           0 : void ModulatedMagneticFieldGrid::setReflective(bool gridReflective,
+      46             :                 bool modGridReflective) {
+      47             :         grid->setReflective(gridReflective);
+      48             :         modGrid->setReflective(modGridReflective);
+      49           0 : }
+      50             : 
+      51           0 : Vector3d ModulatedMagneticFieldGrid::getField(const Vector3d &pos) const {
+      52           0 :         float m = modGrid->interpolate(pos);
+      53           0 :         Vector3d b = grid->interpolate(pos);
+      54           0 :         return b * m;
+      55             : }
+      56             : 
+      57             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html new file mode 100644 index 000000000..1594ee831 --- /dev/null +++ b/doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html @@ -0,0 +1,108 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/PT11Field.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - PT11Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9PT11Field10isUsingASSEv0
_ZN7crpropa9PT11Field10isUsingBSSEv0
_ZN7crpropa9PT11Field10setUseHaloEb0
_ZN7crpropa9PT11Field11isUsingHaloEv0
_ZN7crpropa9PT11Field9SetParamsEv0
_ZN7crpropa9PT11Field9setUseASSEb0
_ZN7crpropa9PT11Field9setUseBSSEb0
_ZN7crpropa9PT11FieldC2Ev0
_ZNK7crpropa9PT11Field8getFieldERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/PT11Field.cpp.func.html b/doc/coverageReport/src/magneticField/PT11Field.cpp.func.html new file mode 100644 index 000000000..62ece690d --- /dev/null +++ b/doc/coverageReport/src/magneticField/PT11Field.cpp.func.html @@ -0,0 +1,108 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/PT11Field.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - PT11Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9PT11Field10isUsingASSEv0
_ZN7crpropa9PT11Field10isUsingBSSEv0
_ZN7crpropa9PT11Field10setUseHaloEb0
_ZN7crpropa9PT11Field11isUsingHaloEv0
_ZN7crpropa9PT11Field9SetParamsEv0
_ZN7crpropa9PT11Field9setUseASSEb0
_ZN7crpropa9PT11Field9setUseBSSEb0
_ZN7crpropa9PT11FieldC2Ev0
_ZNK7crpropa9PT11Field8getFieldERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html b/doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html new file mode 100644 index 000000000..36fdae7a3 --- /dev/null +++ b/doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html @@ -0,0 +1,206 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/PT11Field.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - PT11Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/PT11Field.h"
+       2             : #include "crpropa/Units.h"
+       3             : 
+       4             : #include <algorithm>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           0 : PT11Field::PT11Field() : useASS(true), useBSS(false), useHalo(true) {
+       9             :         // disk parameters
+      10           0 :         d = - 0.6 * kpc;
+      11           0 :         R_sun = 8.5 * kpc;
+      12           0 :         R_c = 5.0 * kpc;
+      13           0 :         z0_D = 1.0 * kpc;
+      14           0 :         B0_D = 2.0 * muG;
+      15             : 
+      16             :         // halo parameters
+      17           0 :         z0_H = 1.3 * kpc;
+      18           0 :         R0_H = 8.0 * kpc;
+      19           0 :         B0_Hn = 4.0 * muG;
+      20           0 :         B0_Hs = 4.0 * muG;
+      21           0 :         z11_H = 0.25 * kpc;
+      22           0 :         z12_H = 0.4 * kpc;
+      23             : 
+      24             :         // set ASS specific parameters
+      25           0 :         setUseASS(true);
+      26           0 : }
+      27             : 
+      28           0 : void PT11Field::SetParams() {
+      29           0 :         cos_pitch = cos(pitch);
+      30           0 :         sin_pitch = sin(pitch);
+      31           0 :         PHI = cos_pitch / sin_pitch * log1p(d / R_sun) - M_PI / 2;
+      32           0 :         cos_PHI = cos(PHI);
+      33           0 : }
+      34             : 
+      35           0 : void PT11Field::setUseASS(bool use) {
+      36           0 :         useASS = use;
+      37           0 :         if (not(use))
+      38             :                 return;
+      39             : 
+      40           0 :         if (useBSS) {
+      41             :                 std::cout << "PT11Field: Disk field changed to ASS" << std::endl;
+      42           0 :                 useBSS = false;
+      43             :         }
+      44             : 
+      45           0 :         pitch = -5.0 * M_PI / 180;
+      46           0 :         B0_Hs = 2.0 * muG;
+      47           0 :         SetParams();
+      48             : }
+      49             : 
+      50           0 : void PT11Field::setUseBSS(bool use) {
+      51           0 :         useBSS = use;
+      52           0 :         if (not(use))
+      53             :                 return;
+      54             : 
+      55           0 :         if (useASS) {
+      56             :                 std::cout << "PT11Field: Disk field changed to BSS" << std::endl;
+      57           0 :                 useASS = false;
+      58             :         }
+      59             : 
+      60           0 :         pitch = -6.0 * M_PI / 180;
+      61           0 :         B0_Hs = 4.0 * muG;
+      62           0 :         SetParams();
+      63             : }
+      64             : 
+      65           0 : void PT11Field::setUseHalo(bool use) {
+      66           0 :         useHalo = use;
+      67           0 : }
+      68             : 
+      69           0 : bool PT11Field::isUsingASS() {
+      70           0 :         return useASS;
+      71             : }
+      72             : 
+      73           0 : bool PT11Field::isUsingBSS() {
+      74           0 :         return useBSS;
+      75             : }
+      76             : 
+      77           0 : bool PT11Field::isUsingHalo() {
+      78           0 :         return useHalo;
+      79             : }
+      80             : 
+      81           0 : Vector3d PT11Field::getField(const Vector3d& pos) const {
+      82           0 :         double r = sqrt(pos.x * pos.x + pos.y * pos.y);  // in-plane radius
+      83             : 
+      84             :         Vector3d b(0.);
+      85             : 
+      86             :         // disk field
+      87           0 :         if ((useASS) or (useBSS)) {
+      88             :                 // PT11 paper has B_theta = B * cos(p) but this seems because they define azimuth clockwise, while we have anticlockwise.
+      89             :                 // see Tinyakov 2002 APh 18,165: "local field points to l=90+p" so p=-5 deg gives l=85 and hence clockwise from above.
+      90             :                 // so to get local B clockwise in our system, need minus (like Sun etal).
+      91             :                 // Ps base their system on Han and Qiao 1994 A&A 288,759 which has a diagram with azimuth clockwise, hence confirmed.
+      92             : 
+      93             :                 // PT11 paper define Earth position at (+8.5, 0, 0) kpc; but usual convention is (-8.5, 0, 0)
+      94             :                 // thus we have to rotate our position by 180 degree in azimuth
+      95           0 :                 double theta = M_PI - pos.getPhi();  // azimuth angle theta: PT11 paper uses opposite convention for azimuth
+      96             :                 // the following is equivalent to sin(pi - phi) and cos(pi - phi) which is computationally slower
+      97           0 :                 double cos_theta = - pos.x / r;
+      98           0 :                 double sin_theta = pos.y / r;
+      99             : 
+     100             :                 // After some geometry calculations (on whiteboard) one finds:
+     101             :                 // Bx = +cos(theta) * B_r - sin(theta) * B_{theta}
+     102             :                 // By = -sin(theta) * B_r - cos(theta) * B_{theta}
+     103             :                 // Use from paper: B_theta = B * cos(pitch)     and B_r = B * sin(pitch)
+     104           0 :                 b.x = sin_pitch * cos_theta - cos_pitch * sin_theta;
+     105           0 :                 b.y = - sin_pitch * sin_theta - cos_pitch * cos_theta;
+     106             :                 b *= -1;        // flip magnetic field direction, as B_{theta} and B_{phi} refering to 180 degree rotated field
+     107             : 
+     108           0 :                 double bMag = cos(theta - cos_pitch / sin_pitch * log(r / R_sun) + PHI);
+     109           0 :                 if (useASS)
+     110           0 :                         bMag = fabs(bMag);
+     111           0 :                 bMag *= B0_D * R_sun / std::max(r, R_c) / cos_PHI * exp(-fabs(pos.z) / z0_D);
+     112             :                 b *= bMag;
+     113             :         }
+     114             : 
+     115             :         // halo field
+     116           0 :         if (useHalo) {
+     117           0 :                 double bMag = (pos.z > 0 ? B0_Hn : - B0_Hs);
+     118           0 :                 double z1 = (fabs(pos.z) < z0_H ? z11_H : z12_H);
+     119           0 :                 bMag *= r / R0_H * exp(1 - r / R0_H) / (1 + pow((fabs(pos.z) - z0_H) / z1, 2.));
+     120             :                 // equation (8) in paper: theta uses now the conventional azimuth definition in contrast to equation (3)
+     121             :                 // cos(phi) = pos.x / r (phi going counter-clockwise)
+     122             :                 // sin(phi) = pos.y / r
+     123             :                 // unitvector of phi in polar coordinates: (-sin(phi), cos(phi), 0)
+     124           0 :                 b += bMag * Vector3d(-pos.y / r, pos.x / r, 0);
+     125             :         }
+     126             : 
+     127           0 :         return b;
+     128             : }
+     129             : 
+     130             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html new file mode 100644 index 000000000..aa48a3251 --- /dev/null +++ b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/PolarizedSingleModeMagneticField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - PolarizedSingleModeMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:153246.9 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa32PolarizedSingleModeMagneticFieldC2ERKdS2_S2_RKNS_7Vector3IdEES6_S6_NSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESC_SC_1
_ZNK7crpropa32PolarizedSingleModeMagneticField8getFieldERKNS_7Vector3IdEE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html new file mode 100644 index 000000000..85b986750 --- /dev/null +++ b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/PolarizedSingleModeMagneticField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - PolarizedSingleModeMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:153246.9 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa32PolarizedSingleModeMagneticFieldC2ERKdS2_S2_RKNS_7Vector3IdEES6_S6_NSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESC_SC_1
_ZNK7crpropa32PolarizedSingleModeMagneticField8getFieldERKNS_7Vector3IdEE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html new file mode 100644 index 000000000..9ac25d10b --- /dev/null +++ b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html @@ -0,0 +1,142 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/PolarizedSingleModeMagneticField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - PolarizedSingleModeMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:153246.9 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/PolarizedSingleModeMagneticField.h"
+       2             : 
+       3             : namespace crpropa {
+       4             : 
+       5           1 : PolarizedSingleModeMagneticField::PolarizedSingleModeMagneticField( const double &B_0, const double &wavelength, const double &sigma, const Vector3d &r_0, const Vector3d &e_1, const Vector3d &e_2, std::string flagAmplitudeRms, std::string flagPolarizationHelicity, std::string flagMode ) {
+       6           1 :         if (flagMode == "elliptical") {
+       7           1 :                 if (abs(sigma) > 1)
+       8           0 :                         throw std::runtime_error("PolarizedSingleModeMagneticField: The value of the  polarization parameter has to lie in the range [-1;+1].");
+       9             :         }
+      10           0 :         else if (flagMode == "circular") {
+      11           0 :                 if (abs(sigma) != 1)
+      12           0 :                         throw std::runtime_error("PolarizedSingleModeMagneticField: For circular polarization the value of the polarization parameter has to be equal to -1 or +1.");
+      13             :         }
+      14           0 :         else if (flagMode == "linear") {
+      15           0 :                 if (abs(sigma) != 0)
+      16           0 :                         throw std::runtime_error("PolarizedSingleModeMagneticField: For linear polarization the value of the polarization parameter has to be equal to 0.");
+      17             :         }
+      18             :         else
+      19           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Wrong value for flagMode. Please choose \"elliptical\" or \"circular\" or \"linear\".");
+      20             : 
+      21           1 :         if (e_1.dot(e_2) != 0)
+      22           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: e_1 and e_2 have to be orthogonal to each other.");
+      23             : 
+      24           1 :         if (e_1.getR() == 0)
+      25           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Vector e_1 cannot be zero.");
+      26             :         unitVector_1 = e_1 / e_1.getR();
+      27             : 
+      28           1 :         if (e_2.getR() == 0)
+      29           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Vector e_2 cannot be zero.");
+      30             :         unitVector_2 = e_2 / e_2.getR();
+      31             : 
+      32             :         wavevector = e_2.cross(e_1);
+      33             : 
+      34             :         //This check is necessary if a polarization with non-orthogonal spanning vectors is desired. This is not implemented in this version, so any corresponding modifications should be made with caution.
+      35             :         //if (wavevector.getR() == 0)
+      36             :         //        throw std::runtime_error("PolarizedSingleModeMagneticField: e_1 cannot be parallel to e_2.");
+      37             : 
+      38             :         wavevector = wavevector / wavevector.getR();
+      39             : 
+      40           1 :         if (wavelength == 0)
+      41           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: The correlation length cannot be zero.");
+      42             :         wavevector = wavevector * 2 * M_PI / wavelength;
+      43             : 
+      44           2 :         if (!((flagPolarizationHelicity == "helicity") || (flagPolarizationHelicity == "polarization")))
+      45           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Wrong value for flagPolarizationHelicity. Please choose \"polarization\" or \"helicity\".");
+      46           1 :         if (flagPolarizationHelicity == "helicity" && abs(sigma) != 1)
+      47           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: In helicity mode only the maximum helicity case (sigma = +1 or sigma = -1) may be chosen.");
+      48             : 
+      49           1 :         if (flagAmplitudeRms == "amplitude")
+      50           1 :                 B_max = B_0;
+      51           0 :         else if (flagAmplitudeRms == "rms")
+      52           0 :                 B_max = sqrt(2 / (1 + sigma * sigma)) * B_0;
+      53             :         else
+      54           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Wrong value for flagAmplitudeRms. Please choose \"amplitude\" or \"rms\".");
+      55             : 
+      56             :         this->r_0 = r_0;
+      57           1 :         this->sigma = sigma;
+      58           1 : }
+      59             : 
+      60           1 : Vector3d PolarizedSingleModeMagneticField::getField(const Vector3d &position) const {
+      61             :         Vector3d delta_r = position - r_0;
+      62             : 
+      63           1 :         return B_max * (unitVector_1 * cos(wavevector.dot(delta_r)) + unitVector_2 * sigma * sin(wavevector.dot(delta_r)));
+      64             : }
+      65             : 
+      66             : } //end namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html new file mode 100644 index 000000000..dbd5a2431 --- /dev/null +++ b/doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html @@ -0,0 +1,188 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/TF17Field.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - TF17Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01960.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9TF17Field10set_H_diskEd0
_ZN7crpropa9TF17Field10set_L_diskEd0
_ZN7crpropa9TF17Field10set_L_haloEd0
_ZN7crpropa9TF17Field10set_a_diskEd0
_ZN7crpropa9TF17Field10set_a_haloEd0
_ZN7crpropa9TF17Field11set_B1_diskEd0
_ZN7crpropa9TF17Field11set_B1_haloEd0
_ZN7crpropa9TF17Field11set_r1_diskEd0
_ZN7crpropa9TF17Field11set_z1_diskEd0
_ZN7crpropa9TF17Field11set_z1_haloEd0
_ZN7crpropa9TF17Field15setUseDiskFieldEb0
_ZN7crpropa9TF17Field15setUseHaloFieldEb0
_ZN7crpropa9TF17Field16isUsingDiskFieldEv0
_ZN7crpropa9TF17Field16isUsingHaloFieldEv0
_ZN7crpropa9TF17Field17set_phi_star_diskEd0
_ZN7crpropa9TF17Field17set_phi_star_haloEd0
_ZN7crpropa9TF17Field6set_HpEd0
_ZN7crpropa9TF17Field6set_LpEd0
_ZN7crpropa9TF17Field6set_p0Ed0
_ZN7crpropa9TF17FieldC2ENS_13TF17DiskModelENS_13TF17HaloModelE0
_ZNK7crpropa9TF17Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getDiskModelB5cxx11Ev0
_ZNK7crpropa9TF17Field12getHaloFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getHaloModelB5cxx11Ev0
_ZNK7crpropa9TF17Field16radialFieldScaleERKdS2_S2_S2_S2_S2_0
_ZNK7crpropa9TF17Field22shiftedWindingFunctionERKdS2_0
_ZNK7crpropa9TF17Field23azimuthalFieldComponentERKdS2_S2_S2_0
_ZNK7crpropa9TF17Field6zscaleERKd0
_ZNK7crpropa9TF17Field8getFieldERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/TF17Field.cpp.func.html b/doc/coverageReport/src/magneticField/TF17Field.cpp.func.html new file mode 100644 index 000000000..4c39636c6 --- /dev/null +++ b/doc/coverageReport/src/magneticField/TF17Field.cpp.func.html @@ -0,0 +1,188 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/TF17Field.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - TF17Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01960.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9TF17Field10set_H_diskEd0
_ZN7crpropa9TF17Field10set_L_diskEd0
_ZN7crpropa9TF17Field10set_L_haloEd0
_ZN7crpropa9TF17Field10set_a_diskEd0
_ZN7crpropa9TF17Field10set_a_haloEd0
_ZN7crpropa9TF17Field11set_B1_diskEd0
_ZN7crpropa9TF17Field11set_B1_haloEd0
_ZN7crpropa9TF17Field11set_r1_diskEd0
_ZN7crpropa9TF17Field11set_z1_diskEd0
_ZN7crpropa9TF17Field11set_z1_haloEd0
_ZN7crpropa9TF17Field15setUseDiskFieldEb0
_ZN7crpropa9TF17Field15setUseHaloFieldEb0
_ZN7crpropa9TF17Field16isUsingDiskFieldEv0
_ZN7crpropa9TF17Field16isUsingHaloFieldEv0
_ZN7crpropa9TF17Field17set_phi_star_diskEd0
_ZN7crpropa9TF17Field17set_phi_star_haloEd0
_ZN7crpropa9TF17Field6set_HpEd0
_ZN7crpropa9TF17Field6set_LpEd0
_ZN7crpropa9TF17Field6set_p0Ed0
_ZN7crpropa9TF17FieldC2ENS_13TF17DiskModelENS_13TF17HaloModelE0
_ZNK7crpropa9TF17Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getDiskModelB5cxx11Ev0
_ZNK7crpropa9TF17Field12getHaloFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getHaloModelB5cxx11Ev0
_ZNK7crpropa9TF17Field16radialFieldScaleERKdS2_S2_S2_S2_S2_0
_ZNK7crpropa9TF17Field22shiftedWindingFunctionERKdS2_0
_ZNK7crpropa9TF17Field23azimuthalFieldComponentERKdS2_S2_S2_0
_ZNK7crpropa9TF17Field6zscaleERKd0
_ZNK7crpropa9TF17Field8getFieldERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html b/doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html new file mode 100644 index 000000000..b277961c9 --- /dev/null +++ b/doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html @@ -0,0 +1,383 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/TF17Field.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField - TF17Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01960.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/TF17Field.h"
+       2             : #include "crpropa/Units.h"
+       3             : 
+       4             : #include <algorithm>
+       5             : #include <string>
+       6             : 
+       7             : namespace crpropa {
+       8             : using namespace std;
+       9             : 
+      10           0 : TF17Field::TF17Field(TF17DiskModel disk_model_, TF17HaloModel halo_model_) {
+      11           0 :     disk_model = disk_model_; 
+      12           0 :     halo_model = halo_model_;
+      13             : 
+      14           0 :     useHaloField = true;
+      15           0 :     useDiskField = true;
+      16             : 
+      17           0 :     if ((halo_model == TF17HaloModel::C0) && (disk_model == TF17DiskModel::Ad1)) {
+      18             :         // disk parameters
+      19           0 :         set_r1_disk(3 * kpc);
+      20           0 :         set_B1_disk(19.0 * muG);
+      21           0 :         set_H_disk(0.055 * kpc);
+      22           0 :         set_phi_star_disk(-54 * M_PI / 180);
+      23           0 :         set_a_disk(0.9 / kpc / kpc);
+      24             :         // halo parameters
+      25           0 :         set_z1_halo(0);
+      26           0 :         set_B1_halo(0.36 * muG);
+      27           0 :         set_L_halo(3.0 * kpc);
+      28           0 :         set_a_halo(1.17 / kpc / kpc);
+      29             :         // shared parameters
+      30           0 :         set_p0(-7.9 * M_PI / 180);
+      31           0 :         set_Hp(5 * kpc);
+      32           0 :         set_Lp(50 * kpc); // > 18 kpc
+      33             :             
+      34           0 :     } else if ((halo_model == TF17HaloModel::C0) && (disk_model == TF17DiskModel::Bd1)) {
+      35             :         // disk parameters
+      36           0 :         set_r1_disk(3 * kpc);
+      37           0 :         set_B1_disk(2.0 * muG);
+      38           0 :         set_H_disk(0.32 * kpc);
+      39           0 :         set_phi_star_disk(153 * M_PI / 180);
+      40             :         // halo parameters
+      41           0 :         set_z1_halo(0);
+      42           0 :         set_B1_halo(0.29 * muG);
+      43           0 :         set_L_halo(3.4 * kpc);
+      44           0 :         set_a_halo(0.88 / kpc / kpc);
+      45             :         // shared parameters
+      46           0 :         set_p0(-7.2 * M_PI / 180);
+      47           0 :         set_Hp(9 * kpc);
+      48           0 :         set_Lp(50 * kpc); // > 16 kpc
+      49             : 
+      50           0 :     } else if ((halo_model == TF17HaloModel::C0) && (disk_model == TF17DiskModel::Dd1)) {
+      51             :         // disk parameters
+      52           0 :         set_z1_disk(1.5 * kpc);
+      53           0 :         set_B1_disk(0.065 * muG);
+      54           0 :         set_L_disk(9.8 * kpc);
+      55           0 :         set_phi_star_disk(14 * M_PI / 180);
+      56             :         // halo parameters
+      57           0 :         set_z1_halo(0);
+      58           0 :         set_B1_halo(0.18 * muG);
+      59           0 :         set_L_halo(4.8 * kpc);
+      60           0 :         set_a_halo(0.61 / kpc / kpc);
+      61             :         // shared parameters
+      62           0 :         set_p0(-7.4 * M_PI / 180);
+      63           0 :         set_Hp(4.2 * kpc);
+      64           0 :         set_Lp(50 * kpc); // > 22 kpc
+      65             : 
+      66           0 :     } else if ((halo_model == TF17HaloModel::C1) && (disk_model == TF17DiskModel::Ad1)) {
+      67             :         // disk parameters
+      68           0 :         set_r1_disk(3 * kpc);
+      69           0 :         set_B1_disk(32.0 * muG);
+      70           0 :         set_H_disk(0.054 * kpc);
+      71           0 :         set_phi_star_disk(-31 * M_PI / 180);
+      72           0 :         set_a_disk(0.031 / kpc / kpc);
+      73             :         // halo parameters
+      74           0 :         set_z1_halo(0);
+      75           0 :         set_B1_halo(9.0 * muG);
+      76           0 :         set_L_halo(2.1 * kpc);
+      77           0 :         set_phi_star_halo(198 * M_PI / 180);
+      78           0 :         set_a_halo(0.33 / kpc / kpc);
+      79             :         // shared parameters
+      80           0 :         set_p0(-9.1 * M_PI / 180);
+      81           0 :         set_Hp(1.2 * kpc);
+      82           0 :         set_Lp(50 * kpc); // > 38 kpc
+      83             : 
+      84           0 :     } else if ((halo_model == TF17HaloModel::C1) && (disk_model == TF17DiskModel::Bd1)) {
+      85             :         // disk parameters
+      86           0 :         set_r1_disk(3 * kpc);
+      87           0 :         set_B1_disk(24 * muG);
+      88           0 :         set_H_disk(0.090 * kpc);
+      89           0 :         set_phi_star_disk(-34 * M_PI / 180);
+      90             :         // halo parameters
+      91           0 :         set_z1_halo(0);
+      92           0 :         set_B1_halo(8.2 * muG);
+      93           0 :         set_L_halo(2.2 * kpc);
+      94           0 :         set_phi_star_halo(197 * M_PI / 180);
+      95           0 :         set_a_halo(0.38 / kpc / kpc);
+      96             :         // shared parameters
+      97           0 :         set_p0(-9.0 * M_PI / 180);
+      98           0 :         set_Hp(1.2 * kpc);
+      99           0 :         set_Lp(50 * kpc); // > 38 kpc
+     100             : 
+     101           0 :     } else if ((halo_model == TF17HaloModel::C1) && (disk_model == TF17DiskModel::Dd1)) {
+     102             :         // disk parameters
+     103           0 :         set_z1_disk(1.5 * kpc);
+     104           0 :         set_B1_disk(0.40 * muG);
+     105           0 :         set_L_disk(2.9 * kpc);
+     106           0 :         set_phi_star_disk(120 * M_PI / 180);
+     107             :         // halo parameters
+     108           0 :         set_z1_halo(0);
+     109           0 :         set_B1_halo(9.5 * muG);
+     110           0 :         set_L_halo(2.1 * kpc);
+     111           0 :         set_phi_star_halo(179 * M_PI / 180);
+     112           0 :         set_a_halo(0.45 / kpc / kpc);
+     113             :         // shared parameters
+     114           0 :         set_p0(-8.4 * M_PI / 180);
+     115           0 :         set_Hp(1.2 * kpc);
+     116           0 :         set_Lp(50 * kpc); // > 30 kpc
+     117             :     }
+     118             : 
+     119           0 :     epsilon = std::numeric_limits<double>::epsilon();
+     120           0 : }
+     121             : 
+     122           0 : void TF17Field::setUseDiskField(bool use) {     useDiskField = use; }
+     123           0 : void TF17Field::setUseHaloField(bool use) { useHaloField = use; }
+     124             : 
+     125           0 : bool TF17Field::isUsingDiskField() { return useDiskField; }
+     126           0 : bool TF17Field::isUsingHaloField() { return useHaloField; }
+     127             : 
+     128           0 : void TF17Field::set_B1_disk(const double B1){ B1_disk = B1; }
+     129           0 : void TF17Field::set_z1_disk(const double z1){ z1_disk = z1; }
+     130           0 : void TF17Field::set_r1_disk(const double r1){ r1_disk = r1; }
+     131           0 : void TF17Field::set_H_disk(const double H){ H_disk = H; }
+     132           0 : void TF17Field::set_L_disk(const double L){ L_disk = L; }
+     133           0 : void TF17Field::set_a_disk(const double a){ a_disk = a; }
+     134           0 : void TF17Field::set_phi_star_disk(const double phi){ phi_star_disk = phi; }
+     135             : 
+     136           0 : void TF17Field::set_B1_halo(const double B1){ B1_halo = B1; }
+     137           0 : void TF17Field::set_z1_halo(const double z1){ z1_halo = z1; }
+     138           0 : void TF17Field::set_L_halo(const double L){ L_halo = L; }
+     139           0 : void TF17Field::set_a_halo(const double a){ a_halo = a; }
+     140           0 : void TF17Field::set_phi_star_halo(const double phi){ phi_star_halo = phi; }
+     141             : 
+     142           0 : void TF17Field::set_Hp(const double H){ H_p = H; }
+     143           0 : void TF17Field::set_Lp(const double L){ L_p = L; }
+     144           0 : void TF17Field::set_p0(const double p0){ 
+     145           0 :     p_0 = p0; 
+     146           0 :     cot_p0 = cos(p_0) / sin(p_0);
+     147           0 : }
+     148             : 
+     149           0 : string TF17Field::getDiskModel() const {
+     150             :     string model_name;
+     151           0 :     switch (disk_model) {
+     152             :         case TF17DiskModel::Ad1 : model_name = "Ad1"; break;
+     153             :         case TF17DiskModel::Bd1 : model_name = "Bd1"; break;
+     154             :         case TF17DiskModel::Dd1 : model_name = "Dd1"; break;
+     155             :     }
+     156           0 :     return model_name;
+     157             : }
+     158           0 : string TF17Field::getHaloModel() const {
+     159             :     string model_name;
+     160           0 :     switch (halo_model) {
+     161             :         case TF17HaloModel::C0 : model_name = "C0"; break;
+     162             :         case TF17HaloModel::C1 : model_name = "C1"; break;
+     163             :     }
+     164           0 :     return model_name;
+     165             : }
+     166             : 
+     167             : 
+     168           0 : Vector3d TF17Field::getField(const Vector3d& pos) const {
+     169           0 :         double r = sqrt(pos.x * pos.x + pos.y * pos.y);  // in-plane radius
+     170           0 :         double phi = M_PI - pos.getPhi(); // azimuth in our convention
+     171             :         // double cosPhi = pos.x / r;
+     172           0 :         double cosPhi = cos(phi);
+     173             :         // double sinPhi = pos.y / r;
+     174           0 :         double sinPhi = sin(phi);
+     175             : 
+     176             :         Vector3d b(0.);
+     177           0 :         if (useDiskField)
+     178           0 :                 b += getDiskField(r, pos.z, phi, sinPhi, cosPhi);       // disk field
+     179           0 :         if (useHaloField)
+     180           0 :                 b += getHaloField(r, pos.z, phi, sinPhi, cosPhi);       // halo field
+     181           0 :         return b;
+     182             : }
+     183             : 
+     184           0 : Vector3d TF17Field::getDiskField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
+     185             :         Vector3d b(0.);
+     186           0 :     double B_r = 0;
+     187             :     double B_phi = 0;
+     188           0 :     double B_z = 0;
+     189             : 
+     190           0 :     if (disk_model == TF17DiskModel::Ad1) { // ==========================================================
+     191           0 :         if (r > r1_disk) {
+     192           0 :             double z1_disk_z = (1. + a_disk * r1_disk * r1_disk) / (1. + a_disk * r * r); // z1_disk / z
+     193             :             // B components in (r, phi, z)
+     194           0 :             double B_r0 = radialFieldScale(B1_disk, phi_star_disk, z1_disk_z*z, phi, r, z);
+     195           0 :             B_r = (r1_disk / r) * z1_disk_z * B_r0;
+     196           0 :             B_z = 2 * a_disk * r1_disk * z1_disk_z*z / (1+ a_disk * r * r) * B_r0;
+     197           0 :             B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
+     198             :         } else {
+     199             :             // within r = r1_disk, the field lines are straight in direction g_phi + phi_star_disk
+     200             :             // and thus z = z1
+     201           0 :             double phi1_disk = shiftedWindingFunction(r1_disk, z) + phi_star_disk;
+     202           0 :             double B_amp = B1_disk * exp(-fabs(z) / H_disk);
+     203           0 :             B_r = cos(phi1_disk - phi) * B_amp;
+     204           0 :             B_phi = sin(phi1_disk - phi) * B_amp;
+     205             :         }
+     206             : 
+     207           0 :     } else if (disk_model == TF17DiskModel::Bd1) { // ===================================================
+     208             :         // for model Bd1, best fit for n = 2 
+     209           0 :         if ( r > epsilon ) {
+     210           0 :             double r1_disk_r = r1_disk / r;     
+     211           0 :             double z1_disk_z = 5. / (r1_disk_r*r1_disk_r + 4./sqrt(r1_disk_r)); // z1_disk / z -> remove z dependancy 
+     212           0 :             double B_r0 = radialFieldScale(B1_disk, phi_star_disk, z1_disk_z*z, phi, r, z);
+     213           0 :             B_r = r1_disk_r * z1_disk_z * B_r0;
+     214           0 :             B_z = -0.4 * r1_disk_r / r * z1_disk_z* z1_disk_z * z * (r1_disk_r*r1_disk_r - 1./sqrt(r1_disk_r)) * B_r0;
+     215             :         } else {
+     216           0 :             double z1_disk_z = 5. * r*r / (r1_disk*r1_disk); // z1_disk / z -> remove z dependancy 
+     217           0 :             double B_r0 = radialFieldScale(B1_disk, phi_star_disk, z1_disk_z*z, phi, r, z);
+     218           0 :             B_r = 5. * r / r1_disk * B_r0;
+     219           0 :             B_z = -10. * z / r1_disk * B_r0;
+     220             :         }
+     221           0 :         B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
+     222             : 
+     223           0 :     } else if (disk_model == TF17DiskModel::Dd1) { // ===================================================
+     224             :         // for model Dd1, best fit for n = 0.5 
+     225           0 :         double z_sign = z >= 0 ? 1. : -1.; 
+     226           0 :         double z_abs = fabs(z); 
+     227           0 :         if ( z_abs > epsilon ) {
+     228           0 :             double z1_disk_z = z1_disk / z_abs; 
+     229           0 :             double r1_disk_r = 1.5 / (sqrt(z1_disk_z) + 0.5/z1_disk_z); // r1_disk / r
+     230           0 :             double F_r = r1_disk_r*r  <= L_disk ? 1. : exp(1. - r1_disk_r*r/L_disk);
+     231             :         // simplication of the equation in the cosinus
+     232           0 :             double B_z0 = z_sign * B1_disk * F_r * cos(phi - shiftedWindingFunction(r, z) - phi_star_disk);
+     233           0 :             B_r = -0.5/1.5 * r1_disk_r * r1_disk_r * r1_disk_r * r / z_abs * (sqrt(z1_disk_z) - 1/z1_disk_z) * B_z0;
+     234           0 :             B_z = z_sign * r1_disk_r * r1_disk_r * B_z0;
+     235             :         } else {
+     236           0 :             double z_z1_disk = z_abs / z1_disk; 
+     237           0 :             double r1_disk_r = 1.5 * sqrt(z_abs / z1_disk); // r1_disk / r
+     238           0 :             double F_r = r1_disk_r*r  <= L_disk ? 1. : exp(1. - r1_disk_r*r/L_disk);
+     239           0 :             double B_z0 = z_sign * B1_disk * F_r * cos(phi - shiftedWindingFunction(r, z) - phi_star_disk);
+     240           0 :             B_r = -1.125 * r / z1_disk * (1 - 2.5 * z_z1_disk * sqrt(z_z1_disk)) * B_z0;
+     241           0 :             B_z = z_sign * r1_disk_r * r1_disk_r * B_z0;
+     242             :         }
+     243           0 :         B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
+     244             :     }
+     245             : 
+     246             :     // Convert to (x, y, z) components
+     247           0 :     b.x = - (B_r * cosPhi - B_phi * sinPhi); // flip x-component at the end
+     248           0 :     b.y = B_r * sinPhi + B_phi * cosPhi;
+     249           0 :     b.z = B_z;
+     250           0 :         return b;
+     251             : }
+     252             : 
+     253           0 : Vector3d TF17Field::getHaloField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
+     254             :     int m;
+     255             : 
+     256             :         Vector3d b(0.);
+     257           0 :         double r1_halo_r =  (1. + a_halo * z1_halo * z1_halo) / (1. + a_halo * z * z);
+     258             :         // B components in (r, phi, z)
+     259             :     double B_z0;
+     260             : 
+     261           0 :     if (halo_model == TF17HaloModel::C0) { // m = 0
+     262           0 :         B_z0 = B1_halo * exp(-r1_halo_r*r / L_halo); 
+     263           0 :     } else if (halo_model == TF17HaloModel::C1) { // m = 1
+     264             :         // simplication of the equation in the cosinus
+     265           0 :         double phi_prime = phi - shiftedWindingFunction(r, z) - phi_star_halo;
+     266           0 :         B_z0 = B1_halo * exp(-r1_halo_r*r / L_halo) * cos(phi_prime); 
+     267             :     }
+     268             : 
+     269             :     // Contrary to article, Br has been rewriten to a little bit by replacing
+     270             :     // (2 * a * r1**3 * z) / (r**2) by (2 * a * r1**2 * z) / (r * (1+a*z**2))
+     271             :     // but that is strictly equivalent except we can reintroduce the z1 in the expression via r1
+     272           0 :         double B_r = 2 * a_halo * r1_halo_r * r1_halo_r * r * z / (1. + a_halo * z * z) * B_z0;
+     273           0 :         double B_z = r1_halo_r * r1_halo_r * B_z0; 
+     274           0 :         double B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
+     275             : 
+     276             :         // Convert to (x, y, z) components
+     277           0 :         b.x = - (B_r * cosPhi - B_phi * sinPhi);        // flip x-component at the end
+     278           0 :         b.y = B_r * sinPhi + B_phi * cosPhi;
+     279           0 :         b.z = B_z;
+     280             : 
+     281           0 :         return b;
+     282             : }
+     283             : 
+     284           0 : double TF17Field::azimuthalFieldComponent(const double& r, const double& z, const double& B_r, const double& B_z) const {
+     285           0 :         double r_ = r / L_p;
+     286           0 :     double rscale = r > epsilon ? r_ * exp(-r_) / (1 - exp(-r_)) : 1 - r_/2. - r_*r_/12. ;
+     287           0 :         double B_phi = cot_p0 / zscale(z) * rscale * B_r;
+     288           0 :     B_phi = B_phi - 2 * z * r / (H_p * H_p) / zscale(z) * shiftedWindingFunction(r, z) * B_z;
+     289           0 :         return B_phi;
+     290             : }
+     291             : 
+     292           0 : double TF17Field::radialFieldScale(const double& B1, const double& phi_star, const double& z1, const double& phi, const double& r, const double& z) const {
+     293             :     // simplication of the equation in the cosinus
+     294           0 :     double phi_prime = phi - shiftedWindingFunction(r, z) - phi_star;
+     295             :         // This term occures is parameterizations of models A and B always bisymmetric (m = 1)
+     296           0 :         return B1 * exp(-fabs(z1) / H_disk) * cos(phi_prime);
+     297             : }
+     298             : 
+     299           0 : double TF17Field::shiftedWindingFunction(const double& r, const double& z) const {
+     300           0 :     return cot_p0 * log(1 - exp(-r / L_p) + epsilon) / zscale(z);
+     301             : }
+     302             : 
+     303           0 : double TF17Field::zscale(const double& z) const {
+     304           0 :         return 1 + z * z / H_p / H_p;
+     305             : }
+     306             : 
+     307             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/index-sort-f.html b/doc/coverageReport/src/magneticField/index-sort-f.html new file mode 100644 index 000000000..e6f4aee3b --- /dev/null +++ b/doc/coverageReport/src/magneticField/index-sort-f.html @@ -0,0 +1,173 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:16691018.2 %
Date:2024-04-08 14:58:22Functions:2913821.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
PT11Field.cpp +
0.0%
+
0.0 %0 / 630.0 %0 / 9
ArchimedeanSpiralField.cpp +
0.0%
+
0.0 %0 / 420.0 %0 / 10
MagneticFieldGrid.cpp +
0.0%
+
0.0 %0 / 310.0 %0 / 11
JF12FieldSolenoidal.cpp +
0.0%
+
0.0 %0 / 1420.0 %0 / 14
TF17Field.cpp +
0.0%
+
0.0 %0 / 1960.0 %0 / 29
JF12Field.cpp +
0.0%
+
0.0 %0 / 2310.0 %0 / 29
MagneticField.cpp +
72.7%72.7%
+
72.7 %48 / 6656.2 %9 / 16
PolarizedSingleModeMagneticField.cpp +
46.9%46.9%
+
46.9 %15 / 32100.0 %2 / 2
CMZField.cpp +
96.3%96.3%
+
96.3 %103 / 107100.0 %18 / 18
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/index-sort-l.html b/doc/coverageReport/src/magneticField/index-sort-l.html new file mode 100644 index 000000000..2650220e6 --- /dev/null +++ b/doc/coverageReport/src/magneticField/index-sort-l.html @@ -0,0 +1,173 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:16691018.2 %
Date:2024-04-08 14:58:22Functions:2913821.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticFieldGrid.cpp +
0.0%
+
0.0 %0 / 310.0 %0 / 11
ArchimedeanSpiralField.cpp +
0.0%
+
0.0 %0 / 420.0 %0 / 10
PT11Field.cpp +
0.0%
+
0.0 %0 / 630.0 %0 / 9
JF12FieldSolenoidal.cpp +
0.0%
+
0.0 %0 / 1420.0 %0 / 14
TF17Field.cpp +
0.0%
+
0.0 %0 / 1960.0 %0 / 29
JF12Field.cpp +
0.0%
+
0.0 %0 / 2310.0 %0 / 29
PolarizedSingleModeMagneticField.cpp +
46.9%46.9%
+
46.9 %15 / 32100.0 %2 / 2
MagneticField.cpp +
72.7%72.7%
+
72.7 %48 / 6656.2 %9 / 16
CMZField.cpp +
96.3%96.3%
+
96.3 %103 / 107100.0 %18 / 18
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/index.html b/doc/coverageReport/src/magneticField/index.html new file mode 100644 index 000000000..e4d6a01d2 --- /dev/null +++ b/doc/coverageReport/src/magneticField/index.html @@ -0,0 +1,173 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:16691018.2 %
Date:2024-04-08 14:58:22Functions:2913821.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ArchimedeanSpiralField.cpp +
0.0%
+
0.0 %0 / 420.0 %0 / 10
CMZField.cpp +
96.3%96.3%
+
96.3 %103 / 107100.0 %18 / 18
JF12Field.cpp +
0.0%
+
0.0 %0 / 2310.0 %0 / 29
JF12FieldSolenoidal.cpp +
0.0%
+
0.0 %0 / 1420.0 %0 / 14
MagneticField.cpp +
72.7%72.7%
+
72.7 %48 / 6656.2 %9 / 16
MagneticFieldGrid.cpp +
0.0%
+
0.0 %0 / 310.0 %0 / 11
PT11Field.cpp +
0.0%
+
0.0 %0 / 630.0 %0 / 9
PolarizedSingleModeMagneticField.cpp +
46.9%46.9%
+
46.9 %15 / 32100.0 %2 / 2
TF17Field.cpp +
0.0%
+
0.0 %0 / 1960.0 %0 / 29
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html new file mode 100644 index 000000000..166f69ed4 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/GridTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - GridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8910485.6 %
Date:2024-04-08 14:58:22Functions:71353.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa14GridTurbulence10dumpToFileENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa14GridTurbulence16getPowerSpectrumEv0
_ZNK7crpropa14GridTurbulence18getMeanFieldVectorEv0
_ZNK7crpropa14GridTurbulence19getRmsFieldStrengthEv0
_ZNK7crpropa14GridTurbulence20getMeanFieldStrengthEv0
_ZNK7crpropa14GridTurbulence26getRmsFieldStrengthPerAxisEv0
_ZNK7crpropa14GridTurbulence7getGridEv1
_ZNK7crpropa14GridTurbulence8getFieldERKNS_7Vector3IdEE4
_ZN7crpropa14GridTurbulence14initTurbulenceEv6
_ZN7crpropa14GridTurbulence8initGridERKNS_14GridPropertiesE6
_ZN7crpropa14GridTurbulenceC2ERKNS_18TurbulenceSpectrumERKNS_14GridPropertiesEj6
_ZN7crpropa14GridTurbulence24executeInverseFFTInplaceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEPA2_fS8_S8_10
_ZN7crpropa14GridTurbulence21checkGridRequirementsENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEdd13
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html new file mode 100644 index 000000000..59602c105 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/GridTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - GridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8910485.6 %
Date:2024-04-08 14:58:22Functions:71353.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14GridTurbulence14initTurbulenceEv6
_ZN7crpropa14GridTurbulence21checkGridRequirementsENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEdd13
_ZN7crpropa14GridTurbulence24executeInverseFFTInplaceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEPA2_fS8_S8_10
_ZN7crpropa14GridTurbulence8initGridERKNS_14GridPropertiesE6
_ZN7crpropa14GridTurbulenceC2ERKNS_18TurbulenceSpectrumERKNS_14GridPropertiesEj6
_ZNK7crpropa14GridTurbulence10dumpToFileENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa14GridTurbulence16getPowerSpectrumEv0
_ZNK7crpropa14GridTurbulence18getMeanFieldVectorEv0
_ZNK7crpropa14GridTurbulence19getRmsFieldStrengthEv0
_ZNK7crpropa14GridTurbulence20getMeanFieldStrengthEv0
_ZNK7crpropa14GridTurbulence26getRmsFieldStrengthPerAxisEv0
_ZNK7crpropa14GridTurbulence7getGridEv1
_ZNK7crpropa14GridTurbulence8getFieldERKNS_7Vector3IdEE4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html new file mode 100644 index 000000000..fb8a58ac8 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html @@ -0,0 +1,289 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/GridTurbulence.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - GridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8910485.6 %
Date:2024-04-08 14:58:22Functions:71353.8 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/turbulentField/GridTurbulence.h"
+       2             : #include "crpropa/GridTools.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #ifdef CRPROPA_HAVE_FFTW3F
+       6             : 
+       7             : namespace crpropa {
+       8             : 
+       9             : 
+      10           6 : GridTurbulence::GridTurbulence(const TurbulenceSpectrum &spectrum,
+      11             :                                const GridProperties &gridProp,
+      12           6 :                                unsigned int seed)
+      13           6 :     : TurbulentField(spectrum), seed(seed) {
+      14           6 :         initGrid(gridProp);
+      15           6 :         checkGridRequirements(gridPtr, spectrum.getLmin(), spectrum.getLmax());
+      16           6 :         initTurbulence();
+      17           6 : }
+      18             : 
+      19           6 : void GridTurbulence::initGrid(const GridProperties &p) {
+      20           6 :         gridPtr = new Grid3f(p);
+      21           6 : }
+      22             : 
+      23           4 : Vector3d GridTurbulence::getField(const Vector3d &pos) const {
+      24           4 :         return gridPtr->interpolate(pos);
+      25             : }
+      26             : 
+      27           1 : const ref_ptr<Grid3f> &GridTurbulence::getGrid() const { return gridPtr; }
+      28             : 
+      29           6 : void GridTurbulence::initTurbulence() {
+      30             : 
+      31             :         Vector3d spacing = gridPtr->getSpacing();
+      32             :         size_t n = gridPtr->getNx(); // size of array
+      33           6 :         size_t n2 = (size_t)floor(n / 2) +
+      34             :                     1; // size array in z-direction in configuration space
+      35             : 
+      36             :         // arrays to hold the complex vector components of the B(k)-field
+      37             :         fftwf_complex *Bkx, *Bky, *Bkz;
+      38           6 :         Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      39           6 :         Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      40           6 :         Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      41             : 
+      42           6 :         Random random;
+      43           6 :         if (seed != 0)
+      44           4 :                 random.seed(seed); // use given seed
+      45             : 
+      46             :         // calculate the n possible discrete wave numbers
+      47           6 :         double K[n];
+      48         390 :         for (size_t i = 0; i < n; i++)
+      49         384 :                 K[i] = ((double)i / n - i / (n / 2));
+      50             : 
+      51             :         // double kMin = 2*M_PI / lMax; // * 2 * spacing.x; // spacing.x / lMax;
+      52             :         // double kMax = 2*M_PI / lMin; // * 2 * spacing.x; // spacing.x / lMin;
+      53           6 :         double kMin = spacing.x / spectrum.getLmax();
+      54           6 :         double kMax = spacing.x / spectrum.getLmin();
+      55           6 :         auto lambda = 1 / spacing.x * 2 * M_PI;
+      56             : 
+      57             :         Vector3f n0(1, 1, 1); // arbitrary vector to construct orthogonal base
+      58             : 
+      59         390 :         for (size_t ix = 0; ix < n; ix++) {
+      60       24960 :                 for (size_t iy = 0; iy < n; iy++) {
+      61      835584 :                         for (size_t iz = 0; iz < n2; iz++) {
+      62             :         
+      63             :                                 Vector3f ek, e1, e2;  // orthogonal base
+      64             : 
+      65      811008 :                                 size_t i = ix * n * n2 + iy * n2 + iz;
+      66      811008 :                                 ek.setXYZ(K[ix], K[iy], K[iz]);
+      67      811008 :                                 double k = ek.getR();
+      68             : 
+      69             :                                 // wave outside of turbulent range -> B(k) = 0
+      70      811008 :                                 if ((k < kMin) || (k > kMax)) {
+      71      395939 :                                         Bkx[i][0] = 0;
+      72      395939 :                                         Bkx[i][1] = 0;
+      73      395939 :                                         Bky[i][0] = 0;
+      74      395939 :                                         Bky[i][1] = 0;
+      75      395939 :                                         Bkz[i][0] = 0;
+      76      395939 :                                         Bkz[i][1] = 0;
+      77             :                                         continue;
+      78             :                                 }
+      79             : 
+      80             :                                 // construct an orthogonal base ek, e1, e2
+      81      415069 :                                 if (ek.isParallelTo(n0, float(1e-3))) {
+      82             :                                         // ek parallel to (1,1,1)
+      83             :                                         e1.setXYZ(-1., 1., 0);
+      84             :                                         e2.setXYZ(1., 1., -2.);
+      85             :                                 } else {
+      86             :                                         // ek not parallel to (1,1,1)
+      87             :                                         e1 = n0.cross(ek);
+      88             :                                         e2 = ek.cross(e1);
+      89             :                                 }
+      90             :                                 e1 /= e1.getR();
+      91             :                                 e2 /= e2.getR();
+      92             : 
+      93             :                                 // random orientation perpendicular to k
+      94      415069 :                                 double theta = 2 * M_PI * random.rand();
+      95      415069 :                                 Vector3f b = e1 * std::cos(theta) + e2 * std::sin(theta); // real b-field vector
+      96             : 
+      97             :                                 // normal distributed amplitude with mean = 0
+      98      415069 :                                 b *= std::sqrt(spectrum.energySpectrum(k*lambda));
+      99             :                                 
+     100             :                                 // uniform random phase
+     101      415069 :                                 double phase = 2 * M_PI * random.rand();
+     102      415069 :                                 double cosPhase = std::cos(phase); // real part
+     103      415069 :                                 double sinPhase = std::sin(phase); // imaginary part
+     104             : 
+     105      415069 :                                 Bkx[i][0] = b.x * cosPhase;
+     106      415069 :                                 Bkx[i][1] = b.x * sinPhase;
+     107      415069 :                                 Bky[i][0] = b.y * cosPhase;
+     108      415069 :                                 Bky[i][1] = b.y * sinPhase;
+     109      415069 :                                 Bkz[i][0] = b.z * cosPhase;
+     110      415069 :                                 Bkz[i][1] = b.z * sinPhase;
+     111             :                         } // for iz
+     112             :                 }     // for iy
+     113             :         }         // for ix
+     114             : 
+     115           6 :         executeInverseFFTInplace(gridPtr, Bkx, Bky, Bkz);
+     116             : 
+     117           6 :         fftwf_free(Bkx);
+     118           6 :         fftwf_free(Bky);
+     119           6 :         fftwf_free(Bkz);
+     120             : 
+     121          24 :         scaleGrid(gridPtr, spectrum.getBrms() /
+     122          12 :                                rmsFieldStrength(gridPtr)); // normalize to Brms
+     123          12 : }
+     124             : 
+     125             : // Check the grid properties before the FFT procedure
+     126          13 : void GridTurbulence::checkGridRequirements(ref_ptr<Grid3f> grid, double lMin,
+     127             :                                            double lMax) {
+     128             :         size_t Nx = grid->getNx();
+     129             :         size_t Ny = grid->getNy();
+     130             :         size_t Nz = grid->getNz();
+     131             :         Vector3d spacing = grid->getSpacing();
+     132             : 
+     133          13 :         if ((Nx != Ny) or (Ny != Nz))
+     134           0 :                 throw std::runtime_error("turbulentField: only cubic grid supported");
+     135          13 :         if ((spacing.x != spacing.y) or (spacing.y != spacing.z))
+     136           0 :                 throw std::runtime_error("turbulentField: only equal spacing suported");
+     137          13 :         if (lMin < 2 * spacing.x)
+     138           1 :                 throw std::runtime_error("turbulentField: lMin < 2 * spacing");
+     139          12 :         if (lMax > Nx * spacing.x) // before was (lMax > Nx * spacing.x / 2), why?
+     140           1 :                 throw std::runtime_error("turbulentField: lMax > size");
+     141          11 :         if (lMax < lMin) 
+     142           1 :                 throw std::runtime_error("lMax < lMin");
+     143          10 : }
+     144             : 
+     145             : // Execute inverse discrete FFT in-place for a 3D grid, from complex to real
+     146             : // space
+     147          10 : void GridTurbulence::executeInverseFFTInplace(ref_ptr<Grid3f> grid,
+     148             :                                               fftwf_complex *Bkx,
+     149             :                                               fftwf_complex *Bky,
+     150             :                                               fftwf_complex *Bkz) {
+     151             : 
+     152             :         size_t n = grid->getNx(); // size of array
+     153          10 :         size_t n2 = (size_t)floor(n / 2) +
+     154             :                     1; // size array in z-direction in configuration space
+     155             : 
+     156             :         // in-place, complex to real, inverse Fourier transformation on each
+     157             :         // component note that the last elements of B(x) are unused now
+     158             :         float *Bx = (float *)Bkx;
+     159          10 :         fftwf_plan plan_x = fftwf_plan_dft_c2r_3d(n, n, n, Bkx, Bx, FFTW_ESTIMATE);
+     160          10 :         fftwf_execute(plan_x);
+     161          10 :         fftwf_destroy_plan(plan_x);
+     162             : 
+     163             :         float *By = (float *)Bky;
+     164          10 :         fftwf_plan plan_y = fftwf_plan_dft_c2r_3d(n, n, n, Bky, By, FFTW_ESTIMATE);
+     165          10 :         fftwf_execute(plan_y);
+     166          10 :         fftwf_destroy_plan(plan_y);
+     167             : 
+     168             :         float *Bz = (float *)Bkz;
+     169          10 :         fftwf_plan plan_z = fftwf_plan_dft_c2r_3d(n, n, n, Bkz, Bz, FFTW_ESTIMATE);
+     170          10 :         fftwf_execute(plan_z);
+     171          10 :         fftwf_destroy_plan(plan_z);
+     172             : 
+     173             :         // save to grid
+     174         650 :         for (size_t ix = 0; ix < n; ix++) {
+     175       41600 :                 for (size_t iy = 0; iy < n; iy++) {
+     176     2662400 :                         for (size_t iz = 0; iz < n; iz++) {
+     177     2621440 :                                 size_t i = ix * n * 2 * n2 + iy * 2 * n2 + iz;
+     178             :                                 Vector3f &b = grid->get(ix, iy, iz);
+     179     2621440 :                                 b.x = Bx[i];
+     180     2621440 :                                 b.y = By[i];
+     181     2621440 :                                 b.z = Bz[i];
+     182             :                         }
+     183             :                 }
+     184             :         }
+     185          10 : }
+     186             : 
+     187           0 : Vector3f GridTurbulence::getMeanFieldVector() const {
+     188           0 :         return meanFieldVector(gridPtr);
+     189             : }
+     190             : 
+     191           0 : double GridTurbulence::getMeanFieldStrength() const {
+     192           0 :         return meanFieldStrength(gridPtr);
+     193             : }
+     194             : 
+     195           0 : double GridTurbulence::getRmsFieldStrength() const {
+     196           0 :         return rmsFieldStrength(gridPtr);
+     197             : }
+     198             : 
+     199           0 : std::array<float, 3> GridTurbulence::getRmsFieldStrengthPerAxis() const {
+     200           0 :         return rmsFieldStrengthPerAxis(gridPtr);
+     201             : }
+     202             :         
+     203           0 : std::vector<std::pair<int, float>> GridTurbulence::getPowerSpectrum() const {
+     204           0 :         return gridPowerSpectrum(gridPtr);
+     205             : }
+     206             : 
+     207           0 : void GridTurbulence::dumpToFile(std::string filename) const {
+     208           0 :         dumpGrid(gridPtr, filename);
+     209           0 : }
+     210             : 
+     211             : } // namespace crpropa
+     212             : 
+     213             : #endif // CRPROPA_HAVE_FFTW3F
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html new file mode 100644 index 000000000..ce798a6be --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/HelicalGridTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - HelicalGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0590.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21HelicalGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
_ZN7crpropa21HelicalGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEdj0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html new file mode 100644 index 000000000..3a300bc05 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/HelicalGridTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - HelicalGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0590.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21HelicalGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
_ZN7crpropa21HelicalGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEdj0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html new file mode 100644 index 000000000..4a3415bc2 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html @@ -0,0 +1,206 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/HelicalGridTurbulence.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - HelicalGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0590.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/turbulentField/HelicalGridTurbulence.h"
+       2             : #include "crpropa/GridTools.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #ifdef CRPROPA_HAVE_FFTW3F
+       6             : #include "fftw3.h"
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10           0 : HelicalGridTurbulence::HelicalGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
+      11             :                                              const GridProperties &gridProp,
+      12           0 :                                              double H, unsigned int seed)
+      13           0 :     : SimpleGridTurbulence(spectrum, gridProp, seed), H(H) {
+      14           0 :         initTurbulence(gridPtr, spectrum.getBrms(), spectrum.getLmin(),
+      15           0 :                        spectrum.getLmax(), -spectrum.getSindex() - 2, seed, H);
+      16           0 : }
+      17             : 
+      18           0 : void HelicalGridTurbulence::initTurbulence(ref_ptr<Grid3f> grid, double Brms,
+      19             :                                            double lMin, double lMax,
+      20             :                                            double alpha, int seed, double H) {
+      21             : 
+      22           0 :         checkGridRequirements(grid, lMin, lMax);
+      23             : 
+      24             :         Vector3d spacing = grid->getSpacing();
+      25             :         size_t n = grid->getNx(); // size of array
+      26           0 :         size_t n2 = (size_t)floor(n / 2) +
+      27             :                     1; // size array in z-direction in configuration space
+      28             : 
+      29             :         // arrays to hold the complex vector components of the B(k)-field
+      30             :         fftwf_complex *Bkx, *Bky, *Bkz;
+      31           0 :         Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      32           0 :         Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      33           0 :         Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      34             : 
+      35           0 :         Random random;
+      36           0 :         if (seed != 0)
+      37           0 :                 random.seed(seed); // use given seed
+      38             : 
+      39             :         // calculate the n possible discrete wave numbers
+      40           0 :         double K[n];
+      41           0 :         for (size_t i = 0; i < n; i++)
+      42           0 :                 K[i] = (double)i / n - i / (n / 2);
+      43             : 
+      44             :         // only used if there is a helicity
+      45             :         double Bktot, Bkplus, Bkminus, thetaplus, thetaminus;
+      46             : 
+      47           0 :         double kMin = spacing.x / lMax;
+      48           0 :         double kMax = spacing.x / lMin;
+      49             :         Vector3f b;           // real b-field vector
+      50             :         Vector3f ek, e1, e2;  // orthogonal base
+      51             :         Vector3f n0(1, 1, 1); // arbitrary vector to construct orthogonal base
+      52             : 
+      53           0 :         for (size_t ix = 0; ix < n; ix++) {
+      54           0 :                 for (size_t iy = 0; iy < n; iy++) {
+      55           0 :                         for (size_t iz = 0; iz < n2; iz++) {
+      56             : 
+      57           0 :                                 size_t i = ix * n * n2 + iy * n2 + iz;
+      58           0 :                                 ek.setXYZ(K[ix], K[iy], K[iz]);
+      59           0 :                                 double k = ek.getR();
+      60             : 
+      61             :                                 // wave outside of turbulent range -> B(k) = 0
+      62           0 :                                 if ((k < kMin) || (k > kMax)) {
+      63           0 :                                         Bkx[i][0] = 0;
+      64           0 :                                         Bkx[i][1] = 0;
+      65           0 :                                         Bky[i][0] = 0;
+      66           0 :                                         Bky[i][1] = 0;
+      67           0 :                                         Bkz[i][0] = 0;
+      68           0 :                                         Bkz[i][1] = 0;
+      69             :                                         continue;
+      70             :                                 }
+      71             : 
+      72             :                                 // construct an orthogonal base ek, e1, e2
+      73             :                                 // (for helical fields together with the real transform the
+      74             :                                 // following convention must be used: e1(-k) = e1(k), e2(-k) = -
+      75             :                                 // e2(k)
+      76           0 :                                 if (ek.getAngleTo(n0) < 1e-3) { // ek parallel to (1,1,1)
+      77             :                                         e1.setXYZ(-1, 1, 0);
+      78             :                                         e2.setXYZ(1, 1, -2);
+      79             :                                 } else { // ek not parallel to (1,1,1)
+      80             :                                         e1 = n0.cross(ek);
+      81             :                                         e2 = ek.cross(e1);
+      82             :                                 }
+      83             :                                 e1 /= e1.getR();
+      84             :                                 e2 /= e2.getR();
+      85             : 
+      86             : 
+      87           0 :                                 double Bkprefactor = mu0 / (4 * M_PI * pow(k, 3));
+      88           0 :                                 Bktot = fabs(random.randNorm() * pow(k, alpha / 2));
+      89           0 :                                 Bkplus = Bkprefactor * sqrt((1 + H) / 2) * Bktot;
+      90           0 :                                 Bkminus = Bkprefactor * sqrt((1 - H) / 2) * Bktot;
+      91           0 :                                 thetaplus = 2 * M_PI * random.rand();
+      92           0 :                                 thetaminus = 2 * M_PI * random.rand();
+      93           0 :                                 double ctp = cos(thetaplus);
+      94           0 :                                 double stp = sin(thetaplus);
+      95           0 :                                 double ctm = cos(thetaminus);
+      96           0 :                                 double stm = sin(thetaminus);
+      97             : 
+      98           0 :                                 Bkx[i][0] = ((Bkplus * ctp + Bkminus * ctm) * e1.x +
+      99           0 :                                              (-Bkplus * stp + Bkminus * stm) * e2.x) /
+     100             :                                             sqrt(2);
+     101           0 :                                 Bkx[i][1] = ((Bkplus * stp + Bkminus * stm) * e1.x +
+     102           0 :                                              (Bkplus * ctp - Bkminus * ctm) * e2.x) /
+     103             :                                             sqrt(2);
+     104           0 :                                 Bky[i][0] = ((Bkplus * ctp + Bkminus * ctm) * e1.y +
+     105           0 :                                              (-Bkplus * stp + Bkminus * stm) * e2.y) /
+     106             :                                             sqrt(2);
+     107           0 :                                 Bky[i][1] = ((Bkplus * stp + Bkminus * stm) * e1.y +
+     108           0 :                                              (Bkplus * ctp - Bkminus * ctm) * e2.y) /
+     109             :                                             sqrt(2);
+     110           0 :                                 Bkz[i][0] = ((Bkplus * ctp + Bkminus * ctm) * e1.z +
+     111           0 :                                              (-Bkplus * stp + Bkminus * stm) * e2.z) /
+     112             :                                             sqrt(2);
+     113           0 :                                 Bkz[i][1] = ((Bkplus * stp + Bkminus * stm) * e1.z +
+     114           0 :                                              (Bkplus * ctp - Bkminus * ctm) * e2.z) /
+     115             :                                             sqrt(2);
+     116             : 
+     117             :                                 Vector3f BkRe(Bkx[i][0], Bky[i][0], Bkz[i][0]);
+     118             :                                 Vector3f BkIm(Bkx[i][1], Bky[i][1], Bkz[i][1]);
+     119             :                         } // for iz
+     120             :                 }     // for iy
+     121             :         }         // for ix
+     122             : 
+     123           0 :         executeInverseFFTInplace(grid, Bkx, Bky, Bkz);
+     124             : 
+     125           0 :         scaleGrid(grid, Brms / rmsFieldStrength(grid)); // normalize to Brms
+     126           0 : }
+     127             : 
+     128             : } // namespace crpropa
+     129             : 
+     130             : #endif // CRPROPA_HAVE_FFTW3F
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html new file mode 100644 index 000000000..ecbe74169 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/PlaneWaveTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - PlaneWaveTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:464895.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PlaneWaveTurbulenceC2ERKNS_18TurbulenceSpectrumEii2
_ZNK7crpropa19PlaneWaveTurbulence8getFieldERKNS_7Vector3IdEE45
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html new file mode 100644 index 000000000..3a3efe0af --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/PlaneWaveTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - PlaneWaveTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:464895.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PlaneWaveTurbulenceC2ERKNS_18TurbulenceSpectrumEii2
_ZNK7crpropa19PlaneWaveTurbulence8getFieldERKNS_7Vector3IdEE45
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html new file mode 100644 index 000000000..0344bde9e --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html @@ -0,0 +1,517 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/PlaneWaveTurbulence.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - PlaneWaveTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:464895.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : // This file contains an implementation of a vectorized cosine, which
+       2             : // is based in part on the implementations in the library "SLEEF" by
+       3             : // Naoki Shibata. SLEEF was used under the Boost Software License,
+       4             : // Version 1.0. The original source file contained the following
+       5             : // copyright notice:
+       6             : //
+       7             : //   //          Copyright Naoki Shibata 2010 - 2018.
+       8             : //   // Distributed under the Boost Software License, Version 1.0.
+       9             : //   //    (See accompanying file LICENSE.txt or copy at
+      10             : //   //          http://www.boost.org/LICENSE_1_0.txt)
+      11             : //
+      12             : // SLEEF was used under the following license, which is not necessarily the
+      13             : // license that applies to this file:
+      14             : //
+      15             : //         Boost Software License - Version 1.0 - August 17th, 2003
+      16             : //
+      17             : //         Permission is hereby granted, free of charge, to any person or
+      18             : //         organization obtaining a copy of the software and accompanying
+      19             : //         documentation covered by this license (the "Software") to use,
+      20             : //         reproduce, display, distribute, execute, and transmit the Software,
+      21             : //         and to prepare derivative works of the Software, and to permit
+      22             : //         third-parties to whom the Software is furnished to do so, all subject
+      23             : //         to the following:
+      24             : //
+      25             : //         The copyright notices in the Software and this entire statement,
+      26             : //         including the above license grant, this restriction and the following
+      27             : //         disclaimer, must be included in all copies of the Software, in whole
+      28             : //         or in part, and all derivative works of the Software, unless such
+      29             : //         copies or derivative works are solely in the form of
+      30             : //         machine-executable object code generated by a source language
+      31             : //         processor.
+      32             : //
+      33             : //         THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
+      34             : //         EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
+      35             : //         MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE AND
+      36             : //         NON-INFRINGEMENT. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR ANYONE
+      37             : //         DISTRIBUTING THE SOFTWARE BE LIABLE FOR ANY DAMAGES OR OTHER
+      38             : //         LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
+      39             : //         OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+      40             : //         THE SOFTWARE.
+      41             : 
+      42             : #include "crpropa/magneticField/turbulentField/PlaneWaveTurbulence.h"
+      43             : #include "crpropa/GridTools.h"
+      44             : #include "crpropa/Random.h"
+      45             : #include "crpropa/Units.h"
+      46             : 
+      47             : #include "kiss/logger.h"
+      48             : 
+      49             : #include <iostream>
+      50             : 
+      51             : #if defined(FAST_WAVES)
+      52             : #if defined(__SSE__) && defined(__SSE2__) && defined(__SSE3__) && defined(__SSE4_1__) && defined(__SSE4_2__) && defined(__AVX__)
+      53             : #define ENABLE_FAST_WAVES
+      54             : #else
+      55             : #error "FAST_WAVES is enabled, but it appears that not all required SIMD extensions are enabled in the compiler. Without these extensions, the FAST_WAVES optimization cannot be used. Please make sure that the SIMD_EXTENSIONS option in cmake matches the capabilities of your target CPU, or (if your target CPU does not support the required extensions), disable the FAST_WAVES flag in cmake."
+      56             : #endif
+      57             : #endif
+      58             : 
+      59             : 
+      60             : #ifdef ENABLE_FAST_WAVES
+      61             : #include <immintrin.h>
+      62             : #endif
+      63             : 
+      64             : namespace crpropa {
+      65             : #ifdef ENABLE_FAST_WAVES
+      66             : // see
+      67             : // https://stackoverflow.com/questions/49941645/get-sum-of-values-stored-in-m256d-with-sse-avx
+      68             : double hsum_double_avx(__m256d v) {
+      69             :         __m128d vlow = _mm256_castpd256_pd128(v);
+      70             :         __m128d vhigh = _mm256_extractf128_pd(v, 1); // high 128
+      71             :         vlow = _mm_add_pd(vlow, vhigh);              // reduce down to 128
+      72             : 
+      73             :         __m128d high64 = _mm_unpackhi_pd(vlow, vlow);
+      74             :         return _mm_cvtsd_f64(_mm_add_sd(vlow, high64)); // reduce to scalar
+      75             : }
+      76             : #endif // defined(ENABLE_FAST_WAVES)
+      77             : 
+      78           2 : PlaneWaveTurbulence::PlaneWaveTurbulence(const TurbulenceSpectrum &spectrum,
+      79           2 :                                          int Nm, int seed)
+      80           2 :     : TurbulentField(spectrum), Nm(Nm) {
+      81             : 
+      82             : #ifdef ENABLE_FAST_WAVES
+      83             :         KISS_LOG_INFO << "PlaneWaveTurbulence: Using SIMD TD13 implementation"
+      84             :                       << std::endl;
+      85             : 
+      86             :         // There used to be a cpuid check here, to see if the cpu running
+      87             :         // this code would support SIMD (SSE + AVX). However, the library providing
+      88             :         // the relevant function is no longer being used, and doing this manually
+      89             :         // might be a bit too much work.
+      90             : #endif
+      91             : 
+      92           2 :         if (Nm <= 1) {
+      93           0 :                 throw std::runtime_error(
+      94             :                     "PlaneWaveTurbulence: Nm <= 1. Specify at least two wavemodes in "
+      95           0 :                     "order to generate the k distribution properly.");
+      96             :         }
+      97             : 
+      98           2 :         Random random;
+      99           2 :         if (seed != 0)
+     100           2 :                 random.seed(seed);
+     101             : 
+     102           2 :         double kmax = 2 * M_PI / spectrum.getLmin();
+     103           2 :         double kmin = 2 * M_PI / spectrum.getLmax();
+     104             : 
+     105           4 :         xi = std::vector<Vector3d>(Nm, Vector3d(0.));
+     106           4 :         kappa = std::vector<Vector3d>(Nm, Vector3d(0.));
+     107           2 :         phi = std::vector<double>(Nm, 0.);
+     108           2 :         costheta = std::vector<double>(Nm, 0.);
+     109           2 :         beta = std::vector<double>(Nm, 0.);
+     110           2 :         Ak = std::vector<double>(Nm, 0.);
+     111           2 :         k = std::vector<double>(Nm, 0.);
+     112             : 
+     113           2 :         double delta = log10(kmax / kmin);
+     114          22 :         for (int i = 0; i < Nm; i++) {
+     115          20 :                 k[i] = pow(10, log10(kmin) + ((double)i) / ((double)(Nm - 1)) * delta);
+     116             :         }
+     117             : 
+     118             :         // * compute Ak *
+     119             : 
+     120             :         double delta_k0 =
+     121           2 :             (k[1] - k[0]) / k[1]; // multiply this by k[i] to get delta_k[i]
+     122             :         // Note: this is probably unnecessary since it's just a factor
+     123             :         // and will get normalized out anyways. It's not like this is
+     124             :         // performance-sensitive code though, and I don't want to change
+     125             :         // anything numerical now.
+     126             : 
+     127             :         // For this loop, the Ak array actually contains Gk*delta_k (ie
+     128             :         // non-normalized Ak^2). Normalization happens in a second loop,
+     129             :         // once the total is known.
+     130             :         double Ak2_sum = 0; // sum of Ak^2 over all k
+     131          22 :         for (int i = 0; i < Nm; i++) {
+     132          20 :                 double k = this->k[i];
+     133          20 :                 double kHat = k * spectrum.getLbendover();
+     134          20 :                 double Gk = spectrum.energySpectrum(k) * (1 + kHat * kHat);     // correct different implementation in TD 13 (eq. 5, missing + 1 in the denuminators exponent)
+     135          20 :                 Ak[i] = Gk * delta_k0 * k;
+     136          20 :                 Ak2_sum += Ak[i];
+     137             : 
+     138             :                 // phi, costheta, and sintheta are for drawing vectors with
+     139             :                 // uniform distribution on the unit sphere.
+     140             :                 // This is similar to Random::randVector(): their t is our phi,
+     141             :                 // z is costheta, and r is sintheta. Our kappa is equivalent to
+     142             :                 // the return value of randVector(); however, TD13 then reuse
+     143             :                 // these values to generate a random vector perpendicular to kappa.
+     144          20 :                 double phi = random.randUniform(-M_PI, M_PI);
+     145          20 :                 double costheta = random.randUniform(-1., 1.);
+     146          20 :                 double sintheta = sqrt(1 - costheta * costheta);
+     147             : 
+     148          20 :                 double alpha = random.randUniform(0, 2 * M_PI);
+     149          20 :                 double beta = random.randUniform(0, 2 * M_PI);
+     150             : 
+     151             :                 Vector3d kappa =
+     152          20 :                     Vector3d(sintheta * cos(phi), sintheta * sin(phi), costheta);
+     153             : 
+     154             :                 // NOTE: all other variable names match the ones from the TD13 paper.
+     155             :                 // However, our xi is actually their psi, and their xi isn't used at
+     156             :                 // all. (Though both can be used for the polarization vector, according
+     157             :                 // to the paper.) The reason for this discrepancy is that this code
+     158             :                 // used to be based on the original GJ99 paper, which provided only a
+     159             :                 // xi vector, and this xi happens to be almost the same as TD13's psi.
+     160             :                 Vector3d xi =
+     161          20 :                     Vector3d(costheta * cos(phi) * cos(alpha) + sin(phi) * sin(alpha),
+     162          20 :                              costheta * sin(phi) * cos(alpha) - cos(phi) * sin(alpha),
+     163          20 :                              -sintheta * cos(alpha));
+     164             : 
+     165             :                 this->xi[i] = xi;
+     166             :                 this->kappa[i] = kappa;
+     167          20 :                 this->phi[i] = phi;
+     168          20 :                 this->costheta[i] = costheta;
+     169          20 :                 this->beta[i] = beta;
+     170             :         }
+     171             : 
+     172             :         // Only in this loop are the actual Ak computed and stored.
+     173             :         // This two-step process is necessary in order to normalize the values
+     174             :         // properly.
+     175          22 :         for (int i = 0; i < Nm; i++) {
+     176          20 :                 Ak[i] = sqrt(2 * Ak[i] / Ak2_sum) * spectrum.getBrms();
+     177             :         }
+     178             : 
+     179             : #ifdef ENABLE_FAST_WAVES
+     180             :         // * copy data into AVX-compatible arrays *
+     181             :         //
+     182             :         // AVX requires all data to be aligned to 256 bit, or 32 bytes, which is the
+     183             :         // same as 4 double precision floating point numbers. Since support for
+     184             :         // alignments this big seems to be somewhat tentative in C++ allocators,
+     185             :         // we're aligning them manually by allocating a normal double array, and
+     186             :         // then computing the offset to the first value with the correct alignment.
+     187             :         // This is a little bit of work, so instead of doing it separately for each
+     188             :         // of the individual data arrays, we're doing it once for one big array that
+     189             :         // all of the component arrays get packed into.
+     190             :         //
+     191             :         // The other thing to keep in mind is that AVX always reads in units of 256
+     192             :         // bits, or 4 doubles. This means that our number of wavemodes must be
+     193             :         // divisible by 4. If it isn't, we simply pad it out with zeros. Since the
+     194             :         // final step of the computation of each wavemode is multiplication by the
+     195             :         // amplitude, which will be set to 0, these padding wavemodes won't affect
+     196             :         // the result.
+     197             : 
+     198             :         avx_Nm = ((Nm + 4 - 1) / 4) * 4; // round up to next larger multiple of 4:
+     199             :                                          // align is 256 = 4 * sizeof(double) bit
+     200             :         avx_data = std::vector<double>(itotal * avx_Nm + 3, 0.);
+     201             : 
+     202             :         // get the first 256-bit aligned element
+     203             :         size_t size = avx_data.size() * sizeof(double);
+     204             :         void *pointer = avx_data.data();
+     205             :         align_offset =
+     206             :             (double *)std::align(32, 32, pointer, size) - avx_data.data();
+     207             : 
+     208             :         // copy into the AVX arrays
+     209             :         for (int i = 0; i < Nm; i++) {
+     210             :                 avx_data[i + align_offset + avx_Nm * iAxi0] = Ak[i] * xi[i].x;
+     211             :                 avx_data[i + align_offset + avx_Nm * iAxi1] = Ak[i] * xi[i].y;
+     212             :                 avx_data[i + align_offset + avx_Nm * iAxi2] = Ak[i] * xi[i].z;
+     213             : 
+     214             :                 // The cosine implementation computes cos(pi*x), so we'll divide out the
+     215             :                 // pi here.
+     216             :                 avx_data[i + align_offset + avx_Nm * ikkappa0] =
+     217             :                     k[i] / M_PI * kappa[i].x;
+     218             :                 avx_data[i + align_offset + avx_Nm * ikkappa1] =
+     219             :                     k[i] / M_PI * kappa[i].y;
+     220             :                 avx_data[i + align_offset + avx_Nm * ikkappa2] =
+     221             :                     k[i] / M_PI * kappa[i].z;
+     222             : 
+     223             :                 // We also need to divide beta by pi, since that goes into the argument
+     224             :                 // of the cosine as well.
+     225             :                 avx_data[i + align_offset + avx_Nm * ibeta] = beta[i] / M_PI;
+     226             :         }
+     227             : #endif // ENABLE_FAST_WAVES
+     228           2 : }
+     229             : 
+     230          45 : Vector3d PlaneWaveTurbulence::getField(const Vector3d &pos) const {
+     231             : 
+     232             : #ifndef ENABLE_FAST_WAVES
+     233             :         Vector3d B(0.);
+     234         495 :         for (int i = 0; i < Nm; i++) {
+     235         450 :                 double z_ = pos.dot(kappa[i]);
+     236         450 :                 B += xi[i] * Ak[i] * cos(k[i] * z_ + beta[i]);
+     237             :         }
+     238          45 :         return B;
+     239             : 
+     240             : #else  // ENABLE_FAST_WAVES
+     241             : 
+     242             :         // Initialize accumulators
+     243             :         //
+     244             :         // There is one accumulator per component of the result vector.
+     245             :         // Note that each accumulator contains four numbers. At the end of
+     246             :         // the loop, each of these numbers will contain the sum of every
+     247             :         // fourth wavemode, starting at a different offset. In the end, each
+     248             :         // of the accumulator's numbers are added together (using
+     249             :         // hsum_double_avx), resulting in the total sum for that component.
+     250             : 
+     251             :         __m256d acc0 = _mm256_setzero_pd();
+     252             :         __m256d acc1 = _mm256_setzero_pd();
+     253             :         __m256d acc2 = _mm256_setzero_pd();
+     254             : 
+     255             :         // broadcast position into AVX registers
+     256             :         __m256d pos0 = _mm256_set1_pd(pos.x);
+     257             :         __m256d pos1 = _mm256_set1_pd(pos.y);
+     258             :         __m256d pos2 = _mm256_set1_pd(pos.z);
+     259             : 
+     260             :         for (int i = 0; i < avx_Nm; i += 4) {
+     261             : 
+     262             :                 // Load data from memory into AVX registers:
+     263             :                 //  - the three components of the vector A * xi
+     264             :                 __m256d Axi0 =
+     265             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * iAxi0);
+     266             :                 __m256d Axi1 =
+     267             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * iAxi1);
+     268             :                 __m256d Axi2 =
+     269             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * iAxi2);
+     270             : 
+     271             :                 //  - the three components of the vector k * kappa
+     272             :                 __m256d kkappa0 = _mm256_load_pd(avx_data.data() + i + align_offset +
+     273             :                                                  avx_Nm * ikkappa0);
+     274             :                 __m256d kkappa1 = _mm256_load_pd(avx_data.data() + i + align_offset +
+     275             :                                                  avx_Nm * ikkappa1);
+     276             :                 __m256d kkappa2 = _mm256_load_pd(avx_data.data() + i + align_offset +
+     277             :                                                  avx_Nm * ikkappa2);
+     278             : 
+     279             :                 //  - the phase beta.
+     280             :                 __m256d beta =
+     281             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * ibeta);
+     282             : 
+     283             :                 // Then, do the computation.
+     284             : 
+     285             :                 // This is the scalar product between k*kappa and pos:
+     286             :                 __m256d z = _mm256_add_pd(_mm256_mul_pd(pos0, kkappa0),
+     287             :                                           _mm256_add_pd(_mm256_mul_pd(pos1, kkappa1),
+     288             :                                                         _mm256_mul_pd(pos2, kkappa2)));
+     289             : 
+     290             :                 // Here, the phase is added on. This is the argument of the cosine.
+     291             :                 __m256d cos_arg = _mm256_add_pd(z, beta);
+     292             : 
+     293             :                 // ********
+     294             :                 // * Computing the cosine
+     295             :                 // * Part 1: Argument reduction
+     296             :                 //
+     297             :                 //  To understand the computation of the cosine, first note that the
+     298             :                 //  cosine is periodic and we thus only need to model its behavior
+     299             :                 //  between 0 and 2*pi to be able compute the function anywhere. In
+     300             :                 //  fact, by mirroring the function along the x and y axes, even the
+     301             :                 //  range between 0 and pi/2 is sufficient for this purpose. In this
+     302             :                 //  range, the cosine can be efficiently evaluated with high precision
+     303             :                 //  by using a polynomial approximation. Thus, to compute the cosine,
+     304             :                 //  the input value is first reduced so that it lies within this range.
+     305             :                 //  Then, the polynomial approximation is evaluated. Finally, if
+     306             :                 //  necessary, the sign of the result is flipped (mirroring the function
+     307             :                 //  along the x axis).
+     308             :                 //
+     309             :                 //  The actual computation is slightly more involved. First, argument
+     310             :                 //  reduction can be simplified drastically by computing cos(pi*x),
+     311             :                 //  such that the values are reduced to the range [0, 0.5) instead of
+     312             :                 //  [0, pi/2). Since the cosine is even (independent of the sign), we
+     313             :                 //  can first reduce values to [-0.5, 0.5) – that is, a simple rounding
+     314             :                 //  operation – and then neutralize the sign. In fact, precisely because
+     315             :                 //  the cosine is even, all terms of the polynomial are powers of x^2,
+     316             :                 //  so the value of x^2 (computed as x*x) forms the basis for the
+     317             :                 //  polynomial approximation. If I understand things correctly, then (in
+     318             :                 //  IEEE-754 floating point) x*x and (-x)*(-x) will always result in the
+     319             :                 //  exact same value, which means that any error bound over [0, 0.5)
+     320             :                 //  automatically applies to (-0.5, 0] as well.
+     321             : 
+     322             :                 // First, compute round(x), and store it in q. If this value is odd,
+     323             :                 // we're looking at the negative half-wave of the cosine, and thus
+     324             :                 // will have to invert the sign of the result.
+     325             :                 __m256d q = _mm256_round_pd(
+     326             :                     cos_arg, (_MM_FROUND_TO_NEAREST_INT | _MM_FROUND_NO_EXC));
+     327             : 
+     328             :                 // Since we're computing cos(pi*x), round(x) always yields the center of
+     329             :                 // a half-wave (where cos(pi*x) achieves an extremum). This point
+     330             :                 // logically corresponds to x=0. Therefore, we subtract this center from
+     331             :                 // the actual input argument to find the corresponding point on the
+     332             :                 // half-wave that is centered around zero.
+     333             :                 __m256d s = _mm256_sub_pd(cos_arg, q);
+     334             : 
+     335             :                 // We now want to check whether q (the index of our half-wave) is even
+     336             :                 // or odd, since all of the odd-numbered half-waves are negative, so
+     337             :                 // we'll have to flip the final result. On an int, this is as simple as
+     338             :                 // checking the 0th bit. Idea: manipulate the double in such a way that
+     339             :                 // we can do this. So, we add 2^52, such that the last digit of the
+     340             :                 // mantissa is actually in the ones' position. Since q may be negative,
+     341             :                 // we'll also add 2^51 to make sure it's positive. Note that 2^51 is
+     342             :                 // even and thus leaves evenness invariant, which is the only thing we
+     343             :                 // care about here.
+     344             :                 //
+     345             :                 // This is based on the int extraction process described here:
+     346             :                 // https://stackoverflow.com/questions/41144668/how-to-efficiently-perform-double-int64-conversions-with-sse-avx/41223013
+     347             :                 //
+     348             :                 // We assume -2^51 <= q < 2^51 for this, which is unproblematic, as
+     349             :                 // double precision has decayed far enough at that point that the
+     350             :                 // usefulness of the cosine becomes limited.
+     351             :                 //
+     352             :                 // Explanation: The mantissa of a double-precision float has 52 bits
+     353             :                 // (excluding the implicit first bit, which is always one). If |q| >
+     354             :                 // 2^51, this implicit first bit has a place value of at least 2^51,
+     355             :                 // while the first stored bit of the mantissa has a place value of at
+     356             :                 // least 2^50. This means that the LSB of the mantissa has a place value
+     357             :                 // of at least 2^(-1), or 0.5. For a cos(pi*x), this corresponds to a
+     358             :                 // quarter of a cycle (pi/2), so at this point the precision of the
+     359             :                 // input argument is so low that going from one representable number to
+     360             :                 // the next causes the result to jump by +/-1.
+     361             : 
+     362             :                 q = _mm256_add_pd(q, _mm256_set1_pd(0x0018000000000000));
+     363             : 
+     364             :                 // Unfortunately, integer comparisons were only introduced in AVX2, so
+     365             :                 // we'll have to make do with a floating point comparison to check
+     366             :                 // whether the last bit is set. However, masking out all but the last
+     367             :                 // bit will result in a denormal float, which may either result in
+     368             :                 // performance problems or just be rounded down to zero, neither of
+     369             :                 // which is what we want here. To fix this, we'll mask in not only bit
+     370             :                 // 0, but also the exponent (and sign, but that doesn't matter) of q.
+     371             :                 // Luckily, the exponent of q is guaranteed to have the fixed value of
+     372             :                 // 1075 (corresponding to 2^52) after our addition.
+     373             : 
+     374             :                 __m256d invert = _mm256_and_pd(
+     375             :                     q, _mm256_castsi256_pd(_mm256_set1_epi64x(0xfff0000000000001)));
+     376             : 
+     377             :                 // If we did have a one in bit 0, our result will be equal to 2^52 + 1.
+     378             :                 invert = _mm256_cmp_pd(
+     379             :                     invert, _mm256_castsi256_pd(_mm256_set1_epi64x(0x4330000000000001)),
+     380             :                     _CMP_EQ_OQ);
+     381             : 
+     382             :                 // Now we know whether to flip the sign of the result. However, remember
+     383             :                 // that we're working on multiple values at a time, so an if statement
+     384             :                 // won't be of much use here (plus it might perform badly). Instead,
+     385             :                 // we'll make use of the fact that the result of the comparison is all
+     386             :                 // ones if the comparison was true (i.e. q is odd and we need to flip
+     387             :                 // the result), and all zeroes otherwise. If we now mask out all bits
+     388             :                 // except the sign bit, we get something that, when xor'ed into our
+     389             :                 // final result, will flip the sign exactly when q is odd.
+     390             :                 invert = _mm256_and_pd(invert, _mm256_set1_pd(-0.0));
+     391             :                 // (Note that the binary representation of -0.0 is all 0 bits, except
+     392             :                 // for the sign bit, which is set to 1.)
+     393             : 
+     394             :                 // TODO: clamp floats between 0 and 1? This would ensure that we never
+     395             :                 // see inf's, but maybe we want that, so that things dont just fail
+     396             :                 // silently...
+     397             : 
+     398             :                 // * end of argument reduction
+     399             :                 // *******
+     400             : 
+     401             :                 // ******
+     402             :                 // * Evaluate the cosine using a polynomial approximation for the zeroth
+     403             :                 // half-wave.
+     404             :                 // * The coefficients for this were generated using sleefs gencoef.c.
+     405             :                 // * These coefficients are probably far from optimal; however, they
+     406             :                 // should be sufficient for this case.
+     407             :                 s = _mm256_mul_pd(s, s);
+     408             : 
+     409             :                 __m256d u = _mm256_set1_pd(+0.2211852080653743946e+0);
+     410             : 
+     411             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s),
+     412             :                                   _mm256_set1_pd(-0.1332560668688523853e+1));
+     413             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s),
+     414             :                                   _mm256_set1_pd(+0.4058509506474178075e+1));
+     415             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s),
+     416             :                                   _mm256_set1_pd(-0.4934797516664651162e+1));
+     417             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s), _mm256_set1_pd(1.));
+     418             : 
+     419             :                 // Then, flip the sign of each double for which invert is not zero.
+     420             :                 // Since invert has only zero bits except for a possible one in bit 63,
+     421             :                 // we can xor it onto our result to selectively invert the 63rd (sign)
+     422             :                 // bit in each double where invert is set.
+     423             :                 u = _mm256_xor_pd(u, invert);
+     424             : 
+     425             :                 // * end computation of cosine
+     426             :                 // **********
+     427             : 
+     428             :                 // Finally, Ak*xi is multiplied on. Since this is a vector, the
+     429             :                 // multiplication needs to be done for each of the three
+     430             :                 // components, so it happens separately.
+     431             :                 acc0 = _mm256_add_pd(_mm256_mul_pd(u, Axi0), acc0);
+     432             :                 acc1 = _mm256_add_pd(_mm256_mul_pd(u, Axi1), acc1);
+     433             :                 acc2 = _mm256_add_pd(_mm256_mul_pd(u, Axi2), acc2);
+     434             :         }
+     435             : 
+     436             :         return Vector3d(hsum_double_avx(acc0), hsum_double_avx(acc1),
+     437             :                         hsum_double_avx(acc2));
+     438             : #endif // ENABLE_FAST_WAVES
+     439             : }
+     440             : 
+     441             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html new file mode 100644 index 000000000..02289b77c --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/SimpleGridTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - SimpleGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5252100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SimpleGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEj3
_ZN7crpropa20SimpleGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi7
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html new file mode 100644 index 000000000..55d106e43 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/SimpleGridTurbulence.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - SimpleGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5252100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SimpleGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi7
_ZN7crpropa20SimpleGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEj3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html new file mode 100644 index 000000000..a0b831617 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html @@ -0,0 +1,193 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField/SimpleGridTurbulence.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentField - SimpleGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5252100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
+       2             : #include "crpropa/GridTools.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #ifdef CRPROPA_HAVE_FFTW3F
+       6             : #include "fftw3.h"
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10           3 : SimpleGridTurbulence::SimpleGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
+      11             :                                            const GridProperties &gridProp,
+      12           3 :                                            unsigned int seed)
+      13           3 :     : GridTurbulence(spectrum, gridProp, seed) {
+      14           6 :         initTurbulence(gridPtr, spectrum.getBrms(), spectrum.getLmin(),
+      15           3 :                        spectrum.getLmax(), -spectrum.getSindex() - 2, seed);
+      16           3 : }
+      17             : 
+      18           7 : void SimpleGridTurbulence::initTurbulence(ref_ptr<Grid3f> grid, double Brms,
+      19             :                                           double lMin, double lMax,
+      20             :                                           double alpha, int seed) {
+      21             :         
+      22             :         Vector3d spacing = grid->getSpacing();
+      23             : 
+      24          11 :         checkGridRequirements(grid, lMin, lMax);
+      25             : 
+      26             :         size_t n = grid->getNx(); // size of array
+      27           4 :         size_t n2 = (size_t)floor(n / 2) +
+      28             :                     1; // size array in z-direction in configuration space
+      29             : 
+      30             :         // arrays to hold the complex vector components of the B(k)-field
+      31             :         fftwf_complex *Bkx, *Bky, *Bkz;
+      32           4 :         Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      33           4 :         Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      34           4 :         Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
+      35             : 
+      36           4 :         Random random;
+      37           4 :         if (seed != 0)
+      38           2 :                 random.seed(seed); // use given seed
+      39             : 
+      40             :         // calculate the n possible discrete wave numbers
+      41           4 :         double K[n];
+      42         260 :         for (size_t i = 0; i < n; i++)
+      43         256 :                 K[i] = (double)i / n - i / (n / 2);
+      44             : 
+      45           4 :         double kMin = spacing.x / lMax;
+      46           4 :         double kMax = spacing.x / lMin;
+      47             :         Vector3f n0(1, 1, 1); // arbitrary vector to construct orthogonal base
+      48             : 
+      49         260 :         for (size_t ix = 0; ix < n; ix++) {
+      50       16640 :                 for (size_t iy = 0; iy < n; iy++) {
+      51      557056 :                         for (size_t iz = 0; iz < n2; iz++) {
+      52             :         
+      53             :                                 Vector3f ek, e1, e2;  // orthogonal base
+      54             : 
+      55      540672 :                                 size_t i = ix * n * n2 + iy * n2 + iz;
+      56      540672 :                                 ek.setXYZ(K[ix], K[iy], K[iz]);
+      57      540672 :                                 double k = ek.getR();
+      58             : 
+      59             :                                 // wave outside of turbulent range -> B(k) = 0
+      60      540672 :                                 if ((k < kMin) || (k > kMax)) {
+      61      264724 :                                         Bkx[i][0] = 0;
+      62      264724 :                                         Bkx[i][1] = 0;
+      63      264724 :                                         Bky[i][0] = 0;
+      64      264724 :                                         Bky[i][1] = 0;
+      65      264724 :                                         Bkz[i][0] = 0;
+      66      264724 :                                         Bkz[i][1] = 0;
+      67             :                                         continue;
+      68             :                                 }
+      69             : 
+      70             :                                 // construct an orthogonal base ek, e1, e2
+      71      275948 :                                 if (ek.isParallelTo(n0, float(1e-3))) {
+      72             :                                         // ek parallel to (1,1,1)
+      73             :                                         e1.setXYZ(-1., 1., 0);
+      74             :                                         e2.setXYZ(1., 1., -2.);
+      75             :                                 } else {
+      76             :                                         // ek not parallel to (1,1,1)
+      77             :                                         e1 = n0.cross(ek);
+      78             :                                         e2 = ek.cross(e1);
+      79             :                                 }
+      80             :                                 e1 /= e1.getR();
+      81             :                                 e2 /= e2.getR();
+      82             : 
+      83             :                                 // random orientation perpendicular to k
+      84      275948 :                                 double theta = 2 * M_PI * random.rand();
+      85      275948 :                                 Vector3f b = e1 * cos(theta) + e2 * sin(theta); // real b-field vector
+      86             : 
+      87             :                                 // normal distributed amplitude with mean = 0 and sigma =
+      88             :                                 // k^alpha/2
+      89      275948 :                                 b *= random.randNorm() * pow(k, alpha / 2);
+      90             : 
+      91             :                                 // uniform random phase
+      92      275948 :                                 double phase = 2 * M_PI * random.rand();
+      93      275948 :                                 double cosPhase = cos(phase); // real part
+      94      275948 :                                 double sinPhase = sin(phase); // imaginary part
+      95             : 
+      96      275948 :                                 Bkx[i][0] = b.x * cosPhase;
+      97      275948 :                                 Bkx[i][1] = b.x * sinPhase;
+      98      275948 :                                 Bky[i][0] = b.y * cosPhase;
+      99      275948 :                                 Bky[i][1] = b.y * sinPhase;
+     100      275948 :                                 Bkz[i][0] = b.z * cosPhase;
+     101      275948 :                                 Bkz[i][1] = b.z * sinPhase;
+     102             :                         } // for iz
+     103             :                 }     // for iy
+     104             :         }         // for ix
+     105             : 
+     106           4 :         executeInverseFFTInplace(grid, Bkx, Bky, Bkz);
+     107             : 
+     108           4 :         fftwf_free(Bkx);
+     109           4 :         fftwf_free(Bky);
+     110           4 :         fftwf_free(Bkz);
+     111             : 
+     112          16 :         scaleGrid(grid, Brms / rmsFieldStrength(grid)); // normalize to Brms
+     113          11 : }
+     114             : 
+     115             : } // namespace crpropa
+     116             : 
+     117             : #endif // CRPROPA_HAVE_FFTW3F
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html b/doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html new file mode 100644 index 000000000..4bb56e51d --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:18726371.1 %
Date:2024-04-08 14:58:22Functions:111957.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.cpp +
0.0%
+
0.0 %0 / 590.0 %0 / 2
GridTurbulence.cpp +
85.6%85.6%
+
85.6 %89 / 10453.8 %7 / 13
SimpleGridTurbulence.cpp +
100.0%
+
100.0 %52 / 52100.0 %2 / 2
PlaneWaveTurbulence.cpp +
95.8%95.8%
+
95.8 %46 / 48100.0 %2 / 2
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html b/doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html new file mode 100644 index 000000000..1a7102ae5 --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:18726371.1 %
Date:2024-04-08 14:58:22Functions:111957.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.cpp +
0.0%
+
0.0 %0 / 590.0 %0 / 2
GridTurbulence.cpp +
85.6%85.6%
+
85.6 %89 / 10453.8 %7 / 13
PlaneWaveTurbulence.cpp +
95.8%95.8%
+
95.8 %46 / 48100.0 %2 / 2
SimpleGridTurbulence.cpp +
100.0%
+
100.0 %52 / 52100.0 %2 / 2
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticField/turbulentField/index.html b/doc/coverageReport/src/magneticField/turbulentField/index.html new file mode 100644 index 000000000..2bfdfdefa --- /dev/null +++ b/doc/coverageReport/src/magneticField/turbulentField/index.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticField/turbulentField + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:18726371.1 %
Date:2024-04-08 14:58:22Functions:111957.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
GridTurbulence.cpp +
85.6%85.6%
+
85.6 %89 / 10453.8 %7 / 13
HelicalGridTurbulence.cpp +
0.0%
+
0.0 %0 / 590.0 %0 / 2
PlaneWaveTurbulence.cpp +
95.8%95.8%
+
95.8 %46 / 48100.0 %2 / 2
SimpleGridTurbulence.cpp +
100.0%
+
100.0 %52 / 52100.0 %2 / 2
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html new file mode 100644 index 000000000..6962e0d0c --- /dev/null +++ b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/MagneticLens.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - MagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4310441.3 %
Date:2024-04-08 14:58:22Functions:61346.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLens12loadLensPartERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd0
_ZN7crpropa12MagneticLens13normalizeLensEv0
_ZN7crpropa12MagneticLens18normalizeLenspartsEv0
_ZN7crpropa12MagneticLens22normalizeMatrixColumnsEv0
_ZN7crpropa12MagneticLens8loadLensERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa12MagneticLens15rigidityCoveredEd0
_ZNK7crpropa12MagneticLens20transformModelVectorEPdd0
_ZN7crpropa12MagneticLens11setLensPartERKN5Eigen12SparseMatrixIdLi0EiEEdd3
_ZN7crpropa12MagneticLens12_checkMatrixERKN5Eigen12SparseMatrixIdLi0EiEE3
_ZN7crpropa12MagneticLens20updateRigidityBoundsEdd3
_ZN7crpropa12MagneticLens18transformCosmicRayEdRNS_7Vector3IdEE4
_ZN7crpropa12MagneticLens18transformCosmicRayEdRdS1_12293
_ZNK7crpropa12MagneticLens11getLensPartEd12293
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html new file mode 100644 index 000000000..291746429 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/MagneticLens.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - MagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4310441.3 %
Date:2024-04-08 14:58:22Functions:61346.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLens11setLensPartERKN5Eigen12SparseMatrixIdLi0EiEEdd3
_ZN7crpropa12MagneticLens12_checkMatrixERKN5Eigen12SparseMatrixIdLi0EiEE3
_ZN7crpropa12MagneticLens12loadLensPartERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd0
_ZN7crpropa12MagneticLens13normalizeLensEv0
_ZN7crpropa12MagneticLens18normalizeLenspartsEv0
_ZN7crpropa12MagneticLens18transformCosmicRayEdRNS_7Vector3IdEE4
_ZN7crpropa12MagneticLens18transformCosmicRayEdRdS1_12293
_ZN7crpropa12MagneticLens20updateRigidityBoundsEdd3
_ZN7crpropa12MagneticLens22normalizeMatrixColumnsEv0
_ZN7crpropa12MagneticLens8loadLensERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa12MagneticLens11getLensPartEd12293
_ZNK7crpropa12MagneticLens15rigidityCoveredEd0
_ZNK7crpropa12MagneticLens20transformModelVectorEPdd0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html new file mode 100644 index 000000000..88d65754f --- /dev/null +++ b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html @@ -0,0 +1,353 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/MagneticLens.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - MagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4310441.3 %
Date:2024-04-08 14:58:22Functions:61346.2 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : //----------------------------------------------------------------------
+       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
+       3             : // a parametrized simulation engine for cosmic rays.
+       4             : //
+       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
+       6             : //                     RWTH Aachen University, Germany
+       7             : // Contact: winchen@physik.rwth-aachen.de
+       8             : //
+       9             : //  This program is free software: you can redistribute it and/or
+      10             : //  modify it under the terms of the GNU General Public License as
+      11             : //  published by the Free Software Foundation, either version 3 of
+      12             : //  the License, or (at your option) any later version.
+      13             : //
+      14             : //  This program is distributed in the hope that it will be useful,
+      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      17             : //  GNU General Public License for more details.
+      18             : //
+      19             : //  You should have received a copy of the GNU General Public License
+      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
+      21             : //----------------------------------------------------------------------
+      22             : 
+      23             : #include "crpropa/magneticLens/MagneticLens.h"
+      24             : 
+      25             : #include "crpropa/Random.h"
+      26             : #include "crpropa/Units.h"
+      27             : 
+      28             : // needed for memcpy in gcc 4.3.2
+      29             : #include <cstring>
+      30             : 
+      31             : namespace crpropa 
+      32             : {
+      33             : 
+      34           0 : void MagneticLens::loadLens(const string &filename)
+      35             : {
+      36           0 :         ifstream infile(filename.c_str());
+      37           0 :         if (!infile)
+      38             :         {
+      39           0 :                 throw std::runtime_error("Can't read file: " + filename);
+      40             :         }
+      41             :         string line;
+      42             : 
+      43             :         string prefix;
+      44           0 :         int sp = filename.find_last_of("/");
+      45           0 :         if (sp >= 0)
+      46             :         {
+      47           0 :                 prefix = filename.substr(0, sp);
+      48           0 :                 prefix.append("/");
+      49             :         }
+      50             :         string mfdatfile;
+      51             :         double emin, emax;
+      52             : 
+      53             :         int lineCounter = 0;
+      54           0 :         while (!infile.eof())
+      55             :         {
+      56           0 :                 getline(infile, line);
+      57           0 :                 lineCounter++;
+      58           0 :                 if (line.find('#') == string::npos)
+      59             :                 {
+      60           0 :                         stringstream ss;
+      61             :                         ss << line;
+      62           0 :                         ss >> mfdatfile >> emin >> emax;
+      63           0 :                         if (ss.fail())
+      64             :                         {
+      65           0 :                                 cerr << "WARNING! Cannot read line " << lineCounter << " of file " << filename << " :\n [" << lineCounter << " ]: " << line << " \n";
+      66           0 :                                 cerr << " ... Skipping line and continue\n";
+      67             :                         }
+      68             :                         else
+      69             :                         {
+      70           0 :                                 this->loadLensPart(prefix + mfdatfile, pow(10, emin) * eV, pow(10, emax) * eV);
+      71             :                         }
+      72           0 :                 }
+      73             :         }
+      74           0 : }
+      75             : 
+      76       12293 : bool MagneticLens::transformCosmicRay(double rigidity, double& phi,
+      77             :                 double& theta) 
+      78             : {
+      79       12293 :         uint32_t c = _pixelization->direction2Pix(phi, theta);
+      80       12293 :         LensPart *lenspart = getLensPart(rigidity);
+      81       12293 :         if (!lenspart)
+      82             :         {
+      83           1 :                 std::cerr << "Warning. Trying to transform cosmic ray with rigidity " << rigidity / eV << " eV which is not covered by this lens!.\n";
+      84           2 :                 std::cerr << " This lens covers the range " << _minimumRigidity /eV << " eV - " << _maximumRigidity << " eV.\n";
+      85           1 :                 return false;
+      86             :         }
+      87             : 
+      88       12292 :         ModelVectorType v = lenspart->getMatrix().col(c);
+      89             : 
+      90             :         uint32_t r;
+      91             : 
+      92             :         // the random number to compare with
+      93       12292 :         double rn = Random::instance().rand();
+      94             : 
+      95             :         ModelVectorType::InnerIterator i(v);
+      96             :   double cpv = 0;
+      97       12292 :   while (i)
+      98             :   {
+      99       12292 :                 cpv += i.value();
+     100       12292 :                 if (rn < cpv)
+     101             :                 {
+     102       12292 :                         _pixelization->pix2Direction(i.index(), phi, theta);
+     103             :                         return true;
+     104             :     }
+     105             :     else
+     106             :     {
+     107             :                         ++i;
+     108             :     }
+     109             :    }
+     110             :   return false;
+     111             : }
+     112             : 
+     113           4 : bool MagneticLens::transformCosmicRay(double rigidity, Vector3d &p){
+     114             : 
+     115           4 :                         double galacticLongitude = atan2(-p.y, -p.x);
+     116           4 :                         double galacticLatitude =       M_PI / 2 - acos(-p.z/ sqrt(p.x*p.x + p.y*p.y + p.z*p.z));
+     117           4 :                         bool result = transformCosmicRay(rigidity, galacticLongitude, galacticLatitude);
+     118             :                         
+     119           4 :                         p.x = -1 * cos(galacticLongitude) * sin(M_PI / 2 - galacticLatitude);
+     120           4 :                         p.y = -1 * sin(galacticLongitude) * sin(M_PI / 2 - galacticLatitude);
+     121           4 :                         p.z = -1. * cos(M_PI / 2 - galacticLatitude);
+     122             : 
+     123           4 :                         return result;
+     124             : }
+     125             : 
+     126           0 : void MagneticLens::loadLensPart(const string &filename, double rigidityMin,
+     127             :                 double rigidityMax)
+     128             : {
+     129           0 :         updateRigidityBounds(rigidityMin, rigidityMax);
+     130             : 
+     131           0 :         LensPart *p = new LensPart(filename, rigidityMin, rigidityMax);
+     132             :         p->loadMatrixFromFile();
+     133           0 :         _checkMatrix(p->getMatrix());
+     134             : 
+     135           0 :         _lensParts.push_back(p);
+     136           0 : }
+     137             : 
+     138           3 : void MagneticLens::_checkMatrix(const ModelMatrixType &M)
+     139             : {
+     140           3 :         if (M.rows() != M.cols())
+     141             :         {
+     142           0 :                 throw std::runtime_error("Not a square Matrix!");
+     143             :         }
+     144             : 
+     145           3 :         if (_pixelization)
+     146             :         {
+     147           3 :                 if (_pixelization->nPix() != M.cols())
+     148             :                 {
+     149             :                         std::cerr << "*** ERROR ***" << endl;
+     150           0 :                         std::cerr << "  Pixelization: " << _pixelization->nPix() << endl;
+     151             :                         std::cerr << "  Matrix Size : " << M.cols() << endl;
+     152           0 :                         throw std::runtime_error("Matrix doesn't fit into Lense");
+     153             :                 }
+     154             :         }
+     155             :         else
+     156             :         {
+     157           0 :                 uint32_t morder = Pixelization::pix2Order(M.cols());
+     158           0 :                 if (morder == 0)
+     159             :                 {
+     160           0 :                         throw std::runtime_error(
+     161           0 :                                         "Matrix size doesn't match healpix scheme!");
+     162             :                 }
+     163           0 :                 _pixelization = new Pixelization(morder);
+     164             :         }
+     165           3 : }
+     166             : 
+     167           3 : void MagneticLens::updateRigidityBounds(double rigidityMin, double rigidityMax)
+     168             : {
+     169           3 :         if (rigidityMin >= rigidityMax)
+     170             :         {
+     171           0 :                 throw std::runtime_error("rigidityMin >= rigidityMax");
+     172             :         }
+     173           3 :         if (rigidityMin < _minimumRigidity)
+     174             :         {
+     175           3 :                 _minimumRigidity = rigidityMin;
+     176             :         }
+     177             : 
+     178           3 :         if (_maximumRigidity < rigidityMin)
+     179             :         {
+     180           3 :                 _maximumRigidity = rigidityMax;
+     181             :         }
+     182           3 : }
+     183             : 
+     184           3 : void MagneticLens::setLensPart(const ModelMatrixType &M, double rigidityMin,
+     185             :                 double rigidityMax)
+     186             : {
+     187           3 :         updateRigidityBounds(rigidityMin, rigidityMax);
+     188           3 :         LensPart *p = new LensPart("Direct Input", rigidityMin, rigidityMax);
+     189             : 
+     190             :         p->setMatrix(M);
+     191             : 
+     192           3 :         _checkMatrix(p->getMatrix());
+     193           3 :         _lensParts.push_back(p);
+     194           3 : }
+     195             : 
+     196       12293 : LensPart* MagneticLens::getLensPart(double rigidity) const
+     197             : {
+     198             :         const_LensPartIter i = _lensParts.begin();
+     199       12294 :         while (i != _lensParts.end())
+     200             :         {
+     201       12293 :                 if (((*i)->getMinimumRigidity() < rigidity / eV)
+     202       12293 :                                 && ((*i)->getMaximumRigidity() >= rigidity / eV))
+     203             :                 {
+     204             :                         return (*i);
+     205             :                 }
+     206             :                 ++i;
+     207             :         }
+     208             :         return NULL;
+     209             : }
+     210             : 
+     211           0 : bool MagneticLens::rigidityCovered(double rigidity) const
+     212             : {
+     213           0 :         if (getLensPart(rigidity))
+     214             :                 return true;
+     215             :         else
+     216           0 :                 return false;
+     217             : }
+     218             : 
+     219             : 
+     220           0 : void MagneticLens::normalizeMatrixColumns()
+     221             : {
+     222           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
+     223             :                         ++iter)
+     224             :         {
+     225           0 :                 normalizeColumns((*iter)->getMatrix());
+     226             :         }
+     227           0 : }
+     228             : 
+     229             : 
+     230           0 : void MagneticLens::normalizeLens()
+     231             : {
+     232             :         // get maximum of sums of columns, and normalize each matrix to that
+     233             :         double norm = 0;
+     234           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
+     235             :                         ++iter)
+     236             :         {
+     237           0 :                 if ((*iter)->getMaximumOfSumsOfColumns() > norm)
+     238             :                 {
+     239           0 :                         norm = (*iter)->getMaximumOfSumsOfColumns();
+     240             :                 }
+     241             :         }
+     242           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
+     243             :                         ++iter)
+     244             :         {
+     245           0 :                 normalizeMatrix((*iter)->getMatrix(), norm);
+     246             :         }
+     247           0 :   _norm = norm;
+     248           0 : }
+     249             : 
+     250           0 : void MagneticLens::normalizeLensparts()
+     251             : {
+     252           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
+     253             :                         ++iter)
+     254             :         {
+     255           0 :                 double norm = (*iter)->getMaximumOfSumsOfColumns();
+     256           0 :                 normalizeMatrix((*iter)->getMatrix(), norm);
+     257             :         }
+     258           0 : }
+     259             : 
+     260           0 : void MagneticLens::transformModelVector(double* model, double rigidity) const
+     261             : {
+     262           0 :         LensPart* lenspart = getLensPart(rigidity);
+     263             :         
+     264           0 :         if (!lenspart)
+     265             :         {
+     266           0 :                 std::cerr << "Warning. Trying to transform vector with rigidity " << rigidity / eV << "eV which is not covered by this lens!.\n" << std::endl;
+     267           0 :                 return;
+     268             :         }
+     269             : 
+     270           0 :         prod_up(lenspart->getMatrix(), model);
+     271             : 
+     272             : }
+     273             : 
+     274             : 
+     275             : 
+     276             : } // namespace parsec
+     277             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html new file mode 100644 index 000000000..0b636302b --- /dev/null +++ b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/ModelMatrix.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - ModelMatrix.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11deserializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa15normalizeMatrixERN5Eigen12SparseMatrixIdLi0EiEEd0
_ZN7crpropa16normalizeColumnsERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa22maximumOfSumsOfColumnsERKN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa6norm_1ERKN5Eigen12SparseVectorIdLi0EiEE0
_ZN7crpropa7prod_upERKN5Eigen12SparseMatrixIdLi0EiEEPd0
_ZN7crpropa9serializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKN5Eigen12SparseMatrixIdLi0EiEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html new file mode 100644 index 000000000..9869c0266 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/ModelMatrix.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - ModelMatrix.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11deserializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa15normalizeMatrixERN5Eigen12SparseMatrixIdLi0EiEEd0
_ZN7crpropa16normalizeColumnsERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa22maximumOfSumsOfColumnsERKN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa6norm_1ERKN5Eigen12SparseVectorIdLi0EiEE0
_ZN7crpropa7prod_upERKN5Eigen12SparseMatrixIdLi0EiEEPd0
_ZN7crpropa9serializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKN5Eigen12SparseMatrixIdLi0EiEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html new file mode 100644 index 000000000..e0c22d95b --- /dev/null +++ b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html @@ -0,0 +1,237 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/ModelMatrix.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - ModelMatrix.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : //----------------------------------------------------------------------
+       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
+       3             : // a parametrized simulation engine for cosmic rays.
+       4             : //
+       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
+       6             : //                     RWTH Aachen University, Germany
+       7             : // Contact: winchen@physik.rwth-aachen.de
+       8             : //
+       9             : //  This program is free software: you can redistribute it and/or
+      10             : //  modify it under the terms of the GNU General Public License as
+      11             : //  published by the Free Software Foundation, either version 3 of
+      12             : //  the License, or (at your option) any later version.
+      13             : //
+      14             : //  This program is distributed in the hope that it will be useful,
+      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      17             : //  GNU General Public License for more details.
+      18             : //
+      19             : //  You should have received a copy of the GNU General Public License
+      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
+      21             : //----------------------------------------------------------------------
+      22             : 
+      23             : #include "crpropa/magneticLens/ModelMatrix.h"
+      24             : #include <ctime>
+      25             : 
+      26             : #include <Eigen/Core>
+      27             : namespace crpropa 
+      28             : {
+      29             : 
+      30           0 : void serialize(const string &filename, const ModelMatrixType& matrix)
+      31             : {
+      32           0 :         ofstream outfile(filename.c_str(), ios::binary);
+      33           0 :         if (!outfile)
+      34             :         {
+      35           0 :                 throw runtime_error("Can't write file: " + filename);
+      36             :         }
+      37             : 
+      38           0 :         uint32_t C = 0;
+      39             :         double val;
+      40             : 
+      41           0 :         C = (uint32_t) (matrix.nonZeros());
+      42           0 :         outfile.write((char*) &C, sizeof(uint32_t));
+      43           0 :         C = (uint32_t) (matrix.rows());
+      44           0 :         outfile.write((char*) &C, sizeof(uint32_t));
+      45           0 :         C = (uint32_t) (matrix.cols());
+      46           0 :         outfile.write((char*) &C, sizeof(uint32_t));
+      47             : 
+      48             :         // serialize non zero elements
+      49           0 :         for (size_t col_idx = 0; col_idx < matrix.cols(); ++col_idx)
+      50             :         {
+      51           0 :                 for (ModelMatrixType::InnerIterator it(matrix,col_idx); it; ++it)
+      52             :                         {
+      53             :                                 it.value();
+      54           0 :                                 C = (uint32_t) it.row();
+      55           0 :                                 outfile.write((char*) &C, sizeof(uint32_t));
+      56             : 
+      57           0 :                                 C = (uint32_t) it.col();
+      58           0 :                                 outfile.write((char*) &C, sizeof(uint32_t));
+      59             : 
+      60           0 :                                 val = it.value();
+      61           0 :                                 outfile.write((char*) &val, sizeof(double));
+      62           0 :                                 if (outfile.fail())
+      63             :                                 {
+      64           0 :                                         throw runtime_error("Error writing file: " + filename);
+      65             :                                 }
+      66             :                         }
+      67             :         }
+      68             : 
+      69           0 :         outfile.close();
+      70           0 : }
+      71             : 
+      72             : 
+      73           0 : void deserialize(const string &filename, ModelMatrixType& matrix)
+      74             : {
+      75           0 :         ifstream infile(filename.c_str(), ios::binary);
+      76           0 :         if (!infile)
+      77             :         {
+      78           0 :                 throw runtime_error("Can't read file: " + filename);
+      79             :         }
+      80             : 
+      81             :         uint32_t nnz, nRows, nColumns;
+      82           0 :         infile.read((char*) &nnz, sizeof(uint32_t));
+      83           0 :         infile.read((char*) &nRows, sizeof(uint32_t));
+      84           0 :         infile.read((char*) &nColumns, sizeof(uint32_t));
+      85           0 :         matrix.resize(nRows, nColumns);
+      86           0 :         matrix.reserve(nnz);
+      87             : 
+      88             :         uint32_t row, column;
+      89             :         double val;
+      90             :         std::vector< Eigen::Triplet<double> > triplets;
+      91           0 :         triplets.resize(nnz);
+      92           0 :         for (size_t i = 0; i < nnz; i++)
+      93             :         {
+      94           0 :                 infile.read((char*) &row, sizeof(uint32_t));
+      95           0 :                 infile.read((char*) &column, sizeof(uint32_t));
+      96           0 :                 infile.read((char*) &val, sizeof(double));
+      97             :                 //M(size1,size2) = val;
+      98           0 :                 triplets[i] = Eigen::Triplet<double>(row, column, val);
+      99             :         }
+     100           0 :         matrix.setFromTriplets(triplets.begin(), triplets.end());
+     101           0 :         matrix.makeCompressed();
+     102           0 : }
+     103             : 
+     104             : 
+     105           0 : double norm_1(const ModelVectorType &v)
+     106             : {
+     107           0 :         return v.cwiseAbs().sum();
+     108             : }
+     109             : 
+     110             : 
+     111           0 : void normalizeColumns(ModelMatrixType &matrix){
+     112           0 :         for (size_t i=0; i< matrix.cols(); i++)
+     113             :         {
+     114           0 :                 ModelVectorType v = matrix.col(i);
+     115           0 :                 double rn = norm_1(v);
+     116           0 :                 matrix.col(i) = v/rn;
+     117             :         }
+     118           0 : }
+     119             : 
+     120             : 
+     121           0 : double maximumOfSumsOfColumns(const ModelMatrixType &matrix) 
+     122             : {
+     123             :         double summax = 0;
+     124           0 :         for (size_t i = 0; i < matrix.cols(); i++)
+     125             :         {
+     126           0 :                 double sum = matrix.col(i).sum();
+     127           0 :                 if (sum > summax)
+     128             :                         summax = sum;
+     129             :         }
+     130           0 :         return summax;
+     131             : }
+     132             : 
+     133           0 :         void normalizeMatrix(ModelMatrixType& matrix, double norm)
+     134             : {
+     135           0 :         matrix /= norm;
+     136           0 : }
+     137             : 
+     138           0 :         void prod_up(const ModelMatrixType& matrix, double* model)
+     139             : {
+     140             : 
+     141             :         // copy storage of model, as matrix vector product cannot be done
+     142             :         // in place
+     143             :         
+     144           0 :         const size_t mSize = matrix.cols();
+     145           0 :         double *origVectorStorage = new double[mSize];
+     146             :         memcpy(origVectorStorage, model, mSize * sizeof(double));
+     147             : 
+     148             : 
+     149             : 
+     150             :         Eigen::Map<Eigen::Matrix<double, Eigen::Dynamic, 1> > origVectorAdaptor(origVectorStorage, mSize);
+     151             :         Eigen::Map<Eigen::Matrix<double, Eigen::Dynamic, 1> > modelVectorAdaptor(model, mSize);
+     152             : 
+     153             :         // perform the optimized product
+     154           0 :         modelVectorAdaptor = matrix * origVectorAdaptor;
+     155             : 
+     156             :         // clean up
+     157           0 :         delete[] origVectorStorage;
+     158           0 : }
+     159             : 
+     160             : 
+     161             : } // namespace parsec
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html new file mode 100644 index 000000000..20670889d --- /dev/null +++ b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/ParticleMapsContainer.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - ParticleMapsContainer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7410570.5 %
Date:2024-04-08 14:58:22Functions:91369.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer11addParticleEidRKNS_7Vector3IdEEd0
_ZN7crpropa21ParticleMapsContainer17forceWeightUpdateEv0
_ZN7crpropa21ParticleMapsContainer6getMapEid0
_ZN7crpropa21ParticleMapsContainer9applyLensERNS_12MagneticLensE0
_ZN7crpropa21ParticleMapsContainer11getEnergiesEi1
_ZN7crpropa21ParticleMapsContainer14getParticleIdsEv1
_ZN7crpropa21ParticleMapsContainer18getRandomParticlesEmRSt6vectorIiSaIiEERS1_IdSaIdEES7_S7_1
_ZN7crpropa21ParticleMapsContainer11addParticleEidddd2
_ZN7crpropa21ParticleMapsContainerD2Ev2
_ZN7crpropa21ParticleMapsContainer10placeOnMapEidRdS1_420
_ZN7crpropa21ParticleMapsContainer14_updateWeightsEv421
_ZNK7crpropa21ParticleMapsContainer10idx2EnergyEi421
_ZNK7crpropa21ParticleMapsContainer10energy2IdxEd422
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html new file mode 100644 index 000000000..fec3680af --- /dev/null +++ b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/ParticleMapsContainer.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - ParticleMapsContainer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7410570.5 %
Date:2024-04-08 14:58:22Functions:91369.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer10placeOnMapEidRdS1_420
_ZN7crpropa21ParticleMapsContainer11addParticleEidRKNS_7Vector3IdEEd0
_ZN7crpropa21ParticleMapsContainer11addParticleEidddd2
_ZN7crpropa21ParticleMapsContainer11getEnergiesEi1
_ZN7crpropa21ParticleMapsContainer14_updateWeightsEv421
_ZN7crpropa21ParticleMapsContainer14getParticleIdsEv1
_ZN7crpropa21ParticleMapsContainer17forceWeightUpdateEv0
_ZN7crpropa21ParticleMapsContainer18getRandomParticlesEmRSt6vectorIiSaIiEERS1_IdSaIdEES7_S7_1
_ZN7crpropa21ParticleMapsContainer6getMapEid0
_ZN7crpropa21ParticleMapsContainer9applyLensERNS_12MagneticLensE0
_ZN7crpropa21ParticleMapsContainerD2Ev2
_ZNK7crpropa21ParticleMapsContainer10energy2IdxEd422
_ZNK7crpropa21ParticleMapsContainer10idx2EnergyEi421
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html new file mode 100644 index 000000000..58e7fc9e5 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html @@ -0,0 +1,275 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/ParticleMapsContainer.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - ParticleMapsContainer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7410570.5 %
Date:2024-04-08 14:58:22Functions:91369.2 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "HepPID/ParticleIDMethods.hh"
+       2             : #include "crpropa/Random.h"
+       3             : #include "crpropa/magneticLens/ParticleMapsContainer.h"
+       4             : #include "crpropa/Units.h"
+       5             : 
+       6             : #include <iostream>
+       7             : #include <fstream>
+       8             : 
+       9             : namespace crpropa  {
+      10             : 
+      11           2 : ParticleMapsContainer::~ParticleMapsContainer() {
+      12           2 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
+      13           4 :                         pid_iter != _data.end(); ++pid_iter) {
+      14           2 :                 for(std::map<int, double*>::iterator energy_iter = pid_iter->second.begin();
+      15           4 :                         energy_iter != pid_iter->second.end(); ++energy_iter) {
+      16           2 :                         delete[] (energy_iter->second);
+      17             :                 }
+      18             :         }
+      19           2 : }
+      20             : 
+      21         422 : int ParticleMapsContainer::energy2Idx(double energy) const {
+      22         422 :         double lE = log10(energy / eV);
+      23         422 :         return int((lE - _bin0lowerEdge) / _deltaLogE);
+      24             : }
+      25             : 
+      26         421 : double ParticleMapsContainer::idx2Energy(int idx) const {
+      27         421 :         return pow(10, idx * _deltaLogE + _bin0lowerEdge + _deltaLogE / 2) * eV;
+      28             : }
+      29             : 
+      30             :                 
+      31           0 : double* ParticleMapsContainer::getMap(const int particleId, double energy) {
+      32           0 :         _weightsUpToDate = false;
+      33           0 :         if (_data.find(particleId) == _data.end()) {
+      34           0 :                 std::cerr << "No map for ParticleID " << particleId << std::endl;
+      35           0 :                 return NULL;
+      36             :         }
+      37           0 :         int energyIdx   = energy2Idx(energy);
+      38           0 :         if (_data[particleId].find(energyIdx) == _data[particleId].end()) {
+      39           0 :                 std::cerr << "No map for ParticleID and energy" << energy / eV << " eV" << std::endl;
+      40           0 :                 return NULL;
+      41             :         }
+      42           0 :         return _data[particleId][energy2Idx(energy)];
+      43             : }
+      44             :                         
+      45             :                         
+      46           2 : void ParticleMapsContainer::addParticle(const int particleId, double energy, double galacticLongitude, double galacticLatitude, double weight) {
+      47           2 :         _weightsUpToDate = false;
+      48           2 :         if (_data.find(particleId) == _data.end()) {
+      49             :                 map<int, double*> M;
+      50           2 :                 _data[particleId] = M;
+      51             :         }
+      52             : 
+      53           2 :         int energyIdx   = energy2Idx(energy);
+      54           4 :         if (_data[particleId].find(energyIdx) == _data[particleId].end()) {
+      55           2 :                 _data[particleId][energyIdx] = new double[_pixelization.getNumberOfPixels()];
+      56           2 :                 std::fill(_data[particleId][energyIdx], _data[particleId][energyIdx] + _pixelization.getNumberOfPixels(), 0);
+      57             :         }
+      58             : 
+      59           2 :         uint32_t pixel = _pixelization.direction2Pix(galacticLongitude, galacticLatitude);
+      60           2 :         _data[particleId][energyIdx][pixel] += weight;
+      61           2 : }
+      62             : 
+      63             : 
+      64           0 : void ParticleMapsContainer::addParticle(const int particleId, double energy, const Vector3d &p, double weight) {
+      65           0 :         double galacticLongitude = atan2(-p.y, -p.x);
+      66           0 :         double galacticLatitude =       M_PI / 2 - acos(-p.z / p.getR());
+      67           0 :         addParticle(particleId, energy, galacticLongitude, galacticLatitude, weight);
+      68           0 : }
+      69             : 
+      70             : 
+      71           1 : std::vector<int> ParticleMapsContainer::getParticleIds() {
+      72             :         std::vector<int> ids;
+      73           1 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
+      74           2 :                         pid_iter != _data.end(); ++pid_iter) {
+      75           1 :                 ids.push_back(pid_iter->first);
+      76             :         }
+      77           1 :         return ids;
+      78             : }
+      79             : 
+      80             : 
+      81           1 : std::vector<double> ParticleMapsContainer::getEnergies(int pid) {
+      82             :         std::vector<double> energies;
+      83           1 :         if (_data.find(pid) != _data.end()) {
+      84           1 :                 for(std::map<int, double*>::iterator iter = _data[pid].begin(); 
+      85           2 :                         iter != _data[pid].end(); ++iter) {
+      86           1 :                         energies.push_back( idx2Energy(iter->first) / eV );
+      87             :                 }
+      88             :         }
+      89           1 :         return energies;
+      90             : }
+      91             : 
+      92             : 
+      93           0 : void ParticleMapsContainer::applyLens(MagneticLens &lens) {
+      94             :         // if lens is normalized, this should not be necessary.
+      95           0 :         _weightsUpToDate = false;
+      96             : 
+      97           0 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
+      98           0 :                         pid_iter != _data.end(); ++pid_iter) {
+      99           0 :                 for(std::map<int, double*>::iterator energy_iter = pid_iter->second.begin();
+     100           0 :                         energy_iter != pid_iter->second.end(); ++energy_iter) {
+     101             :                         // transform only nuclei
+     102           0 :                         double energy = idx2Energy(energy_iter->first);
+     103           0 :                         int chargeNumber = HepPID::Z(pid_iter->first);
+     104           0 :                         if (chargeNumber != 0 && lens.rigidityCovered(energy / chargeNumber)) {
+     105           0 :                                 lens.transformModelVector(energy_iter->second, energy / chargeNumber);
+     106             :                         } else { // still normalize the vectors 
+     107           0 :                                 for(size_t j=0; j< _pixelization.getNumberOfPixels() ; j++) {
+     108           0 :                                         energy_iter->second[j] /= lens.getNorm();
+     109             :                                 }
+     110             :                         }
+     111             :                 }
+     112             :         }
+     113           0 : }
+     114             : 
+     115             : 
+     116         421 : void ParticleMapsContainer::_updateWeights() {
+     117         421 :         if (_weightsUpToDate)
+     118             :                 return;
+     119             : 
+     120           1 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
+     121           2 :                         pid_iter != _data.end(); ++pid_iter) {
+     122           1 :                 _weightsPID[pid_iter->first] = 0;
+     123             : 
+     124           1 :                 for(std::map<int, double*>::iterator energy_iter = pid_iter->second.begin();
+     125           2 :                         energy_iter != pid_iter->second.end(); ++energy_iter)  {
+     126             : 
+     127           1 :                         _weights_pidEnergy[pid_iter->first][energy_iter->first] = 0;
+     128       49153 :                         for(size_t j = 0; j< _pixelization.getNumberOfPixels() ; j++) {
+     129       49152 :                                 _weights_pidEnergy[pid_iter->first][energy_iter->first] +=energy_iter->second[j];
+     130       49152 :                                 _weightsPID[pid_iter->first]+=energy_iter->second[j];
+     131             :                         }
+     132           1 :                         _sumOfWeights+=_weights_pidEnergy[pid_iter->first][energy_iter->first];
+     133             :                 }
+     134             :         }
+     135           1 :         _weightsUpToDate = true;
+     136             : }
+     137             : 
+     138             : 
+     139           1 : void ParticleMapsContainer::getRandomParticles(size_t N, vector<int> &particleId, 
+     140             :         vector<double> &energy, vector<double> &galacticLongitudes,
+     141             :         vector<double> &galacticLatitudes) {
+     142           1 :         _updateWeights();
+     143             : 
+     144           1 :         particleId.resize(N);
+     145           1 :         energy.resize(N);
+     146           1 :         galacticLongitudes.resize(N);
+     147           1 :         galacticLatitudes.resize(N);
+     148             : 
+     149         421 :         for(size_t i=0; i< N; i++) {
+     150             :                 //get particle
+     151         420 :                 double r = Random::instance().rand() * _sumOfWeights;
+     152             :                 std::map<int, double>::iterator iter = _weightsPID.begin();
+     153         420 :                 while ((r-= iter->second) > 0) {
+     154             :                         ++iter; 
+     155             :                 }
+     156         420 :                 particleId[i] = iter->first;
+     157             :         
+     158             :                 //get energy
+     159         420 :                 r = Random::instance().rand() * iter->second;
+     160         420 :                 iter = _weights_pidEnergy[particleId[i]].begin();
+     161         420 :                 while ((r-= iter->second) > 0) {
+     162             :                  ++iter; 
+     163             :                 }
+     164         420 :                 energy[i] = idx2Energy(iter->first) / eV;
+     165             : 
+     166         420 :                 placeOnMap(particleId[i], energy[i] * eV, galacticLongitudes[i], galacticLatitudes[i]);
+     167             :         }
+     168           1 : }
+     169             : 
+     170             : 
+     171         420 : bool ParticleMapsContainer::placeOnMap(int pid, double energy, double &galacticLongitude, double &galacticLatitude) {
+     172         420 :         _updateWeights();
+     173             : 
+     174         420 :         if (_data.find(pid) == _data.end()) {
+     175             :                 return false;
+     176             :         }
+     177         420 :         int energyIdx   = energy2Idx(energy);
+     178         840 :         if (_data[pid].find(energyIdx) == _data[pid].end()) {
+     179             :                 return false;
+     180             :         }
+     181             : 
+     182         420 :         double r = Random::instance().rand() * _weights_pidEnergy[pid][energyIdx];
+     183             : 
+     184    10268580 :         for(size_t j = 0; j< _pixelization.getNumberOfPixels(); j++) {
+     185    10268580 :                 r -= _data[pid][energyIdx][j];
+     186    10268580 :                 if (r <= 0) {
+     187         420 :                         _pixelization.getRandomDirectionInPixel(j, galacticLongitude, galacticLatitude);
+     188         420 :                         return true;
+     189             :                 }
+     190             :         }
+     191             :         return false;
+     192             : }
+     193             : 
+     194             : 
+     195           0 : void ParticleMapsContainer::forceWeightUpdate() {
+     196           0 :         _weightsUpToDate = false;
+     197           0 : }
+     198             : 
+     199             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html new file mode 100644 index 000000000..70dfc7376 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/Pixelization.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - Pixelization.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:305060.0 %
Date:2024-04-08 14:58:22Functions:6875.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization4nPixEh0
_ZN7crpropa12Pixelization9pix2OrderEj0
_ZN7crpropa12Pixelization25getRandomDirectionInPixelEjRdS1_421
_ZNK7crpropa12Pixelization11spherCo2VecEddRN7healpix6vec3_tIdEE24585
_ZNK7crpropa12Pixelization13direction2PixEdd24585
_ZNK7crpropa12Pixelization13pix2DirectionEjRdS1_36868
_ZNK7crpropa12Pixelization12vec2SphereCoERdS1_RKN7healpix6vec3_tIdEE37289
_ZNK7crpropa12Pixelization15angularDistanceEjj49152
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html b/doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html new file mode 100644 index 000000000..d568a50f3 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/Pixelization.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - Pixelization.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:305060.0 %
Date:2024-04-08 14:58:22Functions:6875.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization25getRandomDirectionInPixelEjRdS1_421
_ZN7crpropa12Pixelization4nPixEh0
_ZN7crpropa12Pixelization9pix2OrderEj0
_ZNK7crpropa12Pixelization11spherCo2VecEddRN7healpix6vec3_tIdEE24585
_ZNK7crpropa12Pixelization12vec2SphereCoERdS1_RKN7healpix6vec3_tIdEE37289
_ZNK7crpropa12Pixelization13direction2PixEdd24585
_ZNK7crpropa12Pixelization13pix2DirectionEjRdS1_36868
_ZNK7crpropa12Pixelization15angularDistanceEjj49152
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html b/doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html new file mode 100644 index 000000000..26f97cb78 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html @@ -0,0 +1,205 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens/Pixelization.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLens - Pixelization.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:305060.0 %
Date:2024-04-08 14:58:22Functions:6875.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : //----------------------------------------------------------------------
+       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
+       3             : // a parametrized simulation engine for cosmic rays.
+       4             : //
+       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
+       6             : //                     RWTH Aachen University, Germany
+       7             : // Contact: winchen@physik.rwth-aachen.de
+       8             : //
+       9             : //  This program is free software: you can redistribute it and/or
+      10             : //  modify it under the terms of the GNU General Public License as
+      11             : //  published by the Free Software Foundation, either version 3 of
+      12             : //  the License, or (at your option) any later version.
+      13             : //
+      14             : //  This program is distributed in the hope that it will be useful,
+      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
+      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+      17             : //  GNU General Public License for more details.
+      18             : //
+      19             : //  You should have received a copy of the GNU General Public License
+      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
+      21             : //----------------------------------------------------------------------
+      22             : 
+      23             : #include "crpropa/magneticLens/Pixelization.h"
+      24             : #include "crpropa/Random.h"
+      25             : 
+      26             : namespace crpropa 
+      27             : {
+      28             : 
+      29             :         healpix::T_Healpix_Base<healpix::int64> Pixelization::_healpix_nest = healpix::T_Healpix_Base<healpix::int64>(29, healpix::NEST);
+      30             : 
+      31             : 
+      32           0 : uint8_t Pixelization::pix2Order(uint32_t pix)
+      33             : {
+      34           0 :         for (uint8_t i = 0; i < _nOrder_max; i++)
+      35             :         {
+      36           0 :                 if (pix == _nPix[i])
+      37           0 :                         return i + 1;
+      38             :         }
+      39             :         return 0;
+      40             : }
+      41             : 
+      42           0 : uint32_t Pixelization::nPix(uint8_t order)
+      43             : {
+      44           0 :         if (order > _nOrder_max)
+      45             :         {
+      46             :                 return 0;
+      47             :         }
+      48             :         else
+      49             :         {
+      50           0 :                 return _nPix[order - 1];
+      51             :         }
+      52             : }
+      53             : 
+      54       24585 : uint32_t Pixelization::direction2Pix(double longitude, double latitude) const
+      55             : {
+      56             :         healpix::vec3 v;
+      57       24585 :         spherCo2Vec(longitude, latitude, v);
+      58             :         try
+      59             :         {
+      60       24585 :                 uint32_t i = (uint32_t) _healpix->vec2pix(v);
+      61       24585 :                 return i;
+      62             :         }
+      63           0 :         catch (healpix::PlanckError &e)
+      64             :         {
+      65           0 :                 std::cerr << "Healpix error triggered from direction2Pix(" << longitude << ", " << latitude  << ")\n";
+      66           0 :                 std::cerr << " v = " << v.x <<", " << v.y << ", " <<  v.z << std::endl;
+      67           0 :                 std::cerr << "\n The original exception reads:\n";
+      68           0 :                 std::cerr << e.what() << std::endl;
+      69           0 :                 throw;
+      70           0 :         }
+      71             : }
+      72             : 
+      73       36868 : void Pixelization::pix2Direction(uint32_t i, double &longitude,
+      74             :                 double &latitude) const
+      75             : {
+      76             :         healpix::vec3 v;
+      77             :         try{
+      78       36868 :                 v = _healpix->pix2vec(i);
+      79             :         }
+      80           0 :         catch (healpix::PlanckError &e)
+      81             :         {
+      82           0 :                 std::cerr << "Healpix error triggered from pix2Direction(" << i << ", &longitude, &latitude " << ")\n";
+      83           0 :                 std::cerr << "The original exception reads:\n";
+      84           0 :                 std::cerr << e.what() << std::endl;
+      85           0 :                 throw;
+      86           0 :         }
+      87             : 
+      88       36868 :         vec2SphereCo(longitude, latitude, v);
+      89       36868 : }
+      90             : 
+      91       24585 : void Pixelization::spherCo2Vec(double phi, double theta,
+      92             :                 healpix::vec3 &V) const
+      93             : {
+      94       24585 :         V.x = cos(phi) * cos(theta);
+      95       24585 :         V.y = sin(phi) * cos(theta);
+      96       24585 :         V.z = sin(theta);
+      97       24585 : }
+      98             : 
+      99       37289 : void Pixelization::vec2SphereCo(double &phi, double &theta,
+     100             :                 const healpix::vec3 &V) const
+     101             : {
+     102       37289 :         theta = asin(V.z);
+     103       37289 :         phi = healpix::safe_atan2(V.y, V.x);
+     104       37289 : }
+     105             : 
+     106             : 
+     107       49152 : double Pixelization::angularDistance(uint32_t i, uint32_t j) const
+     108             : {
+     109             :         healpix::vec3 v1, v2;
+     110       49152 :         v1 = _healpix->pix2vec(i);
+     111       49152 :         v2 = _healpix->pix2vec(j);
+     112       49152 :         double s = v1.x * v2.x + v1.y * v2.y + v1.z * v2.z;
+     113             :         // Failsafe for numerical inaccuracies
+     114       49152 :         return ((s > 1) ? 0 : ((s < -1) ? M_PI : acos(s)));
+     115             : }
+     116             : 
+     117         421 : void Pixelization::getRandomDirectionInPixel(uint32_t i, double &longitude, double &latitude) 
+     118             : {
+     119             :         
+     120         421 :         uint64_t inest = _healpix->ring2nest(i);
+     121         421 :         uint64_t nUp = 29 - _healpix->Order();
+     122         421 :         uint64_t iUp = inest * pow(4, nUp);
+     123         421 :         iUp += Random::instance().randInt64(pow(4, nUp));
+     124             : 
+     125         421 :         healpix::vec3 v = _healpix_nest.pix2vec(iUp);
+     126             :         
+     127         421 :         vec2SphereCo(longitude, latitude, v);
+     128         421 : }
+     129             : } // namespace
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/index-sort-f.html b/doc/coverageReport/src/magneticLens/index-sort-f.html new file mode 100644 index 000000000..2a95e9fb8 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/index-sort-f.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:14732245.7 %
Date:2024-04-08 14:58:22Functions:214151.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ModelMatrix.cpp +
0.0%
+
0.0 %0 / 630.0 %0 / 7
MagneticLens.cpp +
41.3%41.3%
+
41.3 %43 / 10446.2 %6 / 13
ParticleMapsContainer.cpp +
70.5%70.5%
+
70.5 %74 / 10569.2 %9 / 13
Pixelization.cpp +
60.0%60.0%
+
60.0 %30 / 5075.0 %6 / 8
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/index-sort-l.html b/doc/coverageReport/src/magneticLens/index-sort-l.html new file mode 100644 index 000000000..7bd0ec2a3 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/index-sort-l.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:14732245.7 %
Date:2024-04-08 14:58:22Functions:214151.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ModelMatrix.cpp +
0.0%
+
0.0 %0 / 630.0 %0 / 7
MagneticLens.cpp +
41.3%41.3%
+
41.3 %43 / 10446.2 %6 / 13
Pixelization.cpp +
60.0%60.0%
+
60.0 %30 / 5075.0 %6 / 8
ParticleMapsContainer.cpp +
70.5%70.5%
+
70.5 %74 / 10569.2 %9 / 13
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/magneticLens/index.html b/doc/coverageReport/src/magneticLens/index.html new file mode 100644 index 000000000..bacc94ec2 --- /dev/null +++ b/doc/coverageReport/src/magneticLens/index.html @@ -0,0 +1,123 @@ + + + + + + + LCOV - coverage.info.cleaned - src/magneticLens + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:14732245.7 %
Date:2024-04-08 14:58:22Functions:214151.2 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticLens.cpp +
41.3%41.3%
+
41.3 %43 / 10446.2 %6 / 13
ModelMatrix.cpp +
0.0%
+
0.0 %0 / 630.0 %0 / 7
ParticleMapsContainer.cpp +
70.5%70.5%
+
70.5 %74 / 10569.2 %9 / 13
Pixelization.cpp +
60.0%60.0%
+
60.0 %30 / 5075.0 %6 / 8
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html new file mode 100644 index 000000000..506fe0201 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/ConstantDensity.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - ConstantDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:748983.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15ConstantDensity14getDescriptionB5cxx11Ev0
_ZN7crpropa15ConstantDensity5setH2Eb1
_ZN7crpropa15ConstantDensity5setH2Ed1
_ZN7crpropa15ConstantDensity5setHIEb1
_ZN7crpropa15ConstantDensity5setHIEd1
_ZN7crpropa15ConstantDensity6setHIIEb1
_ZN7crpropa15ConstantDensity6setHIIEd1
_ZN7crpropa15ConstantDensity10getIsForH2Ev2
_ZN7crpropa15ConstantDensity10getIsForHIEv2
_ZN7crpropa15ConstantDensity11getIsForHIIEv2
_ZN7crpropa15ConstantDensityC2Eddd3
_ZNK7crpropa15ConstantDensity10getDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getH2DensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getHIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity13getHIIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity17getNucleonDensityERKNS_7Vector3IdEE4
_ZN7crpropa15ConstantDensity5setH2Ebd5
_ZN7crpropa15ConstantDensity5setHIEbd5
_ZN7crpropa15ConstantDensity6setHIIEbd5
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html new file mode 100644 index 000000000..f0cb8a317 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/ConstantDensity.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - ConstantDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:748983.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15ConstantDensity10getIsForH2Ev2
_ZN7crpropa15ConstantDensity10getIsForHIEv2
_ZN7crpropa15ConstantDensity11getIsForHIIEv2
_ZN7crpropa15ConstantDensity14getDescriptionB5cxx11Ev0
_ZN7crpropa15ConstantDensity5setH2Eb1
_ZN7crpropa15ConstantDensity5setH2Ebd5
_ZN7crpropa15ConstantDensity5setH2Ed1
_ZN7crpropa15ConstantDensity5setHIEb1
_ZN7crpropa15ConstantDensity5setHIEbd5
_ZN7crpropa15ConstantDensity5setHIEd1
_ZN7crpropa15ConstantDensity6setHIIEb1
_ZN7crpropa15ConstantDensity6setHIIEbd5
_ZN7crpropa15ConstantDensity6setHIIEd1
_ZN7crpropa15ConstantDensityC2Eddd3
_ZNK7crpropa15ConstantDensity10getDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getH2DensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getHIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity13getHIIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity17getNucleonDensityERKNS_7Vector3IdEE4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html new file mode 100644 index 000000000..94c4d2718 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html @@ -0,0 +1,213 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/ConstantDensity.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - ConstantDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:748983.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/massDistribution/ConstantDensity.h"
+       2             : 
+       3             : #include "kiss/logger.h"
+       4             : 
+       5             : #include <sstream>
+       6             : 
+       7             : namespace crpropa{
+       8             : 
+       9           3 : ConstantDensity::ConstantDensity(double HI, double HII, double H2) {
+      10             :         // set all types active which are not equal 0 and change number density
+      11           3 :         if(HI!=0)
+      12           3 :                 setHI(true, HI);
+      13           3 :         if(HII!=0)
+      14           3 :                 setHII(true, HII);
+      15           3 :         if(H2!=0)
+      16           3 :                 setH2(true, H2);
+      17           3 : }
+      18             : 
+      19           4 : double ConstantDensity::getDensity(const Vector3d &position) const {
+      20             :         double n = 0;
+      21             : 
+      22           4 :         if(isHI)
+      23           3 :                 n += HIdensitynumber;
+      24           4 :         if(isHII)
+      25           3 :                 n += HIIdensitynumber;
+      26           4 :         if(isH2)
+      27           3 :                 n += H2densitynumber;
+      28             : 
+      29             :         // check if all densities are deactivated and raise warning if so
+      30           4 :         if((isHI || isHII || isH2) == false){
+      31           2 :                 KISS_LOG_WARNING
+      32           1 :                         << "\nCalled getNucleonDensity on fully deactivated ConstantDensity "
+      33           1 :                         << "gas density model. In this case the density is allways set to 0. \n";
+      34             :         }
+      35             : 
+      36           4 :         return n;
+      37             : }
+      38             : 
+      39           4 : double ConstantDensity::getNucleonDensity(const Vector3d &position) const {
+      40             :         double n = 0;
+      41             : 
+      42           4 :         if(isHI)
+      43           3 :                 n += HIdensitynumber;
+      44           4 :         if(isHII)
+      45           3 :                 n += HIIdensitynumber;
+      46           4 :         if(isH2)
+      47           3 :                 n += 2*H2densitynumber;
+      48             : 
+      49             :         // check if all densities are deactivated and raise warning if so
+      50           4 :         if((isHI || isHII || isH2) == false){
+      51           2 :                 KISS_LOG_WARNING
+      52           1 :                         << "\nCalled getNucleonDensity on fully deactivated ConstantDensity "
+      53           1 :                         << "gas density model. In this case the density is allways set to 0. \n";
+      54             :         }
+      55           4 :         return n;
+      56             : }
+      57             : 
+      58           4 : double ConstantDensity::getHIDensity(const Vector3d &position) const {
+      59           4 :         return HIdensitynumber;
+      60             : }
+      61             : 
+      62           4 : double ConstantDensity::getHIIDensity(const Vector3d &position) const{
+      63           4 :         return HIIdensitynumber;
+      64             : }
+      65             : 
+      66           4 : double ConstantDensity::getH2Density(const Vector3d &position) const{
+      67           4 :         return H2densitynumber;
+      68             : }
+      69             : 
+      70           2 : bool ConstantDensity::getIsForHI() {
+      71           2 :         return isHI;
+      72             : }
+      73             : 
+      74           2 : bool ConstantDensity::getIsForHII() {
+      75           2 :         return isHII;
+      76             : }
+      77             : 
+      78           2 : bool ConstantDensity::getIsForH2() {
+      79           2 :         return isH2;
+      80             : }
+      81             : 
+      82           5 : void ConstantDensity::setHI(bool activate, double densitynumber) {
+      83           5 :         isHI = activate;
+      84           5 :         HIdensitynumber = densitynumber;
+      85           5 : }
+      86             : 
+      87           1 : void ConstantDensity::setHI(bool activate) {
+      88           1 :         setHI(activate, HIdensitynumber);
+      89           1 : }
+      90             : 
+      91           1 : void ConstantDensity::setHI(double densitynumber) {
+      92           1 :         setHI(isHI, densitynumber);
+      93           1 : }
+      94             : 
+      95           5 : void ConstantDensity::setHII(bool activate, double densitynumber) {
+      96           5 :         isHII = activate;
+      97           5 :         HIIdensitynumber = densitynumber;
+      98           5 : }
+      99             : 
+     100           1 : void ConstantDensity::setHII(bool activate) {
+     101           1 :         setHII(activate, HIIdensitynumber);
+     102           1 : }
+     103             : 
+     104           1 : void ConstantDensity::setHII(double densitynumber) {
+     105           1 :         setHII(isHII, densitynumber);
+     106           1 : }
+     107             : 
+     108           5 : void ConstantDensity::setH2(bool activate, double densitynumber) {
+     109           5 :         isH2 = activate;
+     110           5 :         H2densitynumber = densitynumber;
+     111           5 : }
+     112             : 
+     113           1 : void ConstantDensity::setH2(bool activate) {
+     114           1 :         setH2(activate, H2densitynumber);
+     115           1 : }
+     116             : 
+     117           1 : void ConstantDensity::setH2(double densitynumber) {
+     118           1 :         setH2(isH2, densitynumber);
+     119           1 : }
+     120             : 
+     121           0 : std::string ConstantDensity::getDescription() {
+     122           0 :         std::stringstream s;
+     123           0 :         s << "ConstantDensity:\n";
+     124           0 :         s<< "HI component is ";
+     125           0 :         if(!isHI)
+     126           0 :                 s<< "not ";
+     127           0 :         s<< "active and has a density of " << HIdensitynumber/ccm << " cm^-3" << "\nHII component is ";
+     128           0 :         if(!isHII)
+     129           0 :                 s<< "not ";
+     130           0 :         s<<"active and has a density of " << HIIdensitynumber/ccm<<" cm^-3" <<  "\nH2 component is ";
+     131           0 :         if(!isH2)
+     132           0 :                 s<<"not ";
+     133           0 :         s<<"active and has a density of " << H2densitynumber/ccm << " cm^-3";
+     134           0 :         return s.str();
+     135           0 : }
+     136             : 
+     137             : }  // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html new file mode 100644 index 000000000..5ac34bc19 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Cordes.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Cordes.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:162176.2 %
Date:2024-04-08 14:58:22Functions:6785.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Cordes14getDescriptionB5cxx11Ev0
_ZN7crpropa6Cordes10getIsForH2Ev1
_ZN7crpropa6Cordes10getIsForHIEv1
_ZN7crpropa6Cordes11getIsForHIIEv1
_ZNK7crpropa6Cordes17getNucleonDensityERKNS_7Vector3IdEE1
_ZNK7crpropa6Cordes10getDensityERKNS_7Vector3IdEE2
_ZNK7crpropa6Cordes13getHIIDensityERKNS_7Vector3IdEE4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Cordes.cpp.func.html b/doc/coverageReport/src/massDistribution/Cordes.cpp.func.html new file mode 100644 index 000000000..6522e9bd4 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Cordes.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Cordes.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Cordes.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:162176.2 %
Date:2024-04-08 14:58:22Functions:6785.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Cordes10getIsForH2Ev1
_ZN7crpropa6Cordes10getIsForHIEv1
_ZN7crpropa6Cordes11getIsForHIIEv1
_ZN7crpropa6Cordes14getDescriptionB5cxx11Ev0
_ZNK7crpropa6Cordes10getDensityERKNS_7Vector3IdEE2
_ZNK7crpropa6Cordes13getHIIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa6Cordes17getNucleonDensityERKNS_7Vector3IdEE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html new file mode 100644 index 000000000..47a3e4fcf --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html @@ -0,0 +1,122 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Cordes.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Cordes.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:162176.2 %
Date:2024-04-08 14:58:22Functions:6785.7 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/massDistribution/Cordes.h"
+       2             : #include "crpropa/Common.h"
+       3             : 
+       4             : #include <sstream>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           4 : double Cordes::getHIIDensity(const Vector3d &position) const {
+       9             :         double n=0;  // in m^-3
+      10             : 
+      11           4 :         double z=position.z;
+      12           4 :         double R = sqrt(position.x*position.x+position.y*position.y);  //radius in galactic disk
+      13             : 
+      14           4 :         n += 0.025/ccm*exp(-fabs(z)/(1*kpc))*exp(-pow_integer<2>(R/(20*kpc)));  // galactocentric component
+      15           4 :         n += 0.2/ccm*exp(-fabs(z)/(0.15*kpc))*exp(-pow_integer<2>((R-4*kpc)/(2*kpc)));  // anular component
+      16             : 
+      17           4 :         return n;
+      18             : }
+      19             : 
+      20           2 : double Cordes::getDensity(const Vector3d &position) const {
+      21           2 :         return Cordes::getHIIDensity(position);
+      22             : }
+      23             : 
+      24           1 : double Cordes::getNucleonDensity(const Vector3d &position) const {
+      25           1 :         return getHIIDensity(position);
+      26             : }
+      27             : 
+      28           1 : bool Cordes::getIsForHI() {
+      29           1 :         return isforHI;
+      30             : }
+      31             : 
+      32           1 : bool Cordes::getIsForHII() {
+      33           1 :         return isforHII;
+      34             : }
+      35             : 
+      36           1 : bool Cordes::getIsForH2() {
+      37           1 :         return isforH2;
+      38             : }
+      39             : 
+      40           0 : std::string Cordes::getDescription() {
+      41           0 :         std::stringstream s;
+      42           0 :         s << "Density Cordes: includes only an HII component";
+      43           0 :         return s.str();
+      44           0 : }
+      45             : 
+      46             : }  // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html new file mode 100644 index 000000000..31d3bf13c --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Ferriere.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Ferriere.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13615190.1 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8Ferriere14getDescriptionB5cxx11Ev0
_ZN7crpropa8Ferriere10setIsForH2Eb1
_ZN7crpropa8Ferriere10setIsForHIEb1
_ZN7crpropa8Ferriere11setIsForHIIEb1
_ZN7crpropa8Ferriere10getIsForH2Ev4
_ZN7crpropa8Ferriere10getIsForHIEv4
_ZN7crpropa8Ferriere11getIsForHIIEv4
_ZNK7crpropa8Ferriere10getDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere17getNucleonDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere12getH2DensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere12getHIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere13getHIIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere17CMZTransformationERKNS_7Vector3IdEE13
_ZNK7crpropa8Ferriere18DiskTransformationERKNS_7Vector3IdEE13
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html b/doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html new file mode 100644 index 000000000..0c1bd9d00 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Ferriere.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Ferriere.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13615190.1 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8Ferriere10getIsForH2Ev4
_ZN7crpropa8Ferriere10getIsForHIEv4
_ZN7crpropa8Ferriere10setIsForH2Eb1
_ZN7crpropa8Ferriere10setIsForHIEb1
_ZN7crpropa8Ferriere11getIsForHIIEv4
_ZN7crpropa8Ferriere11setIsForHIIEb1
_ZN7crpropa8Ferriere14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Ferriere10getDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere12getH2DensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere12getHIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere13getHIIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere17CMZTransformationERKNS_7Vector3IdEE13
_ZNK7crpropa8Ferriere17getNucleonDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere18DiskTransformationERKNS_7Vector3IdEE13
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html new file mode 100644 index 000000000..b32294595 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html @@ -0,0 +1,349 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Ferriere.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Ferriere.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13615190.1 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/massDistribution/Ferriere.h"
+       2             : #include "crpropa/Common.h"
+       3             : 
+       4             : #include "kiss/logger.h"
+       5             : 
+       6             : #include <sstream>
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10          13 : Vector3d Ferriere::CMZTransformation(const Vector3d &position) const {
+      11             :         // set galactocentric coordinate system with the Sun at (-8.5,0.,0.) instead of (8.5, 0, 0) to be consistand with JF12 implementation
+      12          13 :         double x = -position.x;
+      13          13 :         double y = -position.y;
+      14             : 
+      15             :         double xC = -50*pc;             //offset
+      16             :         double yC = 50*pc;
+      17             :         double sinTc = sin(70.*deg);
+      18             :         double cosTc = cos(70.*deg);
+      19             : 
+      20             :         Vector3d pos;
+      21          13 :         pos.x = (x - xC)*cosTc + (y - yC)*sinTc;
+      22          13 :         pos.y = -(x - xC)*sinTc + (y - yC)*cosTc;
+      23          13 :         pos.z = position.z;
+      24             : 
+      25          13 :         return pos;
+      26             : }
+      27             : 
+      28          13 : Vector3d Ferriere::DiskTransformation(const Vector3d &position) const {
+      29             :         // set galactocentric coordinate system with the Sun at (-8.5,0.,0.) instead of (8.5, 0, 0) to be consistand with JF12 implementation
+      30          13 :         double x = -position.x;
+      31          13 :         double y = - position.y;
+      32          13 :         double z = position.z;
+      33             : 
+      34             :         double alphaD = 13.5*deg;  // rotation arround x-axis
+      35             :         double sinAd = sin(alphaD);
+      36             :         double cosAd = cos(alphaD);
+      37             :         double betaD = 20.*deg;  // rotation arround y'-axis
+      38             :         double sinBd = sin(betaD);
+      39             :         double cosBd = cos(betaD);
+      40             :         double TettaD = 48.5*deg;  // rotation arround x"-axis
+      41             :         double sinTd = sin(TettaD);
+      42             :         double cosTd = cos(TettaD);
+      43             : 
+      44             :         Vector3d pos;
+      45             : 
+      46          13 :         pos.x = x*cosBd*cosTd - y*(sinAd*sinBd*cosTd -cosAd*sinTd)-z*(cosAd*sinBd*cosTd +sinAd*sinTd);
+      47             : 
+      48          13 :         pos.y =  -x*cosBd*sinTd;
+      49          13 :         pos.y += y*(sinAd*sinBd*sinTd +cosAd*cosTd);
+      50          13 :         pos.y += z*(cosAd*sinBd*sinTd -sinAd*cosTd);
+      51             : 
+      52          13 :         pos.z = x*sinBd;
+      53          13 :         pos.z += y*sinAd*cosBd;
+      54          13 :         pos.z += z*cosAd*cosBd;
+      55             : 
+      56          13 :         return pos;
+      57             : }
+      58             : 
+      59          12 : double Ferriere::getHIDensity(const Vector3d &position) const {
+      60             :         double n = 0;
+      61          12 :         double R = sqrt(position.x*position.x+position.y*position.y);
+      62             : 
+      63          12 :         if(R<3*kpc)
+      64             :         {
+      65             :                 // density at center
+      66           6 :                 Vector3d pos = CMZTransformation(position);  // coordinate trafo
+      67           6 :                 double x = pos.x/pc;  // all units in pc
+      68           6 :                 double y = pos.y/pc;
+      69           6 :                 double z = pos.z/pc;
+      70             : 
+      71           6 :                 double A = sqrt(x*x+2.5*2.5*y*y);
+      72           6 :                 double nCMZ = 8.8/ccm*exp(-pow_integer<4>((A-125.)/137))*exp(-pow_integer<2>(z/54.));
+      73             : 
+      74             :                 // density in disk
+      75           6 :                 pos = DiskTransformation(position);  // Corrdinate Trafo
+      76           6 :                 x = pos.x/pc;  // all units in pc
+      77           6 :                 y = pos.y/pc;
+      78           6 :                 z = pos.z/pc;
+      79             : 
+      80           6 :                 A = sqrt(x*x+3.1*3.1*y*y);
+      81           6 :                 double nDisk = 0.34/ccm*exp(-pow_integer<4>((A-1200.)/438.))*exp(-pow_integer<2>(z/120));
+      82             : 
+      83           6 :                 n = nCMZ + nDisk;
+      84             :         }
+      85             :         else{  // outer region
+      86           6 :                 double z = position.z/pc;
+      87             :                 double a;
+      88           6 :                 if(R<=Rsun){
+      89             :                         a = 1;
+      90             :                 } else {
+      91           3 :                         a = R/Rsun;
+      92             :                 }
+      93             : 
+      94           6 :                 double nCold = 0.859*exp(-pow_integer<2>(z/(127*a))); // cold HI
+      95           6 :                 nCold += 0.047*exp(-pow_integer<2>(z/(318*a)));
+      96           6 :                 nCold += 0.094*exp(-fabs(z)/(403*a));
+      97           6 :                 nCold *= 0.340/ccm/(a*a);
+      98             : 
+      99           6 :                 double nWarm = (1.745 - 1.289/a)*exp(-pow_integer<2>(z/(127*a)));  // warm HI
+     100           6 :                 nWarm += (0.473 - 0.070/a)*exp(-pow_integer<2>(z/(318*a)));
+     101           6 :                 nWarm += (0.283 - 0.142/a)*exp(-fabs(z)/(403*a));
+     102           6 :                 nWarm *= 0.226/ccm/a;
+     103             : 
+     104           6 :                 n = nWarm + nCold;
+     105             :         }
+     106             : 
+     107          12 :         return n;
+     108             : }
+     109             : 
+     110          12 : double Ferriere::getHIIDensity(const Vector3d &position) const {
+     111             :         double n = 0;
+     112          12 :         double R = sqrt(position.x*position.x+position.y*position.y);
+     113             : 
+     114          12 :         if(R< 3*kpc){   // inner
+     115           6 :                 double x = position.x/pc;
+     116           6 :                 double y = position.y/pc;
+     117           6 :                 double z = position.z/pc;
+     118             : 
+     119             :                 // warm interstellar matter
+     120           6 :                 double H = (x*x + pow_integer<2>(y+10.))/(145*145);
+     121           6 :                 double nWIM = exp(-H)* exp(-pow_integer<2>(z+20.)/(26*26));
+     122           6 :                 nWIM += 0.009*exp(-pow_integer<2>((R/pc-3700)/(0.5*3700)))*1/pow_integer<2>(cosh(z/140.));
+     123           6 :                 nWIM += 0.005*cos(M_PI*R/pc*0.5/17000)*1/pow_integer<2>(cosh(z/950.));
+     124           6 :                 nWIM *= 8.0/ccm;  // rescaling with density at center
+     125             : 
+     126             :                 //very hot interstellar matter
+     127             :                 double alphaVH = 21.*deg;  // angle for very hot IM in radiant
+     128             :                 double cosA = cos(alphaVH);
+     129             :                 double sinA = sin(alphaVH);
+     130           6 :                 double etta = y*cosA+z*sinA;  // coordinate transformation for VHIM along major axis
+     131           6 :                 double chi = -y*sinA+z*cosA;
+     132             : 
+     133           6 :                 double nVHIM = 0.29/ccm*exp(-((x*x+etta*etta)/(162.*162.)+chi*chi/(90*90)));
+     134             : 
+     135           6 :                 n = nWIM + nVHIM;
+     136             :         } else {  // outer region
+     137           6 :                 double z = position.z;
+     138             : 
+     139           6 :                 double nWarm = 0.0237/ccm*exp(-(R*R-Rsun*Rsun)/pow_integer<2>(37*kpc))*exp(-fabs(z)/(1*kpc));
+     140           6 :                 nWarm += 0.0013/ccm*exp(-(pow_integer<2>(R-4*kpc)-pow_integer<2>(Rsun-4*kpc))/pow_integer<2>(2*kpc))*exp(-fabs(z)/(150*pc));
+     141             : 
+     142           6 :                 double nHot = 0.12*exp(-(R-Rsun)/(4.9*kpc));
+     143           6 :                 nHot += 0.88*exp(-(pow_integer<2>(R-4.5*kpc)-pow_integer<2>(Rsun-4.5*kpc))/pow_integer<2>(2.9*kpc));
+     144           6 :                 nHot *= pow(R/Rsun, -1.65);
+     145           6 :                 nHot *= exp(-fabs(z)/((1500*pc)*pow(R/Rsun,1.65)));
+     146           6 :                 nHot *= 4.8e-4/ccm;
+     147             : 
+     148           6 :                 n= nWarm + nHot;
+     149             :         }
+     150          12 :         return n;
+     151             : }
+     152             : 
+     153          12 : double Ferriere::getH2Density(const Vector3d &position) const{
+     154             :         double n=0;
+     155          12 :         double R=sqrt(position.x*position.x+position.y*position.y);
+     156             : 
+     157          12 :         if(R<3*kpc) {
+     158             :                 // density at center
+     159           6 :                 Vector3d pos =CMZTransformation(position);  // coord trafo for CMZ
+     160           6 :                 double x = pos.x/pc;  // all units in pc
+     161           6 :                 double y = pos.y/pc;
+     162           6 :                 double z = pos.z/pc;
+     163             : 
+     164           6 :                 double A = sqrt(x*x+pow(2.5*y,2));  // ellipticity
+     165           6 :                 double nCMZ = exp(-pow((A-125.)/137.,4))*exp(-pow(z/18.,2));
+     166           6 :                 nCMZ *= 150/ccm;  // rescaling
+     167             : 
+     168             :                 // density in disk
+     169           6 :                 pos = DiskTransformation(position);  // coord trafo for disk
+     170           6 :                 x=pos.x/pc;
+     171           6 :                 y=pos.y/pc;
+     172           6 :                 z=pos.z/pc;
+     173             : 
+     174           6 :                 A = sqrt(x*x+pow_integer<2>(3.1*y));
+     175           6 :                 double nDISK = exp(-pow_integer<4>((A-1200)/438))*exp(-pow_integer<2>(z/42));
+     176           6 :                 nDISK *= 4.8/ccm;  // rescaling
+     177             : 
+     178           6 :                 n = nCMZ + nDISK;
+     179             :         } else {  // outer region
+     180           6 :                 double z = position.z/pc;
+     181           6 :                 n = pow(R/Rsun, -0.58);
+     182           6 :                 n *= exp(-(pow_integer<2>(R-4.5*kpc)-pow_integer<2>(Rsun-4.5*kpc))/pow_integer<2>(2.9*kpc));
+     183           6 :                 n *= exp(-pow_integer<2>(z/(81*pow(R/Rsun,0.58))));
+     184           6 :                 n *= 0.58/ccm;  // rescaling
+     185             :         }
+     186             : 
+     187          12 :         return n;
+     188             : }
+     189             : 
+     190           5 : double Ferriere::getDensity(const Vector3d &position) const{
+     191             :         double n=0;
+     192           5 :         if(isforHI){
+     193           4 :                 n += getHIDensity(position);
+     194             :         }
+     195           5 :         if(isforHII){
+     196           4 :                 n+=getHIIDensity(position);
+     197             :         }
+     198           5 :         if(isforH2){
+     199           4 :                 n+=getH2Density(position);
+     200             :         }
+     201             :         // check if all densities are deactivated and raise warning if so
+     202           5 :         if((isforHI || isforHII || isforH2) == false){
+     203           2 :                 KISS_LOG_WARNING
+     204           1 :                         << "\nCalled getDensity on fully deactivated Ferriere \n"
+     205           1 :                         << "gas density model. The total density is set to 0.";
+     206             :         }
+     207             : 
+     208           5 :         return n;
+     209             : }
+     210             : 
+     211           5 : double Ferriere::getNucleonDensity(const Vector3d &position) const{
+     212             :         double n=0;
+     213           5 :         if(isforHI){
+     214           4 :                 n += getHIDensity(position);
+     215             :         }
+     216           5 :         if(isforHII){
+     217           4 :                 n+=getHIIDensity(position);
+     218             :         }
+     219           5 :         if(isforH2){
+     220           4 :                 n+= 2*getH2Density(position);
+     221             :         }
+     222             : 
+     223             :         // check if all densities are deactivated and raise warning if so
+     224           5 :         if((isforHI || isforHII || isforH2) == false){
+     225           2 :                 KISS_LOG_WARNING
+     226           1 :                         << "\nCalled getNucleonDensity on fully deactivated Ferriere \n"
+     227           1 :                         << "gas density model. The total density is set to 0.";
+     228             :         }
+     229             : 
+     230           5 :         return n;
+     231             : }
+     232             : 
+     233           1 : void Ferriere::setIsForHI(bool HI){
+     234           1 :         isforHI = HI;
+     235           1 : }
+     236             : 
+     237           1 : void Ferriere::setIsForHII(bool HII){
+     238           1 :         isforHII = HII;
+     239           1 : }
+     240             : 
+     241           1 : void Ferriere::setIsForH2(bool H2){
+     242           1 :         isforH2 = H2;
+     243           1 : }
+     244             : 
+     245           4 : bool Ferriere::getIsForHI(){
+     246           4 :         return isforHI;
+     247             : }
+     248             : 
+     249           4 : bool Ferriere::getIsForHII(){
+     250           4 :         return isforHII;
+     251             : }
+     252             : 
+     253           4 : bool Ferriere::getIsForH2(){
+     254           4 :         return isforH2;
+     255             : }
+     256             : 
+     257           0 : std::string Ferriere::getDescription() {
+     258           0 :         std::stringstream s;
+     259           0 :         s << "Density model Ferriere 2007:\n";
+     260           0 :         s<< "HI component is ";
+     261           0 :         if(!isforHI)
+     262           0 :                 s<< "not ";
+     263           0 :         s<< "active.\nHII component is ";
+     264           0 :         if(!isforHII)
+     265           0 :                 s<< "not ";
+     266           0 :         s<<"active.\nH2 component is ";
+     267           0 :         if(!isforH2)
+     268           0 :                 s<<"not ";
+     269           0 :         s<<"active.";
+     270           0 :         return s.str();
+     271           0 : }
+     272             : 
+     273             : }  // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html new file mode 100644 index 000000000..bf02e8f4f --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html @@ -0,0 +1,160 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Massdistribution.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Massdistribution.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:658576.5 %
Date:2024-04-08 14:58:22Functions:192286.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11DensityGrid14getDescriptionB5cxx11Ev0
_ZN7crpropa11DensityGrid7setGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa11DensityList14getDescriptionB5cxx11Ev0
_ZN7crpropa11DensityGrid10setIsForH2Eb1
_ZN7crpropa11DensityGrid10setIsForHIEb1
_ZN7crpropa11DensityGrid11setIsForHIIEb1
_ZNK7crpropa11DensityGrid10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityGrid17getNucleonDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getH2DensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getHIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList13getHIIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList17getNucleonDensityERKNS_7Vector3IdEE1
_ZN7crpropa11DensityGrid10getIsForH2Ev2
_ZN7crpropa11DensityGrid10getIsForHIEv2
_ZN7crpropa11DensityGrid11getIsForHIIEv2
_ZN7crpropa11DensityGridC2ENS_7ref_ptrINS_4GridIfEEEEbbb2
_ZN7crpropa11DensityList10addDensityENS_7ref_ptrINS_7DensityEEE2
_ZNK7crpropa11DensityGrid12getH2DensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid12getHIDensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid13getHIIDensityERKNS_7Vector3IdEE3
_ZN7crpropa11DensityGrid12checkAndWarnEv5
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html new file mode 100644 index 000000000..350b48552 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html @@ -0,0 +1,160 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Massdistribution.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Massdistribution.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:658576.5 %
Date:2024-04-08 14:58:22Functions:192286.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11DensityGrid10getIsForH2Ev2
_ZN7crpropa11DensityGrid10getIsForHIEv2
_ZN7crpropa11DensityGrid10setIsForH2Eb1
_ZN7crpropa11DensityGrid10setIsForHIEb1
_ZN7crpropa11DensityGrid11getIsForHIIEv2
_ZN7crpropa11DensityGrid11setIsForHIIEb1
_ZN7crpropa11DensityGrid12checkAndWarnEv5
_ZN7crpropa11DensityGrid14getDescriptionB5cxx11Ev0
_ZN7crpropa11DensityGrid7setGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa11DensityGridC2ENS_7ref_ptrINS_4GridIfEEEEbbb2
_ZN7crpropa11DensityList10addDensityENS_7ref_ptrINS_7DensityEEE2
_ZN7crpropa11DensityList14getDescriptionB5cxx11Ev0
_ZNK7crpropa11DensityGrid10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityGrid12getH2DensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid12getHIDensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid13getHIIDensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid17getNucleonDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getH2DensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getHIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList13getHIIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList17getNucleonDensityERKNS_7Vector3IdEE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html new file mode 100644 index 000000000..8d925d1a5 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html @@ -0,0 +1,222 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Massdistribution.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Massdistribution.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:658576.5 %
Date:2024-04-08 14:58:22Functions:192286.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/massDistribution/Massdistribution.h"
+       2             : #include <sstream>
+       3             : namespace crpropa {
+       4             : 
+       5           2 : void DensityList::addDensity(ref_ptr<Density> dens) {
+       6           2 :         DensityList.push_back(dens);
+       7           2 : }
+       8             : 
+       9           1 : double DensityList::getDensity(const Vector3d &position) const {
+      10             :         double n = 0.;
+      11           3 :         for (int i = 0; i < DensityList.size(); i++)
+      12           2 :                 n += DensityList[i]->getDensity(position);
+      13           1 :         return n;
+      14             : }
+      15             : 
+      16           1 : double DensityList::getHIDensity(const Vector3d &position) const {
+      17             :         double n = 0.;
+      18           3 :         for (int i = 0; i < DensityList.size(); i++)
+      19           2 :                 n += DensityList[i]->getHIDensity(position);
+      20           1 :         return n;
+      21             : }
+      22             : 
+      23           1 : double DensityList::getHIIDensity(const Vector3d &position) const {
+      24             :         double n = 0.;
+      25           3 :         for (int i = 0; i < DensityList.size(); i++)
+      26           2 :                 n += DensityList[i]->getHIIDensity(position);
+      27           1 :         return n;
+      28             : }
+      29             : 
+      30           1 : double DensityList::getH2Density(const Vector3d &position) const {
+      31             :         double n = 0.;
+      32           3 :         for (int i = 0; i < DensityList.size(); i++)
+      33           2 :                 n += DensityList[i]->getH2Density(position);
+      34           1 :         return n;
+      35             : }
+      36             : 
+      37           1 : double DensityList::getNucleonDensity(const Vector3d &position) const {
+      38             :         double n = 0.;
+      39           3 :         for (int i = 0; i < DensityList.size(); i++)
+      40           2 :                 n += DensityList[i]->getNucleonDensity(position);
+      41           1 :         return n;
+      42             : }
+      43             : 
+      44           0 : std::string DensityList::getDescription() {
+      45           0 :         std::stringstream ss; 
+      46           0 :         ss << "DensityList with " << DensityList.size() << " modules: \n";
+      47           0 :         for (int i = 0; i < DensityList.size(); i++) {
+      48           0 :                 ss << "density " << i + 1 << ": " << DensityList[i] -> getDescription();
+      49             :         }
+      50             :         
+      51           0 :         return ss.str();
+      52           0 : }
+      53             : 
+      54             : // ----------- DensityGrid -----------------------------------------------------------------
+      55             : 
+      56           2 : DensityGrid::DensityGrid(ref_ptr<Grid1f> grid, bool isForHI, bool isForHII, bool isForH2) : 
+      57           2 :         grid(grid), isForHI(isForHI), isForHII(isForHII), isForH2(isForH2) {
+      58           2 :                 checkAndWarn();
+      59           2 :         }
+      60             : 
+      61           5 : void DensityGrid::checkAndWarn() {
+      62           5 :         bool allDeactivated = (isForHI == false) && (isForHII == false) && (isForH2 == false);
+      63             :         if (allDeactivated) {
+      64           0 :                 KISS_LOG_WARNING << "DensityGrid has all types deactivated."
+      65           0 :                         << "In this case all output will be n = 0. \n"
+      66           0 :                         << "Please activate the intended particle type. \n";
+      67             :         }
+      68           5 : }
+      69             : 
+      70           3 : double DensityGrid::getHIDensity(const Vector3d &position) const {
+      71           3 :         if (isForHI)
+      72           3 :                 return grid -> interpolate(position);
+      73             :         else 
+      74             :                 return 0.;
+      75             : }
+      76             : 
+      77           3 : double DensityGrid::getHIIDensity(const Vector3d &position) const {
+      78           3 :         if (isForHII) 
+      79           0 :                 return grid -> interpolate(position);
+      80             :         else
+      81             :                 return 0.;
+      82             : }
+      83             : 
+      84           3 : double DensityGrid::getH2Density(const Vector3d &position) const {
+      85           3 :         if (isForH2)
+      86           0 :                 return grid -> interpolate(position);
+      87             :         else
+      88             :                 return 0.;
+      89             : }
+      90             : 
+      91           1 : double DensityGrid::getDensity(const Vector3d &position) const {
+      92             :         double n = 0;
+      93           1 :         n += getHIDensity(position);
+      94           1 :         n += getHIIDensity(position);
+      95           1 :         n += getH2Density(position);
+      96             : 
+      97           1 :         return n;
+      98             : }
+      99             : 
+     100           1 : double DensityGrid::getNucleonDensity(const Vector3d &position) const {
+     101             :         double n = 0;
+     102           1 :         n += getHIDensity(position);
+     103           1 :         n += getHIIDensity(position);
+     104           1 :         n += 2 * getH2Density(position);
+     105             : 
+     106           1 :         return n;
+     107             : }
+     108             : 
+     109           2 : bool DensityGrid::getIsForHI() {
+     110           2 :         return isForHI;
+     111             : }
+     112             : 
+     113           2 : bool DensityGrid::getIsForHII() {
+     114           2 :         return isForHII;
+     115             : }
+     116             : 
+     117           2 : bool DensityGrid::getIsForH2() {
+     118           2 :         return isForH2;
+     119             : }
+     120             : 
+     121           1 : void DensityGrid::setIsForHI(bool b) {
+     122           1 :         isForHI = b;
+     123           1 :         checkAndWarn();
+     124           1 : }
+     125             : 
+     126           1 : void DensityGrid::setIsForHII(bool b) {
+     127           1 :         isForHII = b;
+     128           1 :         checkAndWarn();
+     129           1 : }
+     130             : 
+     131           1 : void DensityGrid::setIsForH2(bool b) {
+     132           1 :         isForH2 = b;
+     133           1 :         checkAndWarn();
+     134           1 : }
+     135             : 
+     136           0 : void DensityGrid::setGrid(ref_ptr<Grid1f> grid) {
+     137           0 :         this->grid = grid;
+     138           0 : }
+     139             : 
+     140           0 : std::string DensityGrid::getDescription() {
+     141           0 :         std::stringstream ss;
+     142           0 :         ss << "Density in a given grid \n"; 
+     143           0 :         return ss.str();
+     144           0 : }
+     145             : 
+     146             : } //namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html new file mode 100644 index 000000000..6cf5bc02a --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Nakanishi.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Nakanishi.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:587082.9 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Nakanishi14getDescriptionB5cxx11Ev0
_ZN7crpropa9Nakanishi10setIsForH2Eb1
_ZN7crpropa9Nakanishi10setIsForHIEb1
_ZN7crpropa9Nakanishi11getIsForHIIEv1
_ZN7crpropa9Nakanishi10getIsForH2Ev3
_ZN7crpropa9Nakanishi10getIsForHIEv3
_ZNK7crpropa9Nakanishi10getDensityERKNS_7Vector3IdEE3
_ZNK7crpropa9Nakanishi17getNucleonDensityERKNS_7Vector3IdEE3
_ZNK7crpropa9Nakanishi12getH2DensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi12getHIDensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi16getH2ScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi16getHIScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getH2PlanedensityERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getHIPlanedensityERKNS_7Vector3IdEE8
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html new file mode 100644 index 000000000..13484a861 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Nakanishi.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Nakanishi.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:587082.9 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Nakanishi10getIsForH2Ev3
_ZN7crpropa9Nakanishi10getIsForHIEv3
_ZN7crpropa9Nakanishi10setIsForH2Eb1
_ZN7crpropa9Nakanishi10setIsForHIEb1
_ZN7crpropa9Nakanishi11getIsForHIIEv1
_ZN7crpropa9Nakanishi14getDescriptionB5cxx11Ev0
_ZNK7crpropa9Nakanishi10getDensityERKNS_7Vector3IdEE3
_ZNK7crpropa9Nakanishi12getH2DensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi12getHIDensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi16getH2ScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi16getHIScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getH2PlanedensityERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getHIPlanedensityERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getNucleonDensityERKNS_7Vector3IdEE3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html new file mode 100644 index 000000000..79649cf3d --- /dev/null +++ b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html @@ -0,0 +1,195 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution/Nakanishi.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistribution - Nakanishi.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:587082.9 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/massDistribution/Nakanishi.h"
+       2             : #include "crpropa/Common.h"
+       3             : 
+       4             : #include "kiss/logger.h"
+       5             : 
+       6             : #include <sstream>
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10           8 : double Nakanishi::getHIScaleheight(const Vector3d &position) const {
+      11           8 :         double R = sqrt(pow_integer<2>(position.x)+pow_integer<2>(position.y));      // radius in galactic plane
+      12           8 :         double scaleheight = 1.06*pc*(116.3 +19.3*R/kpc+4.1*pow_integer<2>(R/kpc)-0.05*pow_integer<3>(R/kpc));
+      13           8 :         return scaleheight;
+      14             :         }
+      15             : 
+      16           8 : double Nakanishi::getHIPlanedensity(const Vector3d &position) const {
+      17           8 :         double R = sqrt(pow_integer<2>(position.x)+pow_integer<2>(position.y));      // radius in galactic plane
+      18           8 :         double planedensity = 0.94/ccm*(0.6*exp(-R/(2.4*kpc))+0.24*exp(-pow_integer<2>((R-9.5*kpc)/(4.8*kpc))));
+      19           8 :         return planedensity;
+      20             :         }
+      21             : 
+      22             : 
+      23           8 : double Nakanishi::getH2Scaleheight(const Vector3d &position) const {
+      24           8 :         double R = sqrt(pow_integer<2>(position.x)+ pow_integer<2>(position.y));  // radius in galactic plane
+      25           8 :         double scaleheight = 1.06*pc*( 10.8*exp(0.28*R/kpc)+42.78);
+      26           8 :         return scaleheight;
+      27             : }
+      28             : 
+      29           8 : double Nakanishi::getH2Planedensity(const Vector3d &position) const {
+      30           8 :         double R = sqrt(pow_integer<2>(position.x)+pow_integer<2>(position.y));  // radius in galactic plane
+      31           8 :         double planedensity =0.94/ccm*(11.2*exp(-R*R/(0.874*kpc*kpc)) +0.83*exp(-pow_integer<2>((R-4*kpc)/(3.2*kpc))));
+      32           8 :         return planedensity;
+      33             : }
+      34             : 
+      35           6 : double Nakanishi::getHIDensity(const Vector3d &position) const {
+      36             :         double n = 0;  // density
+      37           6 :         double planedensity = getHIPlanedensity(position);
+      38           6 :         double scaleheight = getHIScaleheight(position);
+      39           6 :         n = planedensity*pow(0.5,pow_integer<2>(position.z/scaleheight));
+      40             : 
+      41           6 :         return n;
+      42             : }
+      43             : 
+      44           6 : double Nakanishi::getH2Density(const Vector3d &position) const {
+      45             :         double n = 0;  // density
+      46           6 :         double planedensity = getH2Planedensity(position);
+      47           6 :         double scaleheight = getH2Scaleheight(position);
+      48           6 :         n = planedensity*pow(0.5,pow_integer<2>(position.z/scaleheight));
+      49             : 
+      50           6 :         return n;
+      51             : }
+      52             : 
+      53           3 : double Nakanishi::getDensity(const Vector3d &position) const {
+      54             :         double n = 0;
+      55           3 :         if(isforHI)
+      56           2 :                 n += getHIDensity(position);
+      57           3 :         if(isforH2)
+      58           2 :                 n += getH2Density(position);
+      59             :         
+      60             :         // check if all densities are deactivated and raise warning if so
+      61           3 :         if((isforHI || isforH2) == false){
+      62           2 :                 KISS_LOG_WARNING
+      63           1 :                         << "\n"<<"Called getDensity on fully deactivated Nakanishi \n"
+      64           1 :                         << "gas density model. The total density is set to 0.";
+      65             :         }
+      66           3 :         return n;
+      67             : }
+      68             : 
+      69           3 : double Nakanishi::getNucleonDensity(const Vector3d &position) const {
+      70             :         double n = 0;
+      71           3 :         if(isforHI)
+      72           2 :                 n += getHIDensity(position);
+      73           3 :         if(isforH2)
+      74           2 :                 n += 2*getH2Density(position);  // weight 2 for molecular hydrogen
+      75             : 
+      76             :         // check if all densities are deactivated and raise warning if so
+      77           3 :         if((isforHI || isforH2) == false){
+      78           2 :                 KISS_LOG_WARNING
+      79           1 :                         << "\n"<<"Called getNucleonDensity on fully deactivated Nakanishi \n"
+      80           1 :                         << "gas density model. The total density is set to 0.";
+      81             :         }
+      82             : 
+      83           3 :         return n;
+      84             : }
+      85             : 
+      86           3 : bool Nakanishi::getIsForHI() {
+      87           3 :         return isforHI;
+      88             : }
+      89             : 
+      90           1 : bool Nakanishi::getIsForHII() {
+      91           1 :         return isforHII;
+      92             : }
+      93           3 : bool Nakanishi::getIsForH2() {
+      94           3 :         return isforH2;
+      95             : }
+      96             : 
+      97           1 : void Nakanishi::setIsForHI(bool HI) {
+      98           1 :         isforHI = HI;
+      99           1 : }
+     100             : 
+     101           1 : void Nakanishi::setIsForH2(bool H2) {
+     102           1 :         isforH2 = H2;
+     103           1 : }
+     104             : 
+     105           0 : std::string Nakanishi::getDescription() {
+     106           0 :         std::stringstream s;
+     107           0 :         s << "Density model Nakanishi:\n";
+     108           0 :         s<< "HI component is ";
+     109           0 :         if(isforHI==false)
+     110           0 :                 s<< "not ";
+     111           0 :         s<< "active.\nH2 component is ";
+     112           0 :         if(isforH2==false)
+     113           0 :                 s<<"not ";
+     114           0 :         s<<"active.\nNakanishi has no HII component.";
+     115             : 
+     116           0 :         return s.str();
+     117           0 : }
+     118             : 
+     119             : }  // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/index-sort-f.html b/doc/coverageReport/src/massDistribution/index-sort-f.html new file mode 100644 index 000000000..8608e5fe2 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/index-sort-f.html @@ -0,0 +1,133 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:34941683.9 %
Date:2024-04-08 14:58:22Functions:697690.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Cordes.cpp +
76.2%76.2%
+
76.2 %16 / 2185.7 %6 / 7
Massdistribution.cpp +
76.5%76.5%
+
76.5 %65 / 8586.4 %19 / 22
Ferriere.cpp +
90.1%90.1%
+
90.1 %136 / 15192.9 %13 / 14
Nakanishi.cpp +
82.9%82.9%
+
82.9 %58 / 7092.9 %13 / 14
ConstantDensity.cpp +
83.1%83.1%
+
83.1 %74 / 8994.7 %18 / 19
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/index-sort-l.html b/doc/coverageReport/src/massDistribution/index-sort-l.html new file mode 100644 index 000000000..9ce5836f7 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/index-sort-l.html @@ -0,0 +1,133 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:34941683.9 %
Date:2024-04-08 14:58:22Functions:697690.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Cordes.cpp +
76.2%76.2%
+
76.2 %16 / 2185.7 %6 / 7
Massdistribution.cpp +
76.5%76.5%
+
76.5 %65 / 8586.4 %19 / 22
Nakanishi.cpp +
82.9%82.9%
+
82.9 %58 / 7092.9 %13 / 14
ConstantDensity.cpp +
83.1%83.1%
+
83.1 %74 / 8994.7 %18 / 19
Ferriere.cpp +
90.1%90.1%
+
90.1 %136 / 15192.9 %13 / 14
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/massDistribution/index.html b/doc/coverageReport/src/massDistribution/index.html new file mode 100644 index 000000000..dbbcaaf42 --- /dev/null +++ b/doc/coverageReport/src/massDistribution/index.html @@ -0,0 +1,133 @@ + + + + + + + LCOV - coverage.info.cleaned - src/massDistribution + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:34941683.9 %
Date:2024-04-08 14:58:22Functions:697690.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ConstantDensity.cpp +
83.1%83.1%
+
83.1 %74 / 8994.7 %18 / 19
Cordes.cpp +
76.2%76.2%
+
76.2 %16 / 2185.7 %6 / 7
Ferriere.cpp +
90.1%90.1%
+
90.1 %136 / 15192.9 %13 / 14
Massdistribution.cpp +
76.5%76.5%
+
76.5 %65 / 8586.4 %19 / 22
Nakanishi.cpp +
82.9%82.9%
+
82.9 %58 / 7092.9 %13 / 14
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html b/doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html new file mode 100644 index 000000000..dcbc5453c --- /dev/null +++ b/doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Acceleration.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Acceleration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0890.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16SecondOrderFermiC2Eddj0
_ZN7crpropa17ParticleSplittingC2EPNS_7SurfaceEiidNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa17QuasiLinearTheory6modifyEdPNS_9CandidateE0
_ZN7crpropa17QuasiLinearTheoryC2Eddd0
_ZN7crpropa22DirectedFlowScatteringC2ENS_7Vector3IdEEd0
_ZN7crpropa26AbstractAccelerationModule3addEPNS_18StepLengthModifierE0
_ZN7crpropa26AbstractAccelerationModuleC2Ed0
_ZN7crpropa28DirectedFlowOfScatterCenters6modifyEdPNS_9CandidateE0
_ZN7crpropa28DirectedFlowOfScatterCentersC2ERKNS_7Vector3IdEE0
_ZNK7crpropa16SecondOrderFermi21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa17ParticleSplitting7processEPNS_9CandidateE0
_ZNK7crpropa22DirectedFlowScattering21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7processEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7scatterEPNS_9CandidateERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Acceleration.cpp.func.html b/doc/coverageReport/src/module/Acceleration.cpp.func.html new file mode 100644 index 000000000..d528f5cfc --- /dev/null +++ b/doc/coverageReport/src/module/Acceleration.cpp.func.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Acceleration.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Acceleration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0890.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16SecondOrderFermiC2Eddj0
_ZN7crpropa17ParticleSplittingC2EPNS_7SurfaceEiidNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa17QuasiLinearTheory6modifyEdPNS_9CandidateE0
_ZN7crpropa17QuasiLinearTheoryC2Eddd0
_ZN7crpropa22DirectedFlowScatteringC2ENS_7Vector3IdEEd0
_ZN7crpropa26AbstractAccelerationModule3addEPNS_18StepLengthModifierE0
_ZN7crpropa26AbstractAccelerationModuleC2Ed0
_ZN7crpropa28DirectedFlowOfScatterCenters6modifyEdPNS_9CandidateE0
_ZN7crpropa28DirectedFlowOfScatterCentersC2ERKNS_7Vector3IdEE0
_ZNK7crpropa16SecondOrderFermi21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa17ParticleSplitting7processEPNS_9CandidateE0
_ZNK7crpropa22DirectedFlowScattering21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7processEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7scatterEPNS_9CandidateERKNS_7Vector3IdEE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Acceleration.cpp.gcov.html b/doc/coverageReport/src/module/Acceleration.cpp.gcov.html new file mode 100644 index 000000000..11ea17011 --- /dev/null +++ b/doc/coverageReport/src/module/Acceleration.cpp.gcov.html @@ -0,0 +1,260 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Acceleration.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Acceleration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0890.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/Acceleration.h"
+       2             : #include <crpropa/Common.h>
+       3             : #include <crpropa/Random.h>
+       4             : #include <cmath>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           0 : AbstractAccelerationModule::AbstractAccelerationModule(double _stepLength)
+       9           0 :         : crpropa::Module(), stepLength(_stepLength) {}
+      10             : 
+      11             : 
+      12           0 : void AbstractAccelerationModule::add(StepLengthModifier *modifier) {
+      13           0 :         modifiers.push_back(modifier);
+      14           0 : }
+      15             : 
+      16             : 
+      17           0 : void AbstractAccelerationModule::scatter(
+      18             :         crpropa::Candidate *candidate,
+      19             :         const crpropa::Vector3d &scatter_center_velocity) const {
+      20             :         // particle momentum in lab frame
+      21           0 :         const double E = candidate->current.getEnergy();
+      22           0 :         const crpropa::Vector3d p = candidate->current.getMomentum();
+      23             : 
+      24             :         // transform to rest frame of scatter center (p: prime)
+      25           0 :         const double beta = scatter_center_velocity.getR() / crpropa::c_light;
+      26           0 :         const double gamma = 1. / sqrt(1 - beta * beta);
+      27           0 :         const double Ep = gamma * (E - scatter_center_velocity.dot(p));
+      28             :         const crpropa::Vector3d pp = (p - scatter_center_velocity* E /
+      29             :                 (crpropa::c_light * crpropa::c_light)) * gamma;
+      30             : 
+      31             :         // scatter into random direction
+      32           0 :         const crpropa::Vector3d pp_new = crpropa::Random::instance().randVector() * pp.getR();
+      33             : 
+      34             :         // transform back
+      35           0 :         const double E_new = gamma * (Ep + scatter_center_velocity.dot(pp_new));
+      36             :         const crpropa::Vector3d p_new = (pp_new + scatter_center_velocity * Ep /
+      37             :                 (crpropa::c_light * crpropa::c_light)) * gamma;
+      38             : 
+      39             :         // update candidate properties
+      40           0 :         candidate->current.setEnergy(E_new);
+      41           0 :         candidate->current.setDirection(p_new / p_new.getR());
+      42           0 : }
+      43             : 
+      44             : 
+      45           0 : void AbstractAccelerationModule::process(crpropa::Candidate *candidate) const {
+      46           0 :         double currentStepLength = stepLength;
+      47           0 :         for (auto m : modifiers) {
+      48           0 :                 currentStepLength = m->modify(currentStepLength, candidate);
+      49             :         }
+      50             : 
+      51           0 :         double step = candidate->getCurrentStep();
+      52           0 :         while (step > 0) {
+      53           0 :                 double randDistance = -1. * log(crpropa::Random::instance().rand()) * currentStepLength;
+      54             : 
+      55           0 :                 if (step < randDistance) {
+      56           0 :                         candidate->limitNextStep(0.1 * currentStepLength);
+      57           0 :                         return;
+      58             :                 }
+      59           0 :                 scatter(candidate, scatterCenterVelocity(candidate));
+      60           0 :                 step -= randDistance;
+      61             :         }
+      62             : }
+      63             : 
+      64             : 
+      65           0 : SecondOrderFermi::SecondOrderFermi(double scatterVelocity, double stepLength,
+      66           0 :                                                                    unsigned int sizeOfPitchangleTable)
+      67             :         : AbstractAccelerationModule(stepLength),
+      68           0 :           scatterVelocity(scatterVelocity) {
+      69           0 :         setDescription("SecondOrderFermi Acceleration");
+      70           0 :         angle.resize(sizeOfPitchangleTable);
+      71           0 :         angleCDF.resize(sizeOfPitchangleTable);
+      72             : 
+      73             :         // have a discretized table of beamed pitch angles
+      74           0 :         for (unsigned int i =0; i < sizeOfPitchangleTable; i++) {
+      75           0 :                 angle[i] = i * M_PI / (sizeOfPitchangleTable-1);
+      76           0 :                 angleCDF[i] = (angle[i] +scatterVelocity / crpropa::c_light * sin(angle[i])) / M_PI;
+      77             :         }
+      78           0 : }
+      79             : 
+      80             : 
+      81           0 : crpropa::Vector3d SecondOrderFermi::scatterCenterVelocity(crpropa::Candidate *candidate) const
+      82             : {
+      83           0 :         size_t idx = crpropa::closestIndex(crpropa::Random::instance().rand(), angleCDF);
+      84           0 :         crpropa::Vector3d rv = crpropa::Random::instance().randVector();
+      85           0 :         crpropa::Vector3d rotationAxis = candidate->current.getDirection().cross(rv);
+      86             : 
+      87           0 :         rv = candidate->current.getDirection().getRotated(rotationAxis, M_PI - angle[idx]);
+      88           0 :         return rv * scatterVelocity;
+      89             : }
+      90             : 
+      91             : 
+      92           0 : DirectedFlowOfScatterCenters::DirectedFlowOfScatterCenters(
+      93           0 :         const Vector3d &scatterCenterVelocity)
+      94           0 :         : __scatterVelocity(scatterCenterVelocity) {}
+      95             : 
+      96             : 
+      97           0 : double DirectedFlowOfScatterCenters::modify(double steplength, Candidate* candidate)
+      98             : {
+      99           0 :         double directionModifier = (-1. * __scatterVelocity.dot(candidate->current.getDirection()) + c_light) / c_light;
+     100           0 :         return steplength / directionModifier;
+     101             : }
+     102             : 
+     103             : 
+     104           0 : DirectedFlowScattering::DirectedFlowScattering(
+     105           0 :         crpropa::Vector3d scatterCenterVelocity, double stepLength)
+     106           0 :         : __scatterVelocity(scatterCenterVelocity),
+     107           0 :           AbstractAccelerationModule(stepLength) {
+     108             : 
+     109             :         // In a directed field of scatter centers, the probability to encounter a
+     110             :         // scatter center depends on the direction of the candidate.
+     111           0 :         StepLengthModifier *mod = new DirectedFlowOfScatterCenters(__scatterVelocity);
+     112           0 :         this->add(mod);
+     113           0 : }
+     114             : 
+     115             : 
+     116           0 : crpropa::Vector3d DirectedFlowScattering::scatterCenterVelocity(
+     117             :         crpropa::Candidate *candidate) const { // does not depend on candidate here.
+     118           0 :         return __scatterVelocity;
+     119             : }
+     120             : 
+     121             : 
+     122           0 : QuasiLinearTheory::QuasiLinearTheory(double referenecEnergy,
+     123             :                                                                          double turbulenceIndex,
+     124           0 :                                                                          double minimumRigidity)
+     125           0 :         : __referenceEnergy(referenecEnergy), __turbulenceIndex(turbulenceIndex),
+     126           0 :           __minimumRigidity(minimumRigidity) {}
+     127             : 
+     128             : 
+     129           0 : double QuasiLinearTheory::modify(double steplength, Candidate* candidate)
+     130             : {
+     131           0 :         if (candidate->current.getRigidity() < __minimumRigidity)
+     132             :         {
+     133           0 :                 return steplength * std::pow(__minimumRigidity /
+     134           0 :                         (__referenceEnergy / eV), 2. - __turbulenceIndex);
+     135             :         }
+     136             :         else
+     137             :         {
+     138           0 :                 return steplength * std::pow(candidate->current.getRigidity() /
+     139           0 :                         (__referenceEnergy / eV), 2. - __turbulenceIndex);
+     140             :         }
+     141             : }
+     142             : 
+     143             : 
+     144           0 : ParticleSplitting::ParticleSplitting(Surface *surface, int      crossingThreshold, 
+     145           0 :         int numberSplits, double minWeight, std::string counterid)
+     146           0 :         : surface(surface), crossingThreshold(crossingThreshold),
+     147           0 :           numberSplits(numberSplits), minWeight(minWeight), counterid(counterid){};
+     148             : 
+     149           0 : void ParticleSplitting::process(Candidate *candidate) const {
+     150             :         const double currentDistance =
+     151           0 :                 surface->distance(candidate->current.getPosition());
+     152             :         const double previousDistance =
+     153           0 :                 surface->distance(candidate->previous.getPosition());
+     154             : 
+     155           0 :         if (currentDistance * previousDistance > 0)
+     156             :                 // candidate remains on the same side
+     157             :                 return;
+     158             : 
+     159           0 :         if (candidate->getWeight() < minWeight)
+     160             :                 return;
+     161             : 
+     162             :         int num_crossings = 1;
+     163           0 :         if (candidate->hasProperty(counterid))
+     164           0 :                 num_crossings = candidate->getProperty(counterid).toInt32() + 1;
+     165           0 :         candidate->setProperty(counterid, num_crossings);
+     166             : 
+     167           0 :         if (num_crossings % crossingThreshold != 0)
+     168             :                 return;
+     169             : 
+     170           0 :         candidate->updateWeight(1. / numberSplits);
+     171             : 
+     172           0 :         for (size_t i = 1; i < numberSplits; i++) {
+     173             :                 // No recursive split as the weights of the secondaries created
+     174             :                 // before the split are not affected
+     175           0 :                 ref_ptr<Candidate> new_candidate = candidate->clone(false);
+     176           0 :                 new_candidate->parent = candidate;
+     177           0 :                 uint64_t snr = Candidate::getNextSerialNumber();
+     178           0 :                 Candidate::setNextSerialNumber(snr + 1);
+     179           0 :                 new_candidate->setSerialNumber(snr);
+     180             :                 candidate->addSecondary(new_candidate);
+     181             :         }
+     182             : };
+     183             : 
+     184             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html b/doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html new file mode 100644 index 000000000..d39555576 --- /dev/null +++ b/doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/AdiabaticCooling.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - AdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:232785.2 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEEd1
_ZNK7crpropa16AdiabaticCooling8getLimitEv1
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEE2
_ZNK7crpropa16AdiabaticCooling7processEPNS_9CandidateE2
_ZN7crpropa16AdiabaticCooling8setLimitEd3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html b/doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html new file mode 100644 index 000000000..c94a74943 --- /dev/null +++ b/doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/AdiabaticCooling.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - AdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:232785.2 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16AdiabaticCooling8setLimitEd3
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEE2
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEEd1
_ZNK7crpropa16AdiabaticCooling7processEPNS_9CandidateE2
_ZNK7crpropa16AdiabaticCooling8getLimitEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html b/doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html new file mode 100644 index 000000000..1a9adcc18 --- /dev/null +++ b/doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html @@ -0,0 +1,130 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/AdiabaticCooling.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - AdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:232785.2 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/AdiabaticCooling.h"
+       2             : 
+       3             : namespace crpropa {
+       4             : 
+       5           2 : AdiabaticCooling::AdiabaticCooling(ref_ptr<AdvectionField> advectionField) :
+       6           2 :         advectionField(advectionField) {
+       7           2 :         setLimit(0.1);
+       8           2 : }
+       9             : 
+      10           1 : AdiabaticCooling::AdiabaticCooling(ref_ptr<AdvectionField> advectionField, double limit) :
+      11           1 :         advectionField(advectionField) {
+      12           1 :         setLimit(limit);
+      13           1 : }
+      14             : 
+      15           2 : void AdiabaticCooling::process(Candidate *c) const {
+      16             : 
+      17           2 :         Vector3d pos = c->current.getPosition();
+      18           2 :         double E = c->current.getEnergy(); // Note we use E=p/c (relativistic limit)
+      19             :         
+      20             :         double Div = 0.;        
+      21             :         try {
+      22           2 :                 Div +=  advectionField->getDivergence(pos);
+      23             :         } 
+      24           0 :         catch (std::exception &e) {
+      25           0 :                 KISS_LOG_ERROR  << "AdiabaticCooling: Exception in getDivergence.\n" 
+      26           0 :                                 << e.what();
+      27           0 :         }
+      28             :         
+      29           2 :         double dEdt = -E / 3. * Div;    // cooling due to advection -p/3 * div(V_wind)
+      30             :                                         // (see e.g. Kopp et al. Computer Physics Communication 183
+      31             :                                         // (2012) 530-542)
+      32           2 :         double dt = c->getCurrentStep() / c_light;
+      33           2 :         double dE = dEdt * dt;
+      34             :         
+      35           2 :         c->current.setEnergy(E + dE);
+      36           2 :         if (dEdt==0) {
+      37             :                 return;
+      38             :         }       
+      39           1 :         c->limitNextStep(limit * E / fabs(dEdt) *c_light);
+      40             : }
+      41             : 
+      42           3 : void AdiabaticCooling::setLimit(double l) {
+      43           3 :         limit = l;
+      44           3 : }
+      45             : 
+      46           1 : double AdiabaticCooling::getLimit() const {
+      47           1 :         return limit;
+      48             : }
+      49             :         
+      50             :         
+      51             : 
+      52             : 
+      53             : 
+      54             : } // end namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html b/doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html new file mode 100644 index 000000000..402ed01de --- /dev/null +++ b/doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html @@ -0,0 +1,252 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Boundary.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Boundary.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10621948.4 %
Date:2024-04-08 14:58:22Functions:204544.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11PeriodicBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBoxC2Ev0
_ZN7crpropa13CubicBoundary7setSizeEd0
_ZN7crpropa13CubicBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa13CubicBoundaryC2Ev0
_ZN7crpropa13ReflectiveBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBoxC2Ev0
_ZN7crpropa17SphericalBoundary9setCenterENS_7Vector3IdEE0
_ZN7crpropa17SphericalBoundary9setRadiusEd0
_ZN7crpropa17SphericalBoundaryC2Ev0
_ZN7crpropa19CylindricalBoundary9setHeightEd0
_ZN7crpropa19CylindricalBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa19CylindricalBoundary9setRadiusEd0
_ZN7crpropa19CylindricalBoundaryC2Ev0
_ZN7crpropa19EllipsoidalBoundary12setMajorAxisEd0
_ZN7crpropa19EllipsoidalBoundary14setFocalPointsENS_7Vector3IdEES2_0
_ZN7crpropa19EllipsoidalBoundaryC2Ev0
_ZNK7crpropa11PeriodicBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa13CubicBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ReflectiveBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SphericalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19CylindricalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19EllipsoidalBoundary14getDescriptionB5cxx11Ev0
_ZN7crpropa13ReflectiveBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa17SphericalBoundary12setLimitStepEb1
_ZN7crpropa17SphericalBoundary9setMarginEd1
_ZN7crpropa19CylindricalBoundary12setLimitStepEb1
_ZN7crpropa19CylindricalBoundary9setMarginEd1
_ZN7crpropa19EllipsoidalBoundary12setLimitStepEb1
_ZN7crpropa19EllipsoidalBoundary9setMarginEd1
_ZNK7crpropa13ReflectiveBox7processEPNS_9CandidateE1
_ZN7crpropa11PeriodicBoxC2ENS_7Vector3IdEES2_2
_ZN7crpropa13CubicBoundary12setLimitStepEb2
_ZN7crpropa13CubicBoundary9setMarginEd2
_ZNK7crpropa11PeriodicBox7processEPNS_9CandidateE2
_ZN7crpropa17SphericalBoundaryC2ENS_7Vector3IdEEd3
_ZN7crpropa19CylindricalBoundaryC2ENS_7Vector3IdEEdd3
_ZN7crpropa19EllipsoidalBoundaryC2ENS_7Vector3IdEES2_d3
_ZNK7crpropa17SphericalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19CylindricalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19EllipsoidalBoundary7processEPNS_9CandidateE3
_ZN7crpropa13CubicBoundaryC2ENS_7Vector3IdEEd4
_ZNK7crpropa13CubicBoundary7processEPNS_9CandidateE4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Boundary.cpp.func.html b/doc/coverageReport/src/module/Boundary.cpp.func.html new file mode 100644 index 000000000..faa7abed3 --- /dev/null +++ b/doc/coverageReport/src/module/Boundary.cpp.func.html @@ -0,0 +1,252 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Boundary.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Boundary.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10621948.4 %
Date:2024-04-08 14:58:22Functions:204544.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11PeriodicBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBoxC2ENS_7Vector3IdEES2_2
_ZN7crpropa11PeriodicBoxC2Ev0
_ZN7crpropa13CubicBoundary12setLimitStepEb2
_ZN7crpropa13CubicBoundary7setSizeEd0
_ZN7crpropa13CubicBoundary9setMarginEd2
_ZN7crpropa13CubicBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa13CubicBoundaryC2ENS_7Vector3IdEEd4
_ZN7crpropa13CubicBoundaryC2Ev0
_ZN7crpropa13ReflectiveBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa13ReflectiveBoxC2Ev0
_ZN7crpropa17SphericalBoundary12setLimitStepEb1
_ZN7crpropa17SphericalBoundary9setCenterENS_7Vector3IdEE0
_ZN7crpropa17SphericalBoundary9setMarginEd1
_ZN7crpropa17SphericalBoundary9setRadiusEd0
_ZN7crpropa17SphericalBoundaryC2ENS_7Vector3IdEEd3
_ZN7crpropa17SphericalBoundaryC2Ev0
_ZN7crpropa19CylindricalBoundary12setLimitStepEb1
_ZN7crpropa19CylindricalBoundary9setHeightEd0
_ZN7crpropa19CylindricalBoundary9setMarginEd1
_ZN7crpropa19CylindricalBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa19CylindricalBoundary9setRadiusEd0
_ZN7crpropa19CylindricalBoundaryC2ENS_7Vector3IdEEdd3
_ZN7crpropa19CylindricalBoundaryC2Ev0
_ZN7crpropa19EllipsoidalBoundary12setLimitStepEb1
_ZN7crpropa19EllipsoidalBoundary12setMajorAxisEd0
_ZN7crpropa19EllipsoidalBoundary14setFocalPointsENS_7Vector3IdEES2_0
_ZN7crpropa19EllipsoidalBoundary9setMarginEd1
_ZN7crpropa19EllipsoidalBoundaryC2ENS_7Vector3IdEES2_d3
_ZN7crpropa19EllipsoidalBoundaryC2Ev0
_ZNK7crpropa11PeriodicBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa11PeriodicBox7processEPNS_9CandidateE2
_ZNK7crpropa13CubicBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa13CubicBoundary7processEPNS_9CandidateE4
_ZNK7crpropa13ReflectiveBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ReflectiveBox7processEPNS_9CandidateE1
_ZNK7crpropa17SphericalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SphericalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19CylindricalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19CylindricalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19EllipsoidalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19EllipsoidalBoundary7processEPNS_9CandidateE3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Boundary.cpp.gcov.html b/doc/coverageReport/src/module/Boundary.cpp.gcov.html new file mode 100644 index 000000000..0e651f732 --- /dev/null +++ b/doc/coverageReport/src/module/Boundary.cpp.gcov.html @@ -0,0 +1,370 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Boundary.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Boundary.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10621948.4 %
Date:2024-04-08 14:58:22Functions:204544.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/Boundary.h"
+       2             : #include "crpropa/Units.h"
+       3             : 
+       4             : #include <sstream>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           0 : PeriodicBox::PeriodicBox() :
+       9           0 :                 origin(Vector3d(0, 0, 0)), size(Vector3d(0, 0, 0)) {
+      10           0 : }
+      11             : 
+      12           2 : PeriodicBox::PeriodicBox(Vector3d o, Vector3d s) :
+      13           2 :                 origin(o), size(s) {
+      14           2 : }
+      15             : 
+      16           2 : void PeriodicBox::process(Candidate *c) const {
+      17           2 :         Vector3d pos = c->current.getPosition();
+      18           2 :         Vector3d n = ((pos - origin) / size).floor();
+      19             : 
+      20           2 :         if ((n.x == 0) and (n.y == 0) and (n.z == 0))
+      21             :                 return; // do nothing if candidate is inside the box
+      22             : 
+      23           2 :         c->current.setPosition(pos - n * size);
+      24           2 :         c->previous.setPosition(c->previous.getPosition() - n * size);
+      25           2 :         c->source.setPosition(c->source.getPosition() - n * size);
+      26           2 :         c->created.setPosition(c->created.getPosition() - n * size);
+      27             : }
+      28             : 
+      29           0 : void PeriodicBox::setOrigin(Vector3d o) {
+      30             :         origin = o;
+      31           0 : }
+      32           0 : void PeriodicBox::setSize(Vector3d s) {
+      33             :         size = s;
+      34           0 : }
+      35             : 
+      36           0 : std::string PeriodicBox::getDescription() const {
+      37           0 :         std::stringstream s;
+      38           0 :         s << "Periodic box: origin " << origin / Mpc << " Mpc, ";
+      39           0 :         s << "size " << size / Mpc << " Mpc";
+      40           0 :         return s.str();
+      41           0 : }
+      42             : 
+      43           0 : ReflectiveBox::ReflectiveBox() :
+      44           0 :                 origin(Vector3d(0, 0, 0)), size(Vector3d(0, 0, 0)) {
+      45           0 : }
+      46             : 
+      47           1 : ReflectiveBox::ReflectiveBox(Vector3d o, Vector3d s) :
+      48           1 :                 origin(o), size(s) {
+      49           1 : }
+      50             : 
+      51           1 : void ReflectiveBox::process(Candidate *c) const {
+      52           1 :         Vector3d cur = (c->current.getPosition() - origin) / size; // current position in cell units
+      53           1 :         Vector3d n = cur.floor();
+      54             : 
+      55           1 :         if ((n.x == 0) and (n.y == 0) and (n.z == 0))
+      56             :                 return; // do nothing if candidate is inside the box
+      57             : 
+      58             :         // flip direction
+      59           1 :         Vector3d nReflect(pow(-1, n.x), pow(-1, n.y), pow(-1, n.z));
+      60           1 :         c->current.setDirection(c->current.getDirection() * nReflect);
+      61           1 :         c->previous.setDirection(c->previous.getDirection() * nReflect);
+      62           1 :         c->created.setDirection(c->created.getDirection() * nReflect);
+      63           1 :         c->source.setDirection(c->source.getDirection() * nReflect);
+      64             : 
+      65           1 :         Vector3d src = (c->source.getPosition() - origin) / size; // initial position in cell units
+      66           1 :         Vector3d cre = (c->created.getPosition() - origin) / size; // initial position in cell units
+      67           1 :         Vector3d prv = (c->previous.getPosition() - origin) / size; // previous position in cell units
+      68             : 
+      69             :         // repeatedly translate until the current position is inside the cell
+      70           1 :         while ((cur.x < 0) or (cur.x > 1)) {
+      71           0 :                 double t = 2 * (cur.x > 1);
+      72           0 :                 src.x = t - src.x;
+      73           0 :                 cre.x = t - cre.x;
+      74           0 :                 prv.x = t - prv.x;
+      75           0 :                 cur.x = t - cur.x;
+      76             :         }
+      77           1 :         while ((cur.y < 0) or (cur.y > 1)) {
+      78           0 :                 double t = 2 * (cur.y > 1);
+      79           0 :                 src.y = t - src.y;
+      80           0 :                 cre.y = t - cre.y;
+      81           0 :                 prv.y = t - prv.y;
+      82           0 :                 cur.y = t - cur.y;
+      83             :         }
+      84           2 :         while ((cur.z < 0) or (cur.z > 1)) {
+      85           1 :                 double t = 2 * (cur.z > 1);
+      86           1 :                 src.z = t - src.z;
+      87           1 :                 cre.z = t - cre.z;
+      88           1 :                 prv.z = t - prv.z;
+      89           1 :                 cur.z = t - cur.z;
+      90             :         }
+      91             : 
+      92           1 :         c->current.setPosition(cur * size + origin);
+      93           1 :         c->source.setPosition(src * size + origin);
+      94           1 :         c->created.setPosition(cre * size + origin);
+      95           1 :         c->previous.setPosition(prv * size + origin);
+      96             : }
+      97             : 
+      98           0 : void ReflectiveBox::setOrigin(Vector3d o) {
+      99             :         origin = o;
+     100           0 : }
+     101           0 : void ReflectiveBox::setSize(Vector3d s) {
+     102             :         size = s;
+     103           0 : }
+     104             : 
+     105           0 : std::string ReflectiveBox::getDescription() const {
+     106           0 :         std::stringstream s;
+     107           0 :         s << "Reflective box: origin " << origin / Mpc << " Mpc, ";
+     108           0 :         s << "size " << size / Mpc << " Mpc";
+     109           0 :         return s.str();
+     110           0 : }
+     111             : 
+     112           0 : CubicBoundary::CubicBoundary() :
+     113           0 :                 origin(Vector3d(0, 0, 0)), size(0), limitStep(true), margin(0.1 * kpc) {
+     114           0 : }
+     115             : 
+     116           4 : CubicBoundary::CubicBoundary(Vector3d o, double s) :
+     117           4 :                 origin(o), size(s), limitStep(true), margin(0.1 * kpc) {
+     118           4 : }
+     119             : 
+     120           4 : void CubicBoundary::process(Candidate *c) const {
+     121           4 :         Vector3d r = c->current.getPosition() - origin;
+     122             :         double lo = r.min();
+     123             :         double hi = r.max();
+     124           4 :         if ((lo <= 0) or (hi >= size)) {
+     125           1 :                 reject(c);
+     126             :         }
+     127           4 :         if (limitStep) {
+     128           4 :                 c->limitNextStep(lo + margin);
+     129           4 :                 c->limitNextStep(size - hi + margin);
+     130             :         }
+     131           4 : }
+     132             : 
+     133           0 : void CubicBoundary::setOrigin(Vector3d o) {
+     134             :         origin = o;
+     135           0 : }
+     136           0 : void CubicBoundary::setSize(double s) {
+     137           0 :         size = s;
+     138           0 : }
+     139           2 : void CubicBoundary::setMargin(double m) {
+     140           2 :         margin = m;
+     141           2 : }
+     142           2 : void CubicBoundary::setLimitStep(bool b) {
+     143           2 :         limitStep = b;
+     144           2 : }
+     145             : 
+     146           0 : std::string CubicBoundary::getDescription() const {
+     147           0 :         std::stringstream s;
+     148           0 :         s << "Cubic Boundary: origin " << origin / Mpc << " Mpc, ";
+     149           0 :         s << "size " << size / Mpc << " Mpc, ";
+     150           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     151           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     152           0 :         if (rejectAction.valid())
+     153           0 :                 s << ", Action: " << rejectAction->getDescription();
+     154           0 :         return s.str();
+     155           0 : }
+     156             : 
+     157           0 : SphericalBoundary::SphericalBoundary() :
+     158           0 :                 center(Vector3d(0, 0, 0)), radius(0), limitStep(true), margin(0.1 * kpc) {
+     159           0 : }
+     160             : 
+     161           3 : SphericalBoundary::SphericalBoundary(Vector3d c, double r) :
+     162           3 :                 center(c), radius(r), limitStep(true), margin(0.1 * kpc) {
+     163           3 : }
+     164             : 
+     165           3 : void SphericalBoundary::process(Candidate *c) const {
+     166           3 :         double d = (c->current.getPosition() - center).getR();
+     167           3 :         if (d >= radius) {
+     168           1 :                 reject(c);
+     169             :         }
+     170           3 :         if (limitStep)
+     171           3 :                 c->limitNextStep(radius - d + margin);
+     172           3 : }
+     173             : 
+     174           0 : void SphericalBoundary::setCenter(Vector3d c) {
+     175             :         center = c;
+     176           0 : }
+     177           0 : void SphericalBoundary::setRadius(double r) {
+     178           0 :         radius = r;
+     179           0 : }
+     180           1 : void SphericalBoundary::setMargin(double m) {
+     181           1 :         margin = m;
+     182           1 : }
+     183           1 : void SphericalBoundary::setLimitStep(bool b) {
+     184           1 :         limitStep = b;
+     185           1 : }
+     186             : 
+     187           0 : std::string SphericalBoundary::getDescription() const {
+     188           0 :         std::stringstream s;
+     189           0 :         s << "Spherical Boundary: radius " << radius / Mpc << " Mpc, ";
+     190           0 :         s << "around " << center / Mpc << " Mpc, ";
+     191           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     192           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     193           0 :         if (rejectAction.valid())
+     194           0 :                 s << ", Action: " << rejectAction->getDescription();
+     195           0 :         return s.str();
+     196           0 : }
+     197             : 
+     198           0 : EllipsoidalBoundary::EllipsoidalBoundary() :
+     199             :                 focalPoint1(Vector3d(0, 0, 0)), focalPoint2(Vector3d(0, 0, 0)),
+     200           0 :                 majorAxis(0), limitStep(true), margin(0.1 * kpc) {
+     201           0 : }
+     202             : 
+     203           3 : EllipsoidalBoundary::EllipsoidalBoundary(Vector3d f1, Vector3d f2, double a) :
+     204           3 :                 focalPoint1(f1), focalPoint2(f2), majorAxis(a), limitStep(true),
+     205           3 :                 margin(0.1 * kpc) {
+     206           3 : }
+     207             : 
+     208           3 : void EllipsoidalBoundary::process(Candidate *c) const {
+     209           3 :         Vector3d pos = c->current.getPosition();
+     210           3 :         double d = pos.getDistanceTo(focalPoint1) + pos.getDistanceTo(focalPoint2);
+     211           3 :         if (d >= majorAxis) {
+     212           1 :                 reject(c);
+     213             :         }
+     214           3 :         if (limitStep)
+     215           3 :                 c->limitNextStep(majorAxis - d + margin);
+     216           3 : }
+     217             : 
+     218           0 : void EllipsoidalBoundary::setFocalPoints(Vector3d f1, Vector3d f2) {
+     219             :         focalPoint1 = f1;
+     220             :         focalPoint2 = f2;
+     221           0 : }
+     222           0 : void EllipsoidalBoundary::setMajorAxis(double a) {
+     223           0 :         majorAxis = a;
+     224           0 : }
+     225           1 : void EllipsoidalBoundary::setMargin(double m) {
+     226           1 :         margin = m;
+     227           1 : }
+     228           1 : void EllipsoidalBoundary::setLimitStep(bool b) {
+     229           1 :         limitStep = b;
+     230           1 : }
+     231             : 
+     232           0 : std::string EllipsoidalBoundary::getDescription() const {
+     233           0 :         std::stringstream s;
+     234           0 :         s << "Ellipsoidal Boundary: F1 = " << focalPoint1 / Mpc << " Mpc, ";
+     235           0 :         s << "F2 = " << focalPoint2 / Mpc << " Mpc, ";
+     236           0 :         s << "major axis " << majorAxis / Mpc << " Mpc; ";
+     237           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     238           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     239           0 :         if (rejectAction.valid())
+     240           0 :                 s << ", Action: " << rejectAction->getDescription();
+     241           0 :         return s.str();
+     242           0 : }
+     243             : 
+     244           0 : CylindricalBoundary::CylindricalBoundary() :
+     245           0 :   origin(Vector3d(0,0,0)), height(0), radius(0), limitStep(false), margin(0) {
+     246           0 : }
+     247             : 
+     248           3 : CylindricalBoundary::CylindricalBoundary(Vector3d o, double h, double r) :
+     249           3 :   origin(o), height(h), radius(r), limitStep(false) , margin(0){
+     250           3 : }
+     251             : 
+     252           3 : void CylindricalBoundary::process(Candidate *c) const {
+     253           3 :         Vector3d d = c->current.getPosition() - origin;
+     254           3 :         double R2 = pow(d.x, 2.)+pow(d.y, 2.);
+     255           3 :         double Z = fabs(d.z);
+     256           3 :         if ( R2 < pow(radius, 2.) and Z < height/2.) {
+     257           2 :                 if(limitStep) {
+     258           2 :                         c->limitNextStep(std::min(radius - pow(R2, 0.5), height/2. - Z) + margin);   
+     259             :                 }
+     260             :           return;
+     261             :         }
+     262           1 :         reject(c);
+     263             : }
+     264             : 
+     265           0 : void CylindricalBoundary::setOrigin(Vector3d o) {
+     266             :         origin = o;
+     267           0 : }
+     268           0 : void CylindricalBoundary::setHeight(double h) {
+     269           0 :         height = h;
+     270           0 : }
+     271           0 : void CylindricalBoundary::setRadius(double r) {
+     272           0 :         radius = r;
+     273           0 : }
+     274           1 : void CylindricalBoundary::setLimitStep(bool b) {
+     275           1 :         limitStep = b;
+     276           1 : }
+     277           1 : void CylindricalBoundary::setMargin(double m) {
+     278           1 :         margin = m;
+     279           1 : }
+     280             : 
+     281             : 
+     282           0 : std::string CylindricalBoundary::getDescription() const {
+     283           0 :         std::stringstream s;
+     284           0 :         s << "Cylindrical Boundary: origin = " << origin / kpc << " kpc, ";
+     285           0 :         s << "radius = " << radius / kpc << " kpc, ";
+     286           0 :         s << "height" << height / kpc << " kpc; ";
+     287           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     288           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     289           0 :         if (rejectAction.valid())
+     290           0 :                 s << ", Action: " << rejectAction->getDescription();
+     291           0 :         return s.str();
+     292           0 : }
+     293             : 
+     294             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html b/doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html new file mode 100644 index 000000000..59b7031c8 --- /dev/null +++ b/doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html @@ -0,0 +1,224 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/BreakCondition.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - BreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6317236.6 %
Date:2024-04-08 14:58:22Functions:153839.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MinimumEnergy16setMinimumEnergyEd0
_ZN7crpropa15DetectionLength18setDetectionLengthEd0
_ZN7crpropa15MinimumRedshift18getMinimumRedshiftEv0
_ZN7crpropa15MinimumRedshift18setMinimumRedshiftEd0
_ZN7crpropa15MinimumRigidity18setMinimumRigidityEd0
_ZN7crpropa15MinimumRigidityC2Ed0
_ZN7crpropa19MinimumChargeNumber22setMinimumChargeNumberEi0
_ZN7crpropa23MaximumTrajectoryLength26setMaximumTrajectoryLengthEd0
_ZNK7crpropa13MinimumEnergy14getDescriptionB5cxx11Ev0
_ZNK7crpropa13MinimumEnergy16getMinimumEnergyEv0
_ZNK7crpropa15DetectionLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa15DetectionLength18getDetectionLengthEv0
_ZNK7crpropa15MinimumRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRigidity14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRigidity18getMinimumRigidityEv0
_ZNK7crpropa15MinimumRigidity7processEPNS_9CandidateE0
_ZNK7crpropa19MinimumChargeNumber14getDescriptionB5cxx11Ev0
_ZNK7crpropa19MinimumChargeNumber22getMinimumChargeNumberEv0
_ZNK7crpropa23MaximumTrajectoryLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa23MaximumTrajectoryLength20getObserverPositionsEv0
_ZNK7crpropa23MaximumTrajectoryLength26getMaximumTrajectoryLengthEv0
_ZNK7crpropa26MinimumEnergyPerParticleId14getDescriptionB5cxx11Ev0
_ZNK7crpropa26MinimumEnergyPerParticleId22getMinimumEnergyOthersEv0
_ZN7crpropa15DetectionLengthC2Ed1
_ZN7crpropa15MinimumRedshiftC2Ed1
_ZN7crpropa19MinimumChargeNumberC2Ei1
_ZN7crpropa23MaximumTrajectoryLength19addObserverPositionERKNS_7Vector3IdEE1
_ZN7crpropa26MinimumEnergyPerParticleId22setMinimumEnergyOthersEd1
_ZN7crpropa26MinimumEnergyPerParticleIdC2Ed1
_ZN7crpropa13MinimumEnergyC2Ed2
_ZNK7crpropa15DetectionLength7processEPNS_9CandidateE2
_ZNK7crpropa15MinimumRedshift7processEPNS_9CandidateE2
_ZN7crpropa26MinimumEnergyPerParticleId3addEid3
_ZNK7crpropa19MinimumChargeNumber7processEPNS_9CandidateE4
_ZNK7crpropa26MinimumEnergyPerParticleId7processEPNS_9CandidateE5
_ZN7crpropa23MaximumTrajectoryLengthC2Ed13
_ZNK7crpropa13MinimumEnergy7processEPNS_9CandidateE7644
_ZNK7crpropa23MaximumTrajectoryLength7processEPNS_9CandidateE491649
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/BreakCondition.cpp.func.html b/doc/coverageReport/src/module/BreakCondition.cpp.func.html new file mode 100644 index 000000000..9734252c0 --- /dev/null +++ b/doc/coverageReport/src/module/BreakCondition.cpp.func.html @@ -0,0 +1,224 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/BreakCondition.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - BreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6317236.6 %
Date:2024-04-08 14:58:22Functions:153839.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MinimumEnergy16setMinimumEnergyEd0
_ZN7crpropa13MinimumEnergyC2Ed2
_ZN7crpropa15DetectionLength18setDetectionLengthEd0
_ZN7crpropa15DetectionLengthC2Ed1
_ZN7crpropa15MinimumRedshift18getMinimumRedshiftEv0
_ZN7crpropa15MinimumRedshift18setMinimumRedshiftEd0
_ZN7crpropa15MinimumRedshiftC2Ed1
_ZN7crpropa15MinimumRigidity18setMinimumRigidityEd0
_ZN7crpropa15MinimumRigidityC2Ed0
_ZN7crpropa19MinimumChargeNumber22setMinimumChargeNumberEi0
_ZN7crpropa19MinimumChargeNumberC2Ei1
_ZN7crpropa23MaximumTrajectoryLength19addObserverPositionERKNS_7Vector3IdEE1
_ZN7crpropa23MaximumTrajectoryLength26setMaximumTrajectoryLengthEd0
_ZN7crpropa23MaximumTrajectoryLengthC2Ed13
_ZN7crpropa26MinimumEnergyPerParticleId22setMinimumEnergyOthersEd1
_ZN7crpropa26MinimumEnergyPerParticleId3addEid3
_ZN7crpropa26MinimumEnergyPerParticleIdC2Ed1
_ZNK7crpropa13MinimumEnergy14getDescriptionB5cxx11Ev0
_ZNK7crpropa13MinimumEnergy16getMinimumEnergyEv0
_ZNK7crpropa13MinimumEnergy7processEPNS_9CandidateE7644
_ZNK7crpropa15DetectionLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa15DetectionLength18getDetectionLengthEv0
_ZNK7crpropa15DetectionLength7processEPNS_9CandidateE2
_ZNK7crpropa15MinimumRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRedshift7processEPNS_9CandidateE2
_ZNK7crpropa15MinimumRigidity14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRigidity18getMinimumRigidityEv0
_ZNK7crpropa15MinimumRigidity7processEPNS_9CandidateE0
_ZNK7crpropa19MinimumChargeNumber14getDescriptionB5cxx11Ev0
_ZNK7crpropa19MinimumChargeNumber22getMinimumChargeNumberEv0
_ZNK7crpropa19MinimumChargeNumber7processEPNS_9CandidateE4
_ZNK7crpropa23MaximumTrajectoryLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa23MaximumTrajectoryLength20getObserverPositionsEv0
_ZNK7crpropa23MaximumTrajectoryLength26getMaximumTrajectoryLengthEv0
_ZNK7crpropa23MaximumTrajectoryLength7processEPNS_9CandidateE491649
_ZNK7crpropa26MinimumEnergyPerParticleId14getDescriptionB5cxx11Ev0
_ZNK7crpropa26MinimumEnergyPerParticleId22getMinimumEnergyOthersEv0
_ZNK7crpropa26MinimumEnergyPerParticleId7processEPNS_9CandidateE5
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/BreakCondition.cpp.gcov.html b/doc/coverageReport/src/module/BreakCondition.cpp.gcov.html new file mode 100644 index 000000000..315b82cba --- /dev/null +++ b/doc/coverageReport/src/module/BreakCondition.cpp.gcov.html @@ -0,0 +1,343 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/BreakCondition.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - BreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6317236.6 %
Date:2024-04-08 14:58:22Functions:153839.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/BreakCondition.h"
+       2             : #include "crpropa/ParticleID.h"
+       3             : #include "crpropa/Units.h"
+       4             : 
+       5             : #include <sstream>
+       6             : 
+       7             : namespace crpropa {
+       8             : 
+       9          13 : MaximumTrajectoryLength::MaximumTrajectoryLength(double maxLength) :
+      10          13 :                 maxLength(maxLength) {
+      11          13 : }
+      12             : 
+      13           0 : void MaximumTrajectoryLength::setMaximumTrajectoryLength(double length) {
+      14           0 :         maxLength = length;
+      15           0 : }
+      16             : 
+      17           0 : double MaximumTrajectoryLength::getMaximumTrajectoryLength() const {
+      18           0 :         return maxLength;
+      19             : }
+      20             : 
+      21           1 : void MaximumTrajectoryLength::addObserverPosition(const Vector3d& position) {
+      22           1 :         observerPositions.push_back(position);
+      23           1 : }
+      24             : 
+      25           0 : const std::vector<Vector3d>& MaximumTrajectoryLength::getObserverPositions() const {
+      26           0 :         return observerPositions;
+      27             : }
+      28             : 
+      29           0 : std::string MaximumTrajectoryLength::getDescription() const {
+      30           0 :         std::stringstream s;
+      31           0 :         s << "Maximum trajectory length: " << maxLength / Mpc << " Mpc, ";
+      32           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+      33           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+      34           0 :         if (rejectAction.valid())
+      35           0 :                 s << ", Action: " << rejectAction->getDescription();
+      36           0 :         s << "\n  Observer positions: \n";
+      37           0 :         for (size_t i = 0; i < observerPositions.size(); i++)
+      38           0 :                 s << "    - " << observerPositions[i] / Mpc << " Mpc\n";
+      39           0 :         return s.str();
+      40           0 : }
+      41             : 
+      42      491649 : void MaximumTrajectoryLength::process(Candidate *c) const {
+      43      491649 :         double length = c->getTrajectoryLength();
+      44      491649 :         Vector3d position = c->current.getPosition();
+      45             : 
+      46      491649 :         if(observerPositions.size()) {
+      47             :                 bool inRange = false;
+      48           4 :                 for (size_t i = 0; i < observerPositions.size(); i++) {
+      49           2 :                         double distance = position.getDistanceTo(observerPositions[i]);
+      50           2 :                         if (distance + length < maxLength)
+      51             :                                 inRange = true;
+      52             :                 }
+      53           2 :                 if (!inRange) {
+      54           1 :                         reject(c);
+      55             :                         return;
+      56             :                 }
+      57             :         }
+      58             : 
+      59      491648 :         if (length >= maxLength) {
+      60        1107 :                 reject(c);
+      61             :         } else {
+      62      490541 :                 c->limitNextStep(maxLength - length);
+      63             :         }
+      64             : }
+      65             : 
+      66             : //*****************************************************************************
+      67           2 : MinimumEnergy::MinimumEnergy(double minEnergy) :
+      68           2 :                 minEnergy(minEnergy) {
+      69           2 : }
+      70             : 
+      71           0 : void MinimumEnergy::setMinimumEnergy(double energy) {
+      72           0 :         minEnergy = energy;
+      73           0 : }
+      74             : 
+      75           0 : double MinimumEnergy::getMinimumEnergy() const {
+      76           0 :         return minEnergy;
+      77             : }
+      78             : 
+      79        7644 : void MinimumEnergy::process(Candidate *c) const {
+      80        7644 :         if (c->current.getEnergy() > minEnergy)
+      81             :                 return;
+      82             :         else
+      83           1 :                 reject(c);
+      84             : }
+      85             : 
+      86           0 : std::string MinimumEnergy::getDescription() const {
+      87           0 :         std::stringstream s;
+      88           0 :         s << "Minimum energy: " << minEnergy / EeV << " EeV, ";
+      89           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+      90           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+      91           0 :         if (rejectAction.valid())
+      92           0 :                 s << ", Action: " << rejectAction->getDescription();
+      93           0 :         return s.str();
+      94           0 : }
+      95             : 
+      96             : //*****************************************************************************
+      97           0 : MinimumRigidity::MinimumRigidity(double minRigidity) :
+      98           0 :                 minRigidity(minRigidity) {
+      99           0 : }
+     100             : 
+     101           0 : void MinimumRigidity::setMinimumRigidity(double minRigidity) {
+     102           0 :         this->minRigidity = minRigidity;
+     103           0 : }
+     104             : 
+     105           0 : double MinimumRigidity::getMinimumRigidity() const {
+     106           0 :         return minRigidity;
+     107             : }
+     108             : 
+     109           0 : void MinimumRigidity::process(Candidate *c) const {
+     110           0 :         if (c->current.getRigidity() < minRigidity)
+     111           0 :                 reject(c);
+     112           0 : }
+     113             : 
+     114           0 : std::string MinimumRigidity::getDescription() const {
+     115           0 :         std::stringstream s;
+     116           0 :         s << "Minimum rigidity: " << minRigidity / EeV << " EeV, ";
+     117           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     118           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     119           0 :         if (rejectAction.valid())
+     120           0 :                 s << ", Action: " << rejectAction->getDescription();
+     121           0 :         return s.str();
+     122           0 : }
+     123             : 
+     124             : //*****************************************************************************
+     125           1 : MinimumRedshift::MinimumRedshift(double zmin) :
+     126           1 :                 zmin(zmin) {
+     127           1 : }
+     128             : 
+     129           0 : void MinimumRedshift::setMinimumRedshift(double z) {
+     130           0 :         zmin = z;
+     131           0 : }
+     132             : 
+     133           0 : double MinimumRedshift::getMinimumRedshift() {
+     134           0 :         return zmin;
+     135             : }
+     136             : 
+     137           2 : void MinimumRedshift::process(Candidate* c) const {
+     138           2 :         if (c->getRedshift() > zmin)
+     139             :                 return;
+     140             :         else
+     141           1 :                 reject(c);
+     142             : }
+     143             : 
+     144           0 : std::string MinimumRedshift::getDescription() const {
+     145           0 :         std::stringstream s;
+     146           0 :         s << "Minimum redshift: " << zmin << ", ";
+     147           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     148           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     149           0 :         if (rejectAction.valid())
+     150           0 :                 s << ", Action: " << rejectAction->getDescription();
+     151           0 :         return s.str();
+     152           0 : }
+     153             : 
+     154             : //*****************************************************************************
+     155           1 : MinimumChargeNumber::MinimumChargeNumber(int minChargeNumber) :
+     156           1 :                 minChargeNumber(minChargeNumber) {
+     157           1 : }
+     158             : 
+     159           0 : void MinimumChargeNumber::setMinimumChargeNumber(int chargeNumber) {
+     160           0 :         minChargeNumber = chargeNumber;
+     161           0 : }
+     162             : 
+     163           0 : int MinimumChargeNumber::getMinimumChargeNumber() const {
+     164           0 :         return minChargeNumber;
+     165             : }
+     166             : 
+     167           4 : void MinimumChargeNumber::process(Candidate *c) const {
+     168           4 :         if (chargeNumber(c->current.getId()) > minChargeNumber)
+     169             :                 return;
+     170             :         else
+     171           2 :                 reject(c);
+     172             : }
+     173             : 
+     174           0 : std::string MinimumChargeNumber::getDescription() const {
+     175           0 :         std::stringstream s;
+     176           0 :         s << "Minimum charge number: " << minChargeNumber;
+     177           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     178           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     179           0 :         if (rejectAction.valid())
+     180           0 :                 s << ", Action: " << rejectAction->getDescription();
+     181           0 :         return s.str();
+     182           0 : }
+     183             : 
+     184             : //*****************************************************************************
+     185           1 : MinimumEnergyPerParticleId::MinimumEnergyPerParticleId(double minEnergyOthers) {
+     186           1 :         setMinimumEnergyOthers(minEnergyOthers);
+     187           1 : }
+     188             : 
+     189           3 : void MinimumEnergyPerParticleId::add(int id, double energy) {
+     190           3 :         particleIds.push_back(id);
+     191           3 :         minEnergies.push_back(energy);
+     192           3 : }
+     193             : 
+     194           1 : void MinimumEnergyPerParticleId::setMinimumEnergyOthers(double energy) {
+     195           1 :         minEnergyOthers = energy;
+     196           1 : }
+     197             : 
+     198           0 : double MinimumEnergyPerParticleId::getMinimumEnergyOthers() const {
+     199           0 :         return minEnergyOthers;
+     200             : }
+     201             : 
+     202           5 : void MinimumEnergyPerParticleId::process(Candidate *c) const {
+     203          15 :         for (int i = 0; i < particleIds.size(); i++) {
+     204          12 :                 if (c->current.getId() == particleIds[i]) {
+     205           5 :                         if (c->current.getEnergy() < minEnergies[i])
+     206           3 :                                 reject(c);
+     207             :                         else
+     208             :                                 return;
+     209             :                 }
+     210             :         }
+     211             : 
+     212           3 :         if (c->current.getEnergy() < minEnergyOthers)
+     213           1 :                 reject(c);
+     214             :         else
+     215             :                 return;
+     216             : }
+     217             : 
+     218           0 : std::string MinimumEnergyPerParticleId::getDescription() const {
+     219           0 :         std::stringstream s;
+     220           0 :         s << "Minimum energy for non-specified particles: " << minEnergyOthers / eV << " eV";
+     221           0 :         for (int i = 0; i < minEnergies.size(); i++) {
+     222           0 :                 s << "  for particle " << particleIds[i] << " : " << minEnergies[i] / eV << " eV";
+     223             :         }
+     224           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     225           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     226           0 :         if (rejectAction.valid())
+     227           0 :                 s << ", Action: " << rejectAction->getDescription();
+     228           0 :         return s.str();
+     229           0 : }
+     230             : 
+     231             : //*****************************************************************************
+     232           1 : DetectionLength::DetectionLength(double detLength) :
+     233           1 :                 detLength(detLength) {
+     234           1 : }
+     235             : 
+     236           0 : void DetectionLength::setDetectionLength(double length) {
+     237           0 :         detLength = length;
+     238           0 : }
+     239             : 
+     240           0 : double DetectionLength::getDetectionLength() const {
+     241           0 :         return detLength;
+     242             : }
+     243             : 
+     244             : 
+     245           0 : std::string DetectionLength::getDescription() const {
+     246           0 :         std::stringstream s;
+     247           0 :         s << "Detection length: " << detLength / kpc << " kpc, ";
+     248           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
+     249           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
+     250           0 :         if (rejectAction.valid())
+     251           0 :                 s << ", Action: " << rejectAction->getDescription();
+     252           0 :         return s.str();
+     253           0 : }
+     254             : 
+     255           2 : void DetectionLength::process(Candidate *c) const {
+     256           2 :         double length = c->getTrajectoryLength();
+     257           2 :         double step = c->getCurrentStep();
+     258             : 
+     259           2 :         if (length >= detLength && length - step < detLength) {
+     260           1 :                 reject(c);
+     261             :         } else {
+     262           1 :                 c->limitNextStep(detLength - length);
+     263             :         }
+     264           2 : }
+     265             : 
+     266             : 
+     267             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html b/doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html new file mode 100644 index 000000000..d7f065f98 --- /dev/null +++ b/doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/CandidateSplitting.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - CandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:536186.9 %
Date:2024-04-08 14:58:22Functions:101190.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18CandidateSplittingC2Ev0
_ZN7crpropa18CandidateSplitting16setEnergyBinsDSAEddi1
_ZN7crpropa18CandidateSplittingC2Eddi1
_ZNK7crpropa18CandidateSplitting16getMinimalWeightEv1
_ZNK7crpropa18CandidateSplitting9getNsplitEv1
_ZN7crpropa18CandidateSplitting13setEnergyBinsEdddb3
_ZN7crpropa18CandidateSplittingC2Eiddddb3
_ZN7crpropa18CandidateSplitting16setMinimalWeightEd4
_ZN7crpropa18CandidateSplitting9setNsplitEi4
_ZNK7crpropa18CandidateSplitting13getEnergyBinsEv6
_ZNK7crpropa18CandidateSplitting7processEPNS_9CandidateE6
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/CandidateSplitting.cpp.func.html b/doc/coverageReport/src/module/CandidateSplitting.cpp.func.html new file mode 100644 index 000000000..8031c35f7 --- /dev/null +++ b/doc/coverageReport/src/module/CandidateSplitting.cpp.func.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/CandidateSplitting.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - CandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:536186.9 %
Date:2024-04-08 14:58:22Functions:101190.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18CandidateSplitting13setEnergyBinsEdddb3
_ZN7crpropa18CandidateSplitting16setEnergyBinsDSAEddi1
_ZN7crpropa18CandidateSplitting16setMinimalWeightEd4
_ZN7crpropa18CandidateSplitting9setNsplitEi4
_ZN7crpropa18CandidateSplittingC2Eddi1
_ZN7crpropa18CandidateSplittingC2Eiddddb3
_ZN7crpropa18CandidateSplittingC2Ev0
_ZNK7crpropa18CandidateSplitting13getEnergyBinsEv6
_ZNK7crpropa18CandidateSplitting16getMinimalWeightEv1
_ZNK7crpropa18CandidateSplitting7processEPNS_9CandidateE6
_ZNK7crpropa18CandidateSplitting9getNsplitEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html b/doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html new file mode 100644 index 000000000..c8cd11eb0 --- /dev/null +++ b/doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html @@ -0,0 +1,194 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/CandidateSplitting.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - CandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:536186.9 %
Date:2024-04-08 14:58:22Functions:101190.9 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/CandidateSplitting.h"
+       2             : 
+       3             : namespace crpropa {
+       4             : 
+       5           0 : CandidateSplitting::CandidateSplitting() {
+       6             :         // no particle splitting if EnergyBins and NSplit are not specified
+       7           0 :         setNsplit(0);
+       8           0 :         setMinimalWeight(1.);
+       9           0 : }
+      10             : 
+      11           3 : CandidateSplitting::CandidateSplitting(int nSplit, double Emin, double Emax,  double nBins, double minWeight, bool log) {
+      12           3 :         setNsplit(nSplit);
+      13           3 :         setEnergyBins(Emin, Emax, nBins, log);
+      14           3 :         setMinimalWeight(minWeight);
+      15           3 : }
+      16             : 
+      17           1 : CandidateSplitting::CandidateSplitting(double spectralIndex, double Emin, int nBins)  {
+      18             :         // to use with Diffusive Shock Acceleration
+      19           1 :         if (spectralIndex > 0){
+      20           0 :                 throw std::runtime_error(
+      21           0 :                                 "CandidateSplitting: spectralIndex > 0 !"); 
+      22             :         }
+      23             : 
+      24           1 :         setNsplit(2); // always split in 2, calculate bins in energy for given spectrum:
+      25           1 :         double dE = pow(1. / 2, 1. / (spectralIndex + 1)); 
+      26           1 :         setEnergyBinsDSA(Emin, dE, nBins);
+      27           1 :         setMinimalWeight(1. / pow(2, nBins));
+      28           1 : }
+      29             : 
+      30           6 : void CandidateSplitting::process(Candidate *c) const {
+      31           6 :         double currE = c->current.getEnergy(); 
+      32           6 :         double prevE = c->previous.getEnergy();
+      33             : 
+      34           6 :         if (c->getWeight() <= minWeight){
+      35             :                 // minimal weight reached, no splitting
+      36             :                 return;
+      37             :         }
+      38           5 :         if (currE < Ebins[0] || nSplit == 0 ){
+      39             :                 // current energy is smaller than first bin -> no splitting
+      40             :                 // or, number of splits = 0
+      41             :                 return;
+      42             :         }
+      43           4 :         for (size_t i = 0; i < Ebins.size(); ++i){
+      44             :                 
+      45           4 :                 if( prevE < Ebins[i] ){
+      46             :                         // previous energy is in energy bin [i-1, i]
+      47           3 :                         if(currE < Ebins[i]){
+      48             :                                 //assuming that dE greater than 0, prevE and E in same energy bin -> no splitting
+      49             :                                 return;
+      50             :                         }
+      51             :                         // current energy is in energy bin [i,i+1] or higher -> particle splitting for each crossing
+      52           4 :                         for (size_t j = i; j < Ebins.size(); ++j ){
+      53             : 
+      54             :                                 // adapted from Acceleration Module:
+      55           4 :                                 c->updateWeight(1. / nSplit); // * 1/n_split
+      56             : 
+      57           8 :                                 for (int i = 1; i < nSplit; i++) {
+      58             :                                 
+      59           4 :                                         ref_ptr<Candidate> new_candidate = c->clone(false);
+      60           4 :                                         new_candidate->parent = c;
+      61           4 :                                         new_candidate->previous.setEnergy(currE); // so that new candidate is not split again in next step!
+      62             :                                         c->addSecondary(new_candidate);
+      63             :                                 }
+      64           4 :                                 if (j < Ebins.size()-1 && currE < Ebins[j+1]){
+      65             :                                         // candidate is in energy bin [j, j+1] -> no further splitting
+      66             :                                         return;
+      67             :                                 }
+      68             :                         }
+      69             :                         return;
+      70             :                 }
+      71             :         }
+      72             : }
+      73             : 
+      74           3 : void CandidateSplitting::setEnergyBins(double Emin, double Emax, double nBins, bool log) {
+      75           3 :         Ebins.resize(0);
+      76           3 :         if (Emin > Emax){
+      77           0 :                 throw std::runtime_error(
+      78           0 :                                 "CandidateSplitting: Emin > Emax!");
+      79             :         }
+      80           3 :         double dE = (Emax-Emin)/nBins;
+      81          14 :         for (size_t i = 0; i < nBins; ++i) {
+      82          11 :                 if (log == true) {
+      83           4 :                         Ebins.push_back(Emin * pow(Emax / Emin, i / (nBins - 1.0)));
+      84             :                 } else {
+      85           7 :                         Ebins.push_back(Emin + i * dE);
+      86             :                 }
+      87             :         }
+      88           3 : }
+      89             : 
+      90           1 : void CandidateSplitting::setEnergyBinsDSA(double Emin, double dE, int n) {
+      91           1 :         Ebins.resize(0);
+      92           5 :         for (size_t i = 1; i < n + 1; ++i) {
+      93           4 :                 Ebins.push_back(Emin * pow(dE, i));
+      94             :         }
+      95           1 : }
+      96             : 
+      97           6 : const std::vector<double>& CandidateSplitting::getEnergyBins() const {
+      98           6 :         return Ebins;
+      99             : }
+     100             : 
+     101           4 : void CandidateSplitting::setNsplit(int n) {
+     102           4 :         nSplit = n;
+     103           4 : }
+     104             : 
+     105           4 : void CandidateSplitting::setMinimalWeight(double w) {
+     106           4 :         minWeight = w;
+     107           4 : }
+     108             : 
+     109           1 : int CandidateSplitting::getNsplit() const {
+     110           1 :         return nSplit;
+     111             : }
+     112             : 
+     113           1 : double CandidateSplitting::getMinimalWeight() const {
+     114           1 :         return minWeight;
+     115             : }
+     116             : 
+     117             : } // end namespace crpropa
+     118             : 
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html b/doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html new file mode 100644 index 000000000..119a389bf --- /dev/null +++ b/doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html @@ -0,0 +1,172 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/DiffusionSDE.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - DiffusionSDE.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15420276.2 %
Date:2024-04-08 14:58:22Functions:222588.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa12DiffusionSDE14getDescriptionB5cxx11Ev0
_ZNK7crpropa12DiffusionSDE16getMagneticFieldEv0
_ZNK7crpropa12DiffusionSDE17getAdvectionFieldEv0
_ZNK7crpropa12DiffusionSDE10getEpsilonEv1
_ZNK7crpropa12DiffusionSDE12getToleranceEv1
_ZNK7crpropa12DiffusionSDE14getMaximumStepEv1
_ZNK7crpropa12DiffusionSDE14getMinimumStepEv1
_ZN7crpropa12DiffusionSDE17setAdvectionFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEENS1_INS_14AdvectionFieldEEEdddd3
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEEdddd4
_ZNK7crpropa12DiffusionSDE8getAlphaEv5
_ZNK7crpropa12DiffusionSDE8getScaleEv5
_ZN7crpropa12DiffusionSDE10setEpsilonEd7
_ZN7crpropa12DiffusionSDE12setToleranceEd7
_ZN7crpropa12DiffusionSDE14setMaximumStepEd7
_ZN7crpropa12DiffusionSDE14setMinimumStepEd7
_ZN7crpropa12DiffusionSDE16setMagneticFieldENS_7ref_ptrINS_13MagneticFieldEEE7
_ZN7crpropa12DiffusionSDE8setAlphaEd7
_ZN7crpropa12DiffusionSDE8setScaleEd7
_ZNK7crpropa12DiffusionSDE9driftStepERKNS_7Vector3IdEERS2_d120001
_ZNK7crpropa12DiffusionSDE27getAdvectionFieldAtPositionENS_7Vector3IdEE120002
_ZNK7crpropa12DiffusionSDE16calculateBTensorEdPdNS_7Vector3IdEES3_d480002
_ZNK7crpropa12DiffusionSDE7processEPNS_9CandidateE480003
_ZNK7crpropa12DiffusionSDE7tryStepERKNS_7Vector3IdEERS2_S5_dd960004
_ZNK7crpropa12DiffusionSDE26getMagneticFieldAtPositionENS_7Vector3IdEEd5760025
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/DiffusionSDE.cpp.func.html b/doc/coverageReport/src/module/DiffusionSDE.cpp.func.html new file mode 100644 index 000000000..d4e981a1a --- /dev/null +++ b/doc/coverageReport/src/module/DiffusionSDE.cpp.func.html @@ -0,0 +1,172 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/DiffusionSDE.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - DiffusionSDE.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15420276.2 %
Date:2024-04-08 14:58:22Functions:222588.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12DiffusionSDE10setEpsilonEd7
_ZN7crpropa12DiffusionSDE12setToleranceEd7
_ZN7crpropa12DiffusionSDE14setMaximumStepEd7
_ZN7crpropa12DiffusionSDE14setMinimumStepEd7
_ZN7crpropa12DiffusionSDE16setMagneticFieldENS_7ref_ptrINS_13MagneticFieldEEE7
_ZN7crpropa12DiffusionSDE17setAdvectionFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZN7crpropa12DiffusionSDE8setAlphaEd7
_ZN7crpropa12DiffusionSDE8setScaleEd7
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEENS1_INS_14AdvectionFieldEEEdddd3
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEEdddd4
_ZNK7crpropa12DiffusionSDE10getEpsilonEv1
_ZNK7crpropa12DiffusionSDE12getToleranceEv1
_ZNK7crpropa12DiffusionSDE14getDescriptionB5cxx11Ev0
_ZNK7crpropa12DiffusionSDE14getMaximumStepEv1
_ZNK7crpropa12DiffusionSDE14getMinimumStepEv1
_ZNK7crpropa12DiffusionSDE16calculateBTensorEdPdNS_7Vector3IdEES3_d480002
_ZNK7crpropa12DiffusionSDE16getMagneticFieldEv0
_ZNK7crpropa12DiffusionSDE17getAdvectionFieldEv0
_ZNK7crpropa12DiffusionSDE26getMagneticFieldAtPositionENS_7Vector3IdEEd5760025
_ZNK7crpropa12DiffusionSDE27getAdvectionFieldAtPositionENS_7Vector3IdEE120002
_ZNK7crpropa12DiffusionSDE7processEPNS_9CandidateE480003
_ZNK7crpropa12DiffusionSDE7tryStepERKNS_7Vector3IdEERS2_S5_dd960004
_ZNK7crpropa12DiffusionSDE8getAlphaEv5
_ZNK7crpropa12DiffusionSDE8getScaleEv5
_ZNK7crpropa12DiffusionSDE9driftStepERKNS_7Vector3IdEERS2_d120001
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html b/doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html new file mode 100644 index 000000000..51ca09aab --- /dev/null +++ b/doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html @@ -0,0 +1,480 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/DiffusionSDE.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - DiffusionSDE.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15420276.2 %
Date:2024-04-08 14:58:22Functions:222588.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/DiffusionSDE.h"
+       2             : 
+       3             : 
+       4             : using namespace crpropa;
+       5             : 
+       6             : // Defining Cash-Karp coefficients
+       7             : const double a[] = { 0., 0., 0., 0., 0., 0., 1. / 5., 0., 0., 0., 0.,
+       8             :                 0., 3. / 40., 9. / 40., 0., 0., 0., 0., 3. / 10., -9. / 10., 6. / 5.,
+       9             :                 0., 0., 0., -11. / 54., 5. / 2., -70. / 27., 35. / 27., 0., 0., 1631.
+      10             :                                 / 55296., 175. / 512., 575. / 13824., 44275. / 110592., 253.
+      11             :                                 / 4096., 0. };
+      12             : 
+      13             : const double b[] = { 37. / 378., 0, 250. / 621., 125. / 594., 0., 512.
+      14             :                 / 1771. };
+      15             : 
+      16             : const double bs[] = { 2825. / 27648., 0., 18575. / 48384., 13525.
+      17             :                 / 55296., 277. / 14336., 1. / 4. };
+      18             : 
+      19             : 
+      20             : 
+      21           4 : DiffusionSDE::DiffusionSDE(ref_ptr<MagneticField> magneticField, double tolerance,
+      22           4 :                                  double minStep, double maxStep, double epsilon) :
+      23           4 :         minStep(0)
+      24             : {
+      25           4 :         setMagneticField(magneticField);
+      26           4 :         setMaximumStep(maxStep);
+      27           4 :         setMinimumStep(minStep);
+      28           4 :         setTolerance(tolerance);
+      29           4 :         setEpsilon(epsilon);
+      30           4 :         setScale(1.);
+      31           4 :         setAlpha(1./3.);
+      32           4 :         }
+      33             : 
+      34           3 : DiffusionSDE::DiffusionSDE(ref_ptr<MagneticField> magneticField, ref_ptr<AdvectionField> advectionField, double tolerance, double minStep, double maxStep, double epsilon) :
+      35           3 :         minStep(0)
+      36             : {
+      37           6 :         setMagneticField(magneticField);
+      38           3 :         setAdvectionField(advectionField);
+      39           3 :         setMaximumStep(maxStep);
+      40           3 :         setMinimumStep(minStep);
+      41           3 :         setTolerance(tolerance);
+      42           3 :         setEpsilon(epsilon);
+      43           3 :         setScale(1.);
+      44           3 :         setAlpha(1./3.);
+      45           3 :         }
+      46             : 
+      47      480003 : void DiffusionSDE::process(Candidate *candidate) const {
+      48             : 
+      49             :     // save the new previous particle state
+      50             : 
+      51      480003 :         ParticleState &current = candidate->current;
+      52             :         candidate->previous = current;
+      53             : 
+      54      480003 :         double h = clip(candidate->getNextStep(), minStep, maxStep) / c_light;
+      55      480003 :         Vector3d PosIn = current.getPosition();
+      56      480003 :         Vector3d DirIn = current.getDirection();
+      57             : 
+      58             :     // rectilinear propagation for neutral particles
+      59             :     // If an advection field is provided the drift is also included
+      60      480003 :         if (current.getCharge() == 0) {
+      61           1 :                 Vector3d dir = current.getDirection();
+      62           1 :                 Vector3d Pos = current.getPosition();
+      63             : 
+      64             :                 Vector3d LinProp(0.);
+      65           1 :                 if (advectionField){
+      66           0 :                         driftStep(Pos, LinProp, h);
+      67             :                 }
+      68             : 
+      69           1 :                 current.setPosition(Pos + LinProp + dir*h*c_light);
+      70           1 :                 candidate->setCurrentStep(h * c_light);
+      71           1 :                 candidate->setNextStep(maxStep);
+      72             :                 return;
+      73             :         }
+      74             : 
+      75      480002 :         double z = candidate->getRedshift();
+      76      480002 :         double rig = current.getEnergy() / current.getCharge();
+      77             : 
+      78             : 
+      79             :     // Calculate the Diffusion tensor
+      80      480002 :         double BTensor[] = {0., 0., 0., 0., 0., 0., 0., 0., 0.};
+      81      480002 :         calculateBTensor(rig, BTensor, PosIn, DirIn, z);
+      82             : 
+      83             : 
+      84             :     // Generate random numbers
+      85      480002 :         double eta[] = {0., 0., 0.};
+      86     1920008 :         for(size_t i=0; i < 3; i++) {
+      87     1440006 :                 eta[i] =  Random::instance().randNorm();
+      88             :         }
+      89             : 
+      90      480002 :         double TStep = BTensor[0] * eta[0];
+      91      480002 :         double NStep = BTensor[4] * eta[1];
+      92      480002 :         double BStep = BTensor[8] * eta[2];
+      93             : 
+      94             :         Vector3d TVec(0.);
+      95             :         Vector3d NVec(0.);
+      96             :         Vector3d BVec(0.);
+      97             : 
+      98             :         Vector3d DirOut = Vector3d(0.);
+      99             : 
+     100             : 
+     101      480002 :         double propTime = TStep * sqrt(h) / c_light;
+     102             :         size_t counter = 0;
+     103             :         double r=42.; //arbitrary number larger than one
+     104             : 
+     105             :         do {
+     106             :                 Vector3d PosOut = Vector3d(0.);
+     107             :                 Vector3d PosErr = Vector3d(0.);
+     108      480002 :                 tryStep(PosIn, PosOut, PosErr, z, propTime);
+     109             :             // calculate the relative position error r and the next time step h
+     110      480002 :                 r = PosErr.getR() / tolerance;
+     111      480002 :                 propTime *= 0.5;
+     112      480002 :                 counter += 1;
+     113             : 
+     114             :     // Check for better break condition
+     115      480002 :         } while (r > 1 && fabs(propTime) >= minStep/c_light);
+     116             : 
+     117             : 
+     118      480002 :         size_t stepNumber = pow(2, counter-1);
+     119      480002 :         double allowedTime = TStep * sqrt(h) / c_light / stepNumber;
+     120             :         Vector3d Start = PosIn;
+     121             :         Vector3d PosOut = Vector3d(0.);
+     122             :         Vector3d PosErr = Vector3d(0.);
+     123      960004 :         for (size_t j=0; j<stepNumber; j++) {
+     124      480002 :                 tryStep(Start, PosOut, PosErr, z, allowedTime);
+     125             :                 Start = PosOut;
+     126             :         }
+     127             : 
+     128             :     // Normalize the tangent vector
+     129      480002 :         TVec = (PosOut-PosIn).getUnitVector();
+     130             :     // Exception: If the magnetic field vanishes: Use only advection.
+     131             :     // If an advection field is not provided --> rectilinear propagation.
+     132             :         double tTest = TVec.getR();
+     133      480002 :         if (tTest != tTest) {
+     134           2 :                 Vector3d dir = current.getDirection();
+     135           2 :                 Vector3d Pos = current.getPosition();
+     136             :                 Vector3d LinProp(0.);
+     137           2 :                 if (advectionField){
+     138           1 :                         driftStep(Pos, LinProp, h);
+     139           1 :                         current.setPosition(Pos + LinProp);
+     140           1 :                         candidate->setCurrentStep(h*c_light);
+     141           1 :                         double newStep = 5*h*c_light;
+     142             :                         newStep = clip(newStep, minStep, maxStep);
+     143           1 :                         candidate->setNextStep(newStep);
+     144             :                         return;
+     145             :                 }
+     146           1 :                 current.setPosition(Pos + dir*h*c_light);
+     147           1 :                 candidate->setCurrentStep(h*c_light);
+     148           1 :                 double newStep = 5*h*c_light;
+     149           1 :                 newStep = clip(newStep, minStep, maxStep);
+     150           1 :                 candidate->setNextStep(newStep);
+     151           1 :                 return;
+     152             :         }
+     153             : 
+     154             :     // Choose a random perpendicular vector as the Normal-vector.
+     155             :     // Prevent 'nan's in the NVec-vector in the case of <TVec, NVec> = 0.
+     156      960000 :         while (NVec.getR()==0.){
+     157      480000 :                 Vector3d RandomVector = Random::instance().randVector();
+     158             :                 NVec = TVec.cross( RandomVector );
+     159             :         }
+     160      480000 :         NVec = NVec.getUnitVector();
+     161             : 
+     162             :     // Calculate the Binormal-vector
+     163      480000 :         BVec = (TVec.cross(NVec)).getUnitVector();
+     164             : 
+     165             :     // Calculate the advection step
+     166             :         Vector3d LinProp(0.);
+     167      480000 :         if (advectionField){
+     168      120000 :                 driftStep(PosIn, LinProp, h);
+     169             :         }
+     170             : 
+     171             :     // Integration of the SDE with a Mayorama-Euler-method
+     172      480000 :         Vector3d PO = PosOut + LinProp + (NVec * NStep + BVec * BStep) * sqrt(h) ;
+     173             : 
+     174             :     // Throw error message if something went wrong with propagation.
+     175             :     // Deactivate candidate.
+     176             :         bool NaN = std::isnan(PO.getR());
+     177      480000 :         if (NaN == true){
+     178           0 :                   candidate->setActive(false);
+     179           0 :                   KISS_LOG_WARNING
+     180           0 :                         << "\nCandidate with 'nan'-position occured: \n"
+     181           0 :                         << "position = " << PO << "\n"
+     182           0 :                         << "PosIn = " << PosIn << "\n"
+     183           0 :                         << "TVec = " << TVec << "\n"
+     184           0 :                         << "TStep = " << std::abs(TStep) << "\n"
+     185           0 :                         << "NVec = " << NVec << "\n"
+     186             :                         << "NStep = " << NStep << "\n"
+     187           0 :                         << "BVec = " << BVec << "\n"
+     188             :                         << "BStep = " << BStep << "\n"
+     189           0 :                         << "Candidate is deactivated!\n";
+     190             :                   return;
+     191             :         }
+     192             : 
+     193             :         //DirOut = (PO - PosIn - LinProp).getUnitVector(); //Advection does not change the momentum vector
+     194             :         // Random direction around the tangential direction accounts for the pitch angle average.
+     195      480000 :         DirOut = Random::instance().randConeVector(TVec, M_PI/2.);
+     196      480000 :         current.setPosition(PO);
+     197      480000 :         current.setDirection(DirOut);
+     198      480000 :         candidate->setCurrentStep(h * c_light);
+     199             : 
+     200             :         double nextStep;
+     201      480000 :         if (stepNumber>1){
+     202           0 :                 nextStep = h*pow(stepNumber, -2.)*c_light;
+     203             :         }
+     204             :         else {
+     205      480000 :                 nextStep = 4 * h*c_light;
+     206             :         }
+     207             : 
+     208      480000 :         candidate->setNextStep(nextStep);
+     209             : 
+     210             :         // Debugging and Testing
+     211             :         // Delete comments if additional information should be stored in candidate
+     212             :         // This property "arcLength" can be interpreted as the effective arclength
+     213             :         // of the propagation along a magnetic field line.
+     214             : 
+     215             : /*
+     216             :         const std::string AL = "arcLength";
+     217             :         if (candidate->hasProperty(AL) == false){
+     218             :           double arcLen = (TStep + NStep + BStep) * sqrt(h);
+     219             :           candidate->setProperty(AL, arcLen);
+     220             :           return;
+     221             :         }
+     222             :         else {
+     223             :           double arcLen = candidate->getProperty(AL);
+     224             :           arcLen += (TStep + NStep + BStep) * sqrt(h);
+     225             :           candidate->setProperty(AL, arcLen);
+     226             :         }
+     227             : */
+     228             : 
+     229             : }
+     230             : 
+     231             : 
+     232      960004 : void DiffusionSDE::tryStep(const Vector3d &PosIn, Vector3d &POut, Vector3d &PosErr,double z, double propStep) const {
+     233             : 
+     234             :         Vector3d k[] = {Vector3d(0.),Vector3d(0.),Vector3d(0.),Vector3d(0.),Vector3d(0.),Vector3d(0.)};
+     235             :         POut = PosIn;
+     236             :         //calculate the sum k_i * b_i
+     237     6720028 :         for (size_t i = 0; i < 6; i++) {
+     238             : 
+     239             :                 Vector3d y_n = PosIn;
+     240    20160084 :                 for (size_t j = 0; j < i; j++)
+     241    14400060 :                   y_n += k[j] * a[i * 6 + j] * propStep;
+     242             : 
+     243             :                 // update k_i = direction of the regular magnetic mean field
+     244     5760024 :                 Vector3d BField = getMagneticFieldAtPosition(y_n, z);
+     245             : 
+     246     5760024 :                 k[i] = BField.getUnitVector() * c_light;
+     247             : 
+     248     5760024 :                 POut += k[i] * b[i] * propStep;
+     249     5760024 :                 PosErr +=  (k[i] * (b[i] - bs[i])) * propStep / kpc;
+     250             : 
+     251             :         }
+     252      960004 : }
+     253             : 
+     254      120001 : void DiffusionSDE::driftStep(const Vector3d &pos, Vector3d &linProp, double h) const {
+     255      120001 :         Vector3d advField = getAdvectionFieldAtPosition(pos);
+     256             :         linProp += advField * h;
+     257      120001 :         return;
+     258             : }
+     259             : 
+     260      480002 : void DiffusionSDE::calculateBTensor(double r, double BTen[], Vector3d pos, Vector3d dir, double z) const {
+     261             : 
+     262      480002 :     double DifCoeff = scale * 6.1e24 * pow((std::abs(r) / 4.0e9), alpha);
+     263      480002 :     BTen[0] = pow( 2  * DifCoeff, 0.5);
+     264      480002 :     BTen[4] = pow(2 * epsilon * DifCoeff, 0.5);
+     265      480002 :     BTen[8] = pow(2 * epsilon * DifCoeff, 0.5);
+     266      480002 :     return;
+     267             : 
+     268             : }
+     269             : 
+     270             : 
+     271           7 : void DiffusionSDE::setMinimumStep(double min) {
+     272           7 :         if (min < 0)
+     273           0 :                 throw std::runtime_error("DiffusionSDE: minStep < 0 ");
+     274           7 :         if (min > maxStep)
+     275           0 :                 throw std::runtime_error("DiffusionSDE: minStep > maxStep");
+     276           7 :         minStep = min;
+     277           7 : }
+     278             : 
+     279           7 : void DiffusionSDE::setMaximumStep(double max) {
+     280           7 :         if (max < minStep)
+     281           0 :                 throw std::runtime_error("DiffusionSDE: maxStep < minStep");
+     282           7 :         maxStep = max;
+     283           7 : }
+     284             : 
+     285             : 
+     286           7 : void DiffusionSDE::setTolerance(double tol) {
+     287           7 :         if ((tol > 1) or (tol < 0))
+     288           0 :                 throw std::runtime_error(
+     289           0 :                                 "DiffusionSDE: tolerance error not in range 0-1");
+     290           7 :         tolerance = tol;
+     291           7 : }
+     292             : 
+     293           7 : void DiffusionSDE::setEpsilon(double e) {
+     294           7 :         if ((e > 1) or (e < 0))
+     295           0 :                 throw std::runtime_error(
+     296           0 :                                 "DiffusionSDE: epsilon not in range 0-1");
+     297           7 :         epsilon = e;
+     298           7 : }
+     299             : 
+     300             : 
+     301           7 : void DiffusionSDE::setAlpha(double a) {
+     302           7 :         if ((a > 2.) or (a < 0))
+     303           0 :                 throw std::runtime_error(
+     304           0 :                                 "DiffusionSDE: alpha not in range 0-2");
+     305           7 :         alpha = a;
+     306           7 : }
+     307             : 
+     308           7 : void DiffusionSDE::setScale(double s) {
+     309           7 :         if (s < 0)
+     310           0 :                 throw std::runtime_error(
+     311           0 :                                 "DiffusionSDE: Scale error: Scale < 0");
+     312           7 :         scale = s;
+     313           7 : }
+     314             : 
+     315           7 : void DiffusionSDE::setMagneticField(ref_ptr<MagneticField> f) {
+     316           7 :         magneticField = f;
+     317           7 : }
+     318             : 
+     319           3 : void DiffusionSDE::setAdvectionField(ref_ptr<AdvectionField> f) {
+     320           3 :         advectionField = f;
+     321           3 : }
+     322             : 
+     323           1 : double DiffusionSDE::getMinimumStep() const {
+     324           1 :         return minStep;
+     325             : }
+     326             : 
+     327           1 : double DiffusionSDE::getMaximumStep() const {
+     328           1 :         return maxStep;
+     329             : }
+     330             : 
+     331           1 : double DiffusionSDE::getTolerance() const {
+     332           1 :         return tolerance;
+     333             : }
+     334             : 
+     335           1 : double DiffusionSDE::getEpsilon() const {
+     336           1 :         return epsilon;
+     337             : }
+     338             : 
+     339           5 : double DiffusionSDE::getAlpha() const {
+     340           5 :         return alpha;
+     341             : }
+     342             : 
+     343           5 : double DiffusionSDE::getScale() const {
+     344           5 :         return scale;
+     345             : }
+     346             : 
+     347           0 : ref_ptr<MagneticField> DiffusionSDE::getMagneticField() const {
+     348           0 :         return magneticField;
+     349             : }
+     350             : 
+     351     5760025 : Vector3d DiffusionSDE::getMagneticFieldAtPosition(Vector3d pos, double z) const {
+     352             :         Vector3d B(0, 0, 0);
+     353             :         try {
+     354             :                 // check if field is valid and use the field vector at the
+     355             :                 // position pos with the redshift z
+     356     5760025 :                 if (magneticField.valid())
+     357     5760025 :                         B = magneticField->getField(pos, z);
+     358             :         }
+     359           0 :         catch (std::exception &e) {
+     360           0 :                 KISS_LOG_ERROR  << "DiffusionSDE: Exception in DiffusionSDE::getMagneticFieldAtPosition.\n"
+     361           0 :                                 << e.what();
+     362           0 :         }       
+     363     5760025 :         return B;
+     364             : }
+     365             : 
+     366           0 : ref_ptr<AdvectionField> DiffusionSDE::getAdvectionField() const {
+     367           0 :         return advectionField;
+     368             : }
+     369             : 
+     370      120002 : Vector3d DiffusionSDE::getAdvectionFieldAtPosition(Vector3d pos) const {
+     371             :         Vector3d AdvField(0.);
+     372             :         try {
+     373             :                 // check if field is valid and use the field vector at the
+     374             :                 // position pos
+     375      120002 :                 if (advectionField.valid())
+     376      120002 :                         AdvField = advectionField->getField(pos);
+     377             :         }
+     378           0 :         catch (std::exception &e) {
+     379           0 :                 KISS_LOG_ERROR  << "DiffusionSDE: Exception in DiffusionSDE::getAdvectionFieldAtPosition.\n"
+     380           0 :                                 << e.what();
+     381           0 :         }
+     382      120002 :         return AdvField;
+     383             : }
+     384             : 
+     385           0 : std::string DiffusionSDE::getDescription() const {
+     386           0 :         std::stringstream s;
+     387           0 :         s << "minStep: " << minStep / kpc  << " kpc, ";
+     388           0 :         s << "maxStep: " << maxStep / kpc  << " kpc, ";
+     389           0 :         s << "tolerance: " << tolerance << "\n";
+     390             : 
+     391           0 :         if (epsilon != 0.1) {
+     392           0 :           s << "epsilon: " << epsilon << ", ";
+     393             :           }
+     394             : 
+     395           0 :         if (alpha != 1./3.) {
+     396           0 :           s << "alpha: " << alpha << "\n";
+     397             :           }
+     398             : 
+     399           0 :         if (scale != 1.) {
+     400           0 :           s << "D_0: " << scale*6.1e24 << " m^2/s" << "\n";
+     401             :           }
+     402             : 
+     403           0 :         return s.str();
+     404           0 : }
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html new file mode 100644 index 000000000..a80dbd404 --- /dev/null +++ b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMDoublePairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMDoublePairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:687294.4 %
Date:2024-04-08 14:58:22Functions:1010100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22EMDoublePairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa22EMDoublePairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa22EMDoublePairProduction7processEPNS_9CandidateE1
_ZNK7crpropa22EMDoublePairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa22EMDoublePairProduction11setThinningEd3
_ZN7crpropa22EMDoublePairProduction8setLimitEd3
_ZN7crpropa22EMDoublePairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZN7crpropa22EMDoublePairProduction16setHaveElectronsEb4
_ZN7crpropa22EMDoublePairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa22EMDoublePairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html new file mode 100644 index 000000000..4e691a3a6 --- /dev/null +++ b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMDoublePairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMDoublePairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:687294.4 %
Date:2024-04-08 14:58:22Functions:1010100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22EMDoublePairProduction11setThinningEd3
_ZN7crpropa22EMDoublePairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa22EMDoublePairProduction16setHaveElectronsEb4
_ZN7crpropa22EMDoublePairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22EMDoublePairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa22EMDoublePairProduction8setLimitEd3
_ZN7crpropa22EMDoublePairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZNK7crpropa22EMDoublePairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa22EMDoublePairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa22EMDoublePairProduction7processEPNS_9CandidateE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html new file mode 100644 index 000000000..5469562c6 --- /dev/null +++ b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html @@ -0,0 +1,209 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMDoublePairProduction.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMDoublePairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:687294.4 %
Date:2024-04-08 14:58:22Functions:1010100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/EMDoublePairProduction.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #include <fstream>
+       6             : #include <limits>
+       7             : #include <stdexcept>
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11           3 : EMDoublePairProduction::EMDoublePairProduction(ref_ptr<PhotonField> photonField, bool haveElectrons, double thinning, double limit) {
+      12           3 :         setPhotonField(photonField);
+      13           3 :         setHaveElectrons(haveElectrons);
+      14           3 :         setLimit(limit);
+      15           3 :         setThinning(thinning);
+      16           3 : }
+      17             : 
+      18          15 : void EMDoublePairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
+      19          15 :         this->photonField = photonField;
+      20          15 :         std::string fname = photonField->getFieldName();
+      21          15 :         setDescription("EMDoublePairProduction: " + fname);
+      22          45 :         initRate(getDataPath("EMDoublePairProduction/rate_" + fname + ".txt"));
+      23          15 : }
+      24             : 
+      25           4 : void EMDoublePairProduction::setHaveElectrons(bool haveElectrons) {
+      26           4 :         this->haveElectrons = haveElectrons;
+      27           4 : }
+      28             : 
+      29           3 : void EMDoublePairProduction::setLimit(double limit) {
+      30           3 :         this->limit = limit;
+      31           3 : }
+      32             : 
+      33           3 : void EMDoublePairProduction::setThinning(double thinning) {
+      34           3 :         this->thinning = thinning;
+      35           3 : }
+      36             : 
+      37          15 : void EMDoublePairProduction::initRate(std::string filename) {
+      38          15 :         std::ifstream infile(filename.c_str());
+      39             : 
+      40          15 :         if (!infile.good())
+      41           0 :                 throw std::runtime_error("EMDoublePairProduction: could not open file " + filename);
+      42             : 
+      43             :         // clear previously loaded interaction rates
+      44          15 :         tabEnergy.clear();
+      45          15 :         tabRate.clear();
+      46             : 
+      47        3306 :         while (infile.good()) {
+      48        3291 :                 if (infile.peek() != '#') {
+      49             :                         double a, b;
+      50             :                         infile >> a >> b;
+      51        3231 :                         if (infile) {
+      52        3216 :                                 tabEnergy.push_back(pow(10, a) * eV);
+      53        3216 :                                 tabRate.push_back(b / Mpc);
+      54             :                         }
+      55             :                 }
+      56        3291 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      57             :         }
+      58          15 :         infile.close();
+      59          15 : }
+      60             : 
+      61             : 
+      62           1 : void EMDoublePairProduction::performInteraction(Candidate *candidate) const {
+      63             :         // the photon is lost after the interaction
+      64           1 :         candidate->setActive(false);
+      65             : 
+      66           1 :         if (not haveElectrons)
+      67           0 :                 return;
+      68             : 
+      69             :         // Use assumption of Lee 96 arXiv:9604098
+      70             :         // Energy is equally shared between one e+e- pair, but take mass of second e+e- pair into account.
+      71             :         // This approximation has been shown to be valid within -1.5%.
+      72           1 :         double z = candidate->getRedshift();
+      73           1 :         double E = candidate->current.getEnergy() * (1 + z);
+      74           1 :         double Ee = (E - 2 * mass_electron * c_squared) / 2;
+      75             : 
+      76           1 :         Random &random = Random::instance();
+      77           1 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+      78             : 
+      79           1 :         double f = Ee / E;
+      80             : 
+      81           1 :         if (haveElectrons) {
+      82           1 :                 if (random.rand() < pow(1 - f, thinning)) {
+      83           1 :                         double w = 1. / pow(1 - f, thinning);
+      84           1 :                         candidate->addSecondary( 11, Ee / (1 + z), pos, w, interactionTag);
+      85             :                 } 
+      86           1 :                 if (random.rand() < pow(f, thinning)) {
+      87           1 :                         double w = 1. / pow(f, thinning);
+      88           1 :                         candidate->addSecondary(-11, Ee / (1 + z), pos, w, interactionTag);
+      89             :                 }
+      90             :         }
+      91             : }
+      92             : 
+      93           1 : void EMDoublePairProduction::process(Candidate *candidate) const {
+      94             :         // check if photon
+      95           1 :         if (candidate->current.getId() != 22)
+      96             :                 return;
+      97             : 
+      98             :         // scale the electron energy instead of background photons
+      99           1 :         double z = candidate->getRedshift();
+     100           1 :         double E = (1 + z) * candidate->current.getEnergy();
+     101             : 
+     102             :         // check if in tabulated energy range
+     103           1 :         if (E < tabEnergy.front() or (E > tabEnergy.back()))
+     104             :                 return;
+     105             : 
+     106             :         // interaction rate
+     107           1 :         double rate = interpolate(E, tabEnergy, tabRate);
+     108           1 :         rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
+     109             : 
+     110             :         // check for interaction
+     111           1 :         Random &random = Random::instance();
+     112           1 :         double randDistance = -log(random.rand()) / rate;
+     113           1 :         double step = candidate->getCurrentStep();
+     114           1 :         if (step < randDistance) {
+     115           1 :                 candidate->limitNextStep(limit / rate);
+     116           1 :                 return;
+     117             :         } else { // after performing interaction photon ceases to exist (hence return)
+     118           0 :                 performInteraction(candidate);
+     119           0 :                 return;
+     120             :         }
+     121             : 
+     122             : }
+     123             : 
+     124           1 : void EMDoublePairProduction::setInteractionTag(std::string tag) {
+     125           1 :         interactionTag = tag;
+     126           1 : }
+     127             : 
+     128           2 : std::string EMDoublePairProduction::getInteractionTag() const {
+     129           2 :         return interactionTag;
+     130             : }
+     131             : 
+     132             : 
+     133             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html new file mode 100644 index 000000000..8878c9d70 --- /dev/null +++ b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMInverseComptonScattering.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMInverseComptonScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12813396.2 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa26EMInverseComptonScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa32ICSSecondariesEnergyDistribution6sampleEdd1
_ZN7crpropa32ICSSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa26EMInverseComptonScattering18performInteractionEPNS_9CandidateE1
_ZNK7crpropa26EMInverseComptonScattering17getInteractionTagB5cxx11Ev2
_ZN7crpropa26EMInverseComptonScattering11setThinningEd5
_ZN7crpropa26EMInverseComptonScattering8setLimitEd5
_ZN7crpropa26EMInverseComptonScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd5
_ZN7crpropa26EMInverseComptonScattering14setHavePhotonsEb6
_ZN7crpropa26EMInverseComptonScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE17
_ZN7crpropa26EMInverseComptonScattering18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZN7crpropa26EMInverseComptonScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZNK7crpropa26EMInverseComptonScattering7processEPNS_9CandidateE15285
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html new file mode 100644 index 000000000..aa4472145 --- /dev/null +++ b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMInverseComptonScattering.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMInverseComptonScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12813396.2 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa26EMInverseComptonScattering11setThinningEd5
_ZN7crpropa26EMInverseComptonScattering14setHavePhotonsEb6
_ZN7crpropa26EMInverseComptonScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE17
_ZN7crpropa26EMInverseComptonScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa26EMInverseComptonScattering18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZN7crpropa26EMInverseComptonScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZN7crpropa26EMInverseComptonScattering8setLimitEd5
_ZN7crpropa26EMInverseComptonScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd5
_ZN7crpropa32ICSSecondariesEnergyDistribution6sampleEdd1
_ZN7crpropa32ICSSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa26EMInverseComptonScattering17getInteractionTagB5cxx11Ev2
_ZNK7crpropa26EMInverseComptonScattering18performInteractionEPNS_9CandidateE1
_ZNK7crpropa26EMInverseComptonScattering7processEPNS_9CandidateE15285
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html new file mode 100644 index 000000000..c5f4dfec4 --- /dev/null +++ b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html @@ -0,0 +1,325 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMInverseComptonScattering.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMInverseComptonScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12813396.2 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/EMInverseComptonScattering.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Random.h"
+       4             : #include "crpropa/Common.h"
+       5             : 
+       6             : #include <fstream>
+       7             : #include <limits>
+       8             : #include <stdexcept>
+       9             : 
+      10             : namespace crpropa {
+      11             : 
+      12             : static const double mec2 = mass_electron * c_squared;
+      13             : 
+      14           5 : EMInverseComptonScattering::EMInverseComptonScattering(ref_ptr<PhotonField> photonField, bool havePhotons, double thinning, double limit) {
+      15           5 :         setPhotonField(photonField);
+      16           5 :         setHavePhotons(havePhotons);
+      17           5 :         setLimit(limit);
+      18           5 :         setThinning(thinning);
+      19           5 : }
+      20             : 
+      21          17 : void EMInverseComptonScattering::setPhotonField(ref_ptr<PhotonField> photonField) {
+      22          17 :         this->photonField = photonField;
+      23          17 :         std::string fname = photonField->getFieldName();
+      24          17 :         setDescription("EMInverseComptonScattering: " + fname);
+      25          51 :         initRate(getDataPath("EMInverseComptonScattering/rate_" + fname + ".txt"));
+      26          51 :         initCumulativeRate(getDataPath("EMInverseComptonScattering/cdf_" + fname + ".txt"));
+      27          17 : }
+      28             : 
+      29           6 : void EMInverseComptonScattering::setHavePhotons(bool havePhotons) {
+      30           6 :         this->havePhotons = havePhotons;
+      31           6 : }
+      32             : 
+      33           5 : void EMInverseComptonScattering::setLimit(double limit) {
+      34           5 :         this->limit = limit;
+      35           5 : }
+      36             : 
+      37           5 : void EMInverseComptonScattering::setThinning(double thinning) {
+      38           5 :         this->thinning = thinning;
+      39           5 : }
+      40             : 
+      41          17 : void EMInverseComptonScattering::initRate(std::string filename) {
+      42          17 :         std::ifstream infile(filename.c_str());
+      43             : 
+      44          17 :         if (!infile.good())
+      45           0 :                 throw std::runtime_error("EMInverseComptonScattering: could not open file " + filename);
+      46             : 
+      47             :         // clear previously loaded tables
+      48          17 :         tabEnergy.clear();
+      49          17 :         tabRate.clear();
+      50             : 
+      51        4879 :         while (infile.good()) {
+      52        4862 :                 if (infile.peek() != '#') {
+      53             :                         double a, b;
+      54             :                         infile >> a >> b;
+      55        4794 :                         if (infile) {
+      56        4777 :                                 tabEnergy.push_back(pow(10, a) * eV);
+      57        4777 :                                 tabRate.push_back(b / Mpc);
+      58             :                         }
+      59             :                 }
+      60        4862 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      61             :         }
+      62          17 :         infile.close();
+      63          17 : }
+      64             : 
+      65          17 : void EMInverseComptonScattering::initCumulativeRate(std::string filename) {
+      66          17 :         std::ifstream infile(filename.c_str());
+      67             : 
+      68          17 :         if (!infile.good())
+      69           0 :                 throw std::runtime_error("EMInverseComptonScattering: could not open file " + filename);
+      70             : 
+      71             :         // clear previously loaded tables
+      72          17 :         tabE.clear();
+      73          17 :         tabs.clear();
+      74          17 :         tabCDF.clear();
+      75             :         
+      76             :         // skip header
+      77          85 :         while (infile.peek() == '#')
+      78          68 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      79             : 
+      80             :         // read s values in first line
+      81             :         double a;
+      82             :         infile >> a; // skip first value
+      83        3000 :         while (infile.good() and (infile.peek() != '\n')) {
+      84             :                 infile >> a;
+      85        2983 :                 tabs.push_back(pow(10, a) * eV * eV);
+      86             :         }
+      87             : 
+      88             :         // read all following lines: E, cdf values
+      89        4794 :         while (infile.good()) {
+      90             :                 infile >> a;
+      91        4794 :                 if (!infile)
+      92             :                         break;  // end of file
+      93        4777 :                 tabE.push_back(pow(10, a) * eV);
+      94             :                 std::vector<double> cdf;
+      95      843000 :                 for (int i = 0; i < tabs.size(); i++) {
+      96             :                         infile >> a;
+      97      838223 :                         cdf.push_back(a / Mpc);
+      98             :                 }
+      99        4777 :                 tabCDF.push_back(cdf);
+     100             :         }
+     101          17 :         infile.close();
+     102          17 : }
+     103             : 
+     104             : // Class to calculate the energy distribution of the ICS photon and to sample from it
+     105             : class ICSSecondariesEnergyDistribution {
+     106             :         private:
+     107             :                 std::vector< std::vector<double> > data;
+     108             :                 std::vector<double> s_values;
+     109             :                 size_t Ns;
+     110             :                 size_t Nrer;
+     111             :                 double s_min;
+     112             :                 double s_max;
+     113             :                 double dls;
+     114             : 
+     115             :         public:
+     116             :                 // differential cross-section, see Lee '96 (arXiv:9604098), eq. 23 for x = Ee'/Ee
+     117             :                 double dSigmadE(double x, double beta) {
+     118     1000000 :                         double q = ((1 - beta) / beta) * (1 - 1./x);
+     119     1000000 :                         return ((1 + beta) / beta) * (x + 1./x + 2 * q + q * q);
+     120             :                 }
+     121             : 
+     122             :                 // create the cumulative energy distribution of the up-scattered photon
+     123           1 :                 ICSSecondariesEnergyDistribution() {
+     124           1 :                         Ns = 1000;
+     125           1 :                         Nrer = 1000;
+     126           1 :                         s_min = mec2 * mec2;
+     127           1 :                         s_max = 2e23 * eV * eV;
+     128           1 :                         dls = (log(s_max) - log(s_min)) / Ns;
+     129           1 :                         data = std::vector< std::vector<double> >(1000, std::vector<double>(1000));
+     130           1 :                         std::vector<double> data_i(1000);
+     131             : 
+     132             :                         // tabulate s bin borders
+     133           1 :                         s_values = std::vector<double>(1001);
+     134        1002 :                         for (size_t i = 0; i < Ns + 1; ++i)
+     135        1001 :                                 s_values[i] = s_min * exp(i*dls);
+     136             : 
+     137             : 
+     138             :                         // for each s tabulate cumulative differential cross section
+     139        1001 :                         for (size_t i = 0; i < Ns; i++) {
+     140        1000 :                                 double s = s_min * exp((i+0.5) * dls);
+     141        1000 :                                 double beta = (s - s_min) / (s + s_min);
+     142        1000 :                                 double x0 = (1 - beta) / (1 + beta);
+     143        1000 :                                 double dlx = -log(x0) / Nrer;
+     144             : 
+     145             :                                 // cumulative midpoint integration
+     146        1000 :                                 data_i[0] = dSigmadE(x0, beta) * expm1(dlx);
+     147     1000000 :                                 for (size_t j = 1; j < Nrer; j++) {
+     148      999000 :                                         double x = x0 * exp((j+0.5) * dlx);
+     149      999000 :                                         double dx = exp((j+1) * dlx) - exp(j * dlx);
+     150      999000 :                                         data_i[j] = dSigmadE(x, beta) * dx;
+     151      999000 :                                         data_i[j] += data_i[j-1];
+     152             :                                 }
+     153        1000 :                                 data[i] = data_i;
+     154             :                         }
+     155           1 :                 }
+     156             : 
+     157             :                 // draw random energy for the up-scattered photon Ep(Ee, s)
+     158           1 :                 double sample(double Ee, double s) {
+     159           1 :                         size_t idx = std::lower_bound(s_values.begin(), s_values.end(), s) - s_values.begin();
+     160           1 :                         std::vector<double> s0 = data[idx];
+     161           1 :                         Random &random = Random::instance();
+     162           1 :                         size_t j = random.randBin(s0) + 1; // draw random bin (upper bin boundary returned)
+     163           1 :                         double beta = (s - s_min) / (s + s_min);
+     164           1 :                         double x0 = (1 - beta) / (1 + beta);
+     165           1 :                         double dlx = -log(x0) / Nrer;
+     166           1 :                         double binWidth = x0 * (exp(j * dlx) - exp((j-1) * dlx));
+     167           1 :                         double Ep = (x0 * exp((j-1) * dlx) + binWidth) * Ee;
+     168           2 :                         return std::min(Ee, Ep); // prevent Ep > Ee from numerical inaccuracies
+     169             :                 }
+     170             : };
+     171             : 
+     172           1 : void EMInverseComptonScattering::performInteraction(Candidate *candidate) const {
+     173             :         // scale the particle energy instead of background photons
+     174           1 :         double z = candidate->getRedshift();
+     175           1 :         double E = candidate->current.getEnergy() * (1 + z);
+     176             : 
+     177           1 :         if (E < tabE.front() or E > tabE.back())
+     178             :                 return;
+     179             : 
+     180             :         // sample the value of s
+     181           1 :         Random &random = Random::instance();
+     182           1 :         size_t i = closestIndex(E, tabE);
+     183           1 :         size_t j = random.randBin(tabCDF[i]);
+     184           1 :         double s_kin = pow(10, log10(tabs[j]) + (random.rand() - 0.5) * 0.1);
+     185           1 :         double s = s_kin + mec2 * mec2;
+     186             : 
+     187             :         // sample electron energy after scattering
+     188           1 :         static ICSSecondariesEnergyDistribution distribution;
+     189           1 :         double Enew = distribution.sample(E, s);
+     190             : 
+     191             :         // add up-scattered photon
+     192           1 :         double Esecondary = E - Enew;
+     193           1 :         double f = Enew / E;
+     194           1 :         if (havePhotons) {
+     195           1 :                 if (random.rand() < pow(1 - f, thinning)) {
+     196           1 :                         double w = 1. / pow(1 - f, thinning);
+     197           1 :                         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     198           1 :                         candidate->addSecondary(22, Esecondary / (1 + z), pos, w, interactionTag);
+     199             :                 }
+     200             :         }
+     201             : 
+     202             :         // update the primary particle energy; do this after adding the secondary to correctly set the secondary's parent
+     203           1 :         candidate->current.setEnergy(Enew / (1 + z));
+     204             : }
+     205             : 
+     206       15285 : void EMInverseComptonScattering::process(Candidate *candidate) const {
+     207             :         // check if electron / positron
+     208       15285 :         int id = candidate->current.getId();
+     209       15285 :         if (abs(id) != 11)
+     210             :                 return;
+     211             : 
+     212             :         // scale the particle energy instead of background photons
+     213           1 :         double z = candidate->getRedshift();
+     214           1 :         double E = candidate->current.getEnergy() * (1 + z);
+     215             : 
+     216           1 :         if (E < tabEnergy.front() or (E > tabEnergy.back()))
+     217             :                 return;
+     218             : 
+     219             :         // interaction rate
+     220           1 :         double rate = interpolate(E, tabEnergy, tabRate);
+     221           1 :         rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
+     222             : 
+     223             :         // run this loop at least once to limit the step size
+     224           1 :         double step = candidate->getCurrentStep();
+     225           1 :         Random &random = Random::instance();
+     226             :         do {
+     227           1 :                 double randDistance = -log(random.rand()) / rate;
+     228             : 
+     229             :                 // check for interaction; if it doesn't ocurr, limit next step
+     230           1 :                 if (step < randDistance) {
+     231           1 :                         candidate->limitNextStep(limit / rate);
+     232           1 :                         return;
+     233             :                 }
+     234           0 :                 performInteraction(candidate);
+     235             : 
+     236             :                 // repeat with remaining step
+     237           0 :                 step -= randDistance;
+     238           0 :         } while (step > 0);
+     239             : }
+     240             : 
+     241           1 : void EMInverseComptonScattering::setInteractionTag(std::string tag) {
+     242           1 :         interactionTag = tag;
+     243           1 : }
+     244             : 
+     245           2 : std::string EMInverseComptonScattering::getInteractionTag() const {
+     246           2 :         return interactionTag;
+     247             : }
+     248             : 
+     249             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html new file mode 100644 index 000000000..084270148 --- /dev/null +++ b/doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMPairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13413797.8 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16EMPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa31PPSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa16EMPairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa16EMPairProduction8setLimitEd9
_ZN7crpropa16EMPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd9
_ZN7crpropa16EMPairProduction11setThinningEd13
_ZN7crpropa16EMPairProduction16setHaveElectronsEb14
_ZN7crpropa16EMPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE33
_ZN7crpropa16EMPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa16EMPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa31PPSecondariesEnergyDistribution6sampleEdd563
_ZNK7crpropa16EMPairProduction18performInteractionEPNS_9CandidateE563
_ZNK7crpropa16EMPairProduction7processEPNS_9CandidateE16965
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMPairProduction.cpp.func.html b/doc/coverageReport/src/module/EMPairProduction.cpp.func.html new file mode 100644 index 000000000..082cd9399 --- /dev/null +++ b/doc/coverageReport/src/module/EMPairProduction.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMPairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13413797.8 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16EMPairProduction11setThinningEd13
_ZN7crpropa16EMPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE33
_ZN7crpropa16EMPairProduction16setHaveElectronsEb14
_ZN7crpropa16EMPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa16EMPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa16EMPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa16EMPairProduction8setLimitEd9
_ZN7crpropa16EMPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd9
_ZN7crpropa31PPSecondariesEnergyDistribution6sampleEdd563
_ZN7crpropa31PPSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa16EMPairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa16EMPairProduction18performInteractionEPNS_9CandidateE563
_ZNK7crpropa16EMPairProduction7processEPNS_9CandidateE16965
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html b/doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html new file mode 100644 index 000000000..b3986bf74 --- /dev/null +++ b/doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html @@ -0,0 +1,340 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMPairProduction.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13413797.8 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/EMPairProduction.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #include <fstream>
+       6             : #include <limits>
+       7             : #include <stdexcept>
+       8             : 
+       9             : 
+      10             : namespace crpropa {
+      11             : 
+      12             : static const double mec2 = mass_electron * c_squared;
+      13             : 
+      14           9 : EMPairProduction::EMPairProduction(ref_ptr<PhotonField> photonField, bool haveElectrons, double thinning, double limit) {
+      15           9 :         setPhotonField(photonField);
+      16           9 :         setThinning(thinning);
+      17           9 :         setLimit(limit);
+      18           9 :         setHaveElectrons(haveElectrons);
+      19           9 : }
+      20             : 
+      21          33 : void EMPairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
+      22          33 :         this->photonField = photonField;
+      23          33 :         std::string fname = photonField->getFieldName();
+      24          33 :         setDescription("EMPairProduction: " + fname);
+      25          99 :         initRate(getDataPath("EMPairProduction/rate_" + fname + ".txt"));
+      26          99 :         initCumulativeRate(getDataPath("EMPairProduction/cdf_" + fname + ".txt"));
+      27          33 : }
+      28             : 
+      29          14 : void EMPairProduction::setHaveElectrons(bool haveElectrons) {
+      30          14 :         this->haveElectrons = haveElectrons;
+      31          14 : }
+      32             : 
+      33           9 : void EMPairProduction::setLimit(double limit) {
+      34           9 :         this->limit = limit;
+      35           9 : }
+      36             : 
+      37          13 : void EMPairProduction::setThinning(double thinning) {
+      38          13 :         this->thinning = thinning;
+      39          13 : }
+      40             : 
+      41          33 : void EMPairProduction::initRate(std::string filename) {
+      42          33 :         std::ifstream infile(filename.c_str());
+      43             : 
+      44          33 :         if (!infile.good())
+      45           0 :                 throw std::runtime_error("EMPairProduction: could not open file " + filename);
+      46             : 
+      47             :         // clear previously loaded interaction rates
+      48          33 :         tabEnergy.clear();
+      49          33 :         tabRate.clear();
+      50             : 
+      51        7510 :         while (infile.good()) {
+      52        7477 :                 if (infile.peek() != '#') {
+      53             :                         double a, b;
+      54             :                         infile >> a >> b;
+      55        7345 :                         if (infile) {
+      56        7312 :                                 tabEnergy.push_back(pow(10, a) * eV);
+      57        7312 :                                 tabRate.push_back(b / Mpc);
+      58             :                         }
+      59             :                 }
+      60        7477 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      61             :         }
+      62          33 :         infile.close();
+      63          33 : }
+      64             : 
+      65          33 : void EMPairProduction::initCumulativeRate(std::string filename) {
+      66          33 :         std::ifstream infile(filename.c_str());
+      67             : 
+      68          33 :         if (!infile.good())
+      69           0 :                 throw std::runtime_error("EMPairProduction: could not open file " + filename);
+      70             : 
+      71             :         // clear previously loaded tables
+      72          33 :         tabE.clear();
+      73          33 :         tabs.clear();
+      74          33 :         tabCDF.clear();
+      75             :         
+      76             :         // skip header
+      77         165 :         while (infile.peek() == '#')
+      78         132 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      79             : 
+      80             :         // read s values in first line
+      81             :         double a;
+      82             :         infile >> a; // skip first value
+      83        3663 :         while (infile.good() and (infile.peek() != '\n')) {
+      84             :                 infile >> a;
+      85        3630 :                 tabs.push_back(pow(10, a) * eV * eV);
+      86             :         }
+      87             : 
+      88             :         // read all following lines: E, cdf values
+      89        7345 :         while (infile.good()) {
+      90             :                 infile >> a;
+      91        7345 :                 if (!infile)
+      92             :                         break;  // end of file
+      93        7312 :                 tabE.push_back(pow(10, a) * eV);
+      94             :                 std::vector<double> cdf;
+      95      811632 :                 for (int i = 0; i < tabs.size(); i++) {
+      96             :                         infile >> a;
+      97      804320 :                         cdf.push_back(a / Mpc);
+      98             :                 }
+      99        7312 :                 tabCDF.push_back(cdf);
+     100             :         }
+     101          33 :         infile.close();
+     102          33 : }
+     103             : 
+     104             : // Hold an data array to interpolate the energy distribution on
+     105             : class PPSecondariesEnergyDistribution {
+     106             :         private:
+     107             :                 std::vector<double> tab_s;
+     108             :                 std::vector< std::vector<double> > data;
+     109             :                 size_t N;
+     110             : 
+     111             :         public:
+     112             :                 // differential cross section for pair production for x = Epositron/Egamma, compare Lee 96 arXiv:9604098
+     113             :                 double dSigmadE_PPx(double x, double beta) {
+     114     1000000 :                         double A = (x / (1. - x) + (1. - x) / x );
+     115     1000000 :                         double B =  (1. / x + 1. / (1. - x) );
+     116        1000 :                         double y = (1 - beta * beta);
+     117     1000000 :                         return A + y * B - y * y / 4 * B * B;
+     118             :                 }
+     119             : 
+     120           1 :                 PPSecondariesEnergyDistribution() {
+     121           1 :                         N = 1000;
+     122             :                         size_t Ns = 1000;
+     123             :                         double s_min = 4 * mec2 * mec2;
+     124             :                         double s_max = 1e23 * eV * eV;
+     125             :                         double dls = log(s_max / s_min) / Ns;
+     126           1 :                         data = std::vector< std::vector<double> >(Ns, std::vector<double>(N));
+     127           1 :                         tab_s = std::vector<double>(Ns + 1);
+     128             : 
+     129        1002 :                         for (size_t i = 0; i < Ns + 1; ++i)
+     130        1001 :                                 tab_s[i] = s_min * exp(i*dls); // tabulate s bin borders
+     131             : 
+     132        1001 :                         for (size_t i = 0; i < Ns; i++) {
+     133        1000 :                                 double s = s_min * exp(i*dls + 0.5*dls);
+     134        1000 :                                 double beta = sqrt(1 - s_min/s);
+     135        1000 :                                 double x0 = (1 - beta) / 2;
+     136        1000 :                                 double dx = log((1 + beta) / (1 - beta)) / N;
+     137             : 
+     138             :                                 // cumulative midpoint integration
+     139        1000 :                                 std::vector<double> data_i(1000);
+     140        1000 :                                 data_i[0] = dSigmadE_PPx(x0, beta) * expm1(dx);
+     141     1000000 :                                 for (size_t j = 1; j < N; j++) {
+     142      999000 :                                         double x = x0 * exp(j*dx + 0.5*dx);
+     143      999000 :                                         double binWidth = exp((j+1)*dx)-exp(j*dx);
+     144      999000 :                                         data_i[j] = dSigmadE_PPx(x, beta) * binWidth + data_i[j-1];
+     145             :                                 }
+     146        1000 :                                 data[i] = data_i;
+     147             :                         }
+     148           1 :                 }
+     149             : 
+     150             :                 // sample positron energy from cdf(E, s_kin)
+     151         563 :                 double sample(double E0, double s) {
+     152             :                         // get distribution for given s
+     153         563 :                         size_t idx = std::lower_bound(tab_s.begin(), tab_s.end(), s) - tab_s.begin();
+     154         563 :                         if (idx > data.size())
+     155             :                                 return NAN;
+     156             :                                 
+     157         563 :                         std::vector<double> s0 = data[idx];
+     158             : 
+     159             :                         // draw random bin
+     160         563 :                         Random &random = Random::instance();
+     161         563 :                         size_t j = random.randBin(s0) + 1;
+     162             : 
+     163             :                         double s_min = 4. * mec2 * mec2;
+     164         563 :                         double beta = sqrtl(1. - s_min / s);
+     165         563 :                         double x0 = (1. - beta) / 2.;
+     166         563 :                         double dx = log((1 + beta) / (1 - beta)) / N;
+     167         563 :                         double binWidth = x0 * (exp(j*dx) - exp((j-1)*dx));
+     168         563 :                         if (random.rand() < 0.5)
+     169         290 :                                 return E0 * (x0 * exp((j-1) * dx) + binWidth);
+     170             :                         else
+     171         273 :                                 return E0 * (1 - (x0 * exp((j-1) * dx) + binWidth));
+     172             :                 }
+     173             : };
+     174             : 
+     175         563 : void EMPairProduction::performInteraction(Candidate *candidate) const {
+     176             :         // scale particle energy instead of background photon energy
+     177         563 :         double z = candidate->getRedshift();
+     178         563 :         double E = candidate->current.getEnergy() * (1 + z);
+     179             : 
+     180             :         // check if secondary electron pair needs to be produced
+     181         563 :         if (not haveElectrons)
+     182           0 :                 return;
+     183             : 
+     184             :         // check if in tabulated energy range
+     185         563 :         if (E < tabE.front() or (E > tabE.back()))
+     186             :                 return;
+     187             : 
+     188             :         // sample the value of s
+     189         563 :         Random &random = Random::instance();
+     190         563 :         size_t i = closestIndex(E, tabE);  // find closest tabulation point
+     191         563 :         size_t j = random.randBin(tabCDF[i]);
+     192        1092 :         double lo = std::max(4 * mec2 * mec2, tabs[j-1]);  // first s-tabulation point below min(s_kin) = (2 me c^2)^2; ensure physical value
+     193         563 :         double hi = tabs[j];
+     194         563 :         double s = lo + random.rand() * (hi - lo);
+     195             : 
+     196             :         // sample electron / positron energy
+     197         563 :         static PPSecondariesEnergyDistribution interpolation;
+     198         563 :         double Ee = interpolation.sample(E, s);
+     199         563 :         double Ep = E - Ee;
+     200         563 :         double f = Ep / E;
+     201             : 
+     202             :         // for some backgrounds Ee=nan due to precision limitations.
+     203         563 :         if (not std::isfinite(Ee) || not std::isfinite(Ep))
+     204             :                 return;
+     205             : 
+     206             :         // photon is lost after interacting
+     207         563 :         candidate->setActive(false);
+     208             : 
+     209             :         // sample random position along current step
+     210         563 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     211             :         // apply sampling
+     212         563 :         if (random.rand() < pow(f, thinning)) {
+     213         563 :                 double w = 1. / pow(f, thinning);
+     214         563 :                 candidate->addSecondary(11, Ep / (1 + z), pos, w, interactionTag);
+     215             :         }
+     216         563 :         if (random.rand() < pow(1 - f, thinning)){
+     217         563 :                 double w = 1. / pow(1 - f, thinning);
+     218         563 :                 candidate->addSecondary(-11, Ee / (1 + z), pos, w, interactionTag);  
+     219             :         }
+     220             : }
+     221             : 
+     222       16965 : void EMPairProduction::process(Candidate *candidate) const {
+     223             :         // check if photon
+     224       16965 :         if (candidate->current.getId() != 22)
+     225             :                 return;
+     226             : 
+     227             :         // scale particle energy instead of background photon energy
+     228         841 :         double z = candidate->getRedshift();
+     229         841 :         double E = candidate->current.getEnergy() * (1 + z);
+     230             : 
+     231             :         // check if in tabulated energy range
+     232         841 :         if ((E < tabEnergy.front()) or (E > tabEnergy.back()))
+     233             :                 return;
+     234             : 
+     235             :         // interaction rate
+     236         651 :         double rate = interpolate(E, tabEnergy, tabRate);
+     237         651 :         rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
+     238             : 
+     239             :         // run this loop at least once to limit the step size 
+     240         651 :         double step = candidate->getCurrentStep();
+     241         651 :         Random &random = Random::instance();
+     242             :         do {
+     243         651 :                 double randDistance = -log(random.rand()) / rate;
+     244             :                 // check for interaction; if it doesn't ocurr, limit next step
+     245         651 :                 if (step < randDistance) { 
+     246          89 :                         candidate->limitNextStep(limit / rate);
+     247             :                 } else {
+     248         562 :                         performInteraction(candidate);
+     249         562 :                         return;
+     250             :                 }
+     251          89 :                 step -= randDistance; 
+     252          89 :         } while (step > 0.);
+     253             : 
+     254             : }
+     255             : 
+     256           1 : void EMPairProduction::setInteractionTag(std::string tag) {
+     257           1 :         interactionTag = tag;
+     258           1 : }
+     259             : 
+     260           2 : std::string EMPairProduction::getInteractionTag() const {
+     261           2 :         return interactionTag;
+     262             : }
+     263             : 
+     264             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html new file mode 100644 index 000000000..bfb861b6b --- /dev/null +++ b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMTripletPairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMTripletPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9410094.0 %
Date:2024-04-08 14:58:22Functions:1111100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa23EMTripletPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa23EMTripletPairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa23EMTripletPairProduction7processEPNS_9CandidateE1
_ZNK7crpropa23EMTripletPairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa23EMTripletPairProduction11setThinningEd3
_ZN7crpropa23EMTripletPairProduction8setLimitEd3
_ZN7crpropa23EMTripletPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZN7crpropa23EMTripletPairProduction16setHaveElectronsEb4
_ZN7crpropa23EMTripletPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa23EMTripletPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa23EMTripletPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html new file mode 100644 index 000000000..bfa5c293f --- /dev/null +++ b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html @@ -0,0 +1,116 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMTripletPairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMTripletPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9410094.0 %
Date:2024-04-08 14:58:22Functions:1111100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa23EMTripletPairProduction11setThinningEd3
_ZN7crpropa23EMTripletPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa23EMTripletPairProduction16setHaveElectronsEb4
_ZN7crpropa23EMTripletPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa23EMTripletPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa23EMTripletPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa23EMTripletPairProduction8setLimitEd3
_ZN7crpropa23EMTripletPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZNK7crpropa23EMTripletPairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa23EMTripletPairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa23EMTripletPairProduction7processEPNS_9CandidateE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html new file mode 100644 index 000000000..a959e6b81 --- /dev/null +++ b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html @@ -0,0 +1,263 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/EMTripletPairProduction.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - EMTripletPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9410094.0 %
Date:2024-04-08 14:58:22Functions:1111100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/EMTripletPairProduction.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #include <fstream>
+       6             : #include <limits>
+       7             : #include <stdexcept>
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11             : static const double mec2 = mass_electron * c_squared;
+      12             : 
+      13           3 : EMTripletPairProduction::EMTripletPairProduction(ref_ptr<PhotonField> photonField, bool haveElectrons, double thinning, double limit) {
+      14           3 :         setPhotonField(photonField);
+      15           3 :         setHaveElectrons(haveElectrons);
+      16           3 :         setLimit(limit);
+      17           3 :         setThinning(thinning);
+      18           3 : }
+      19             : 
+      20          15 : void EMTripletPairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
+      21          15 :         this->photonField = photonField;
+      22          15 :         std::string fname = photonField->getFieldName();
+      23          15 :         setDescription("EMTripletPairProduction: " + fname);
+      24          45 :         initRate(getDataPath("EMTripletPairProduction/rate_" + fname + ".txt"));
+      25          45 :         initCumulativeRate(getDataPath("EMTripletPairProduction/cdf_" + fname + ".txt"));
+      26          15 : }
+      27             : 
+      28           4 : void EMTripletPairProduction::setHaveElectrons(bool haveElectrons) {
+      29           4 :         this->haveElectrons = haveElectrons;
+      30           4 : }
+      31             : 
+      32           3 : void EMTripletPairProduction::setLimit(double limit) {
+      33           3 :         this->limit = limit;
+      34           3 : }
+      35             : 
+      36           3 : void EMTripletPairProduction::setThinning(double thinning) {
+      37           3 :         this->thinning = thinning;
+      38           3 : }
+      39             : 
+      40          15 : void EMTripletPairProduction::initRate(std::string filename) {
+      41          15 :         std::ifstream infile(filename.c_str());
+      42             : 
+      43          15 :         if (!infile.good())
+      44           0 :                 throw std::runtime_error("EMTripletPairProduction: could not open file " + filename);
+      45             : 
+      46             :         // clear previously loaded interaction rates
+      47          15 :         tabEnergy.clear();
+      48          15 :         tabRate.clear();
+      49             : 
+      50        3340 :         while (infile.good()) {
+      51        3325 :                 if (infile.peek() != '#') {
+      52             :                         double a, b;
+      53             :                         infile >> a >> b;
+      54        3265 :                         if (infile) {
+      55        3250 :                                 tabEnergy.push_back(pow(10, a) * eV);
+      56        3250 :                                 tabRate.push_back(b / Mpc);
+      57             :                         }
+      58             :                 }
+      59        3325 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      60             :         }
+      61          15 :         infile.close();
+      62          15 : }
+      63             : 
+      64          15 : void EMTripletPairProduction::initCumulativeRate(std::string filename) {
+      65          15 :         std::ifstream infile(filename.c_str());
+      66             : 
+      67          15 :         if (!infile.good())
+      68           0 :                 throw std::runtime_error(
+      69           0 :                                 "EMTripletPairProduction: could not open file " + filename);
+      70             : 
+      71             :         // clear previously loaded tables
+      72          15 :         tabE.clear();
+      73          15 :         tabs.clear();
+      74          15 :         tabCDF.clear();
+      75             :         
+      76             :         // skip header
+      77          75 :         while (infile.peek() == '#')
+      78          60 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      79             : 
+      80             :         // read s values in first line
+      81             :         double a;
+      82             :         infile >> a; // skip first value
+      83        1590 :         while (infile.good() and (infile.peek() != '\n')) {
+      84             :                 infile >> a;
+      85        1575 :                 tabs.push_back(pow(10, a) * eV * eV);
+      86             :         }
+      87             : 
+      88             :         // read all following lines: E, cdf values
+      89        3265 :         while (infile.good()) {
+      90             :                 infile >> a;
+      91        3265 :                 if (!infile)
+      92             :                         break;  // end of file
+      93        3250 :                 tabE.push_back(pow(10, a) * eV);
+      94             :                 std::vector<double> cdf;
+      95      344500 :                 for (int i = 0; i < tabs.size(); i++) {
+      96             :                         infile >> a;
+      97      341250 :                         cdf.push_back(a / Mpc);
+      98             :                 }
+      99        3250 :                 tabCDF.push_back(cdf);
+     100             :         }
+     101          15 :         infile.close();
+     102          15 : }
+     103             : 
+     104           1 : void EMTripletPairProduction::performInteraction(Candidate *candidate) const {
+     105           1 :         int id = candidate->current.getId();
+     106           1 :         if  (abs(id) != 11)
+     107             :                 return;
+     108             : 
+     109             :         // scale the particle energy instead of background photons
+     110           1 :         double z = candidate->getRedshift();
+     111           1 :         double E = candidate->current.getEnergy() * (1 + z);
+     112             : 
+     113           1 :         if (E < tabE.front() or E > tabE.back())
+     114             :                 return;
+     115             : 
+     116             :         // sample the value of eps
+     117           1 :         Random &random = Random::instance();
+     118           1 :         size_t i = closestIndex(E, tabE);
+     119           1 :         size_t j = random.randBin(tabCDF[i]);
+     120           1 :         double s_kin = pow(10, log10(tabs[j]) + (random.rand() - 0.5) * 0.1);
+     121           1 :         double eps = s_kin / 4. / E; // random background photon energy
+     122             : 
+     123             :         // Use approximation from A. Mastichiadis et al., Astroph. Journ. 300:178-189 (1986), eq. 30.
+     124             :         // This approx is valid only for alpha >=100 where alpha = p0*eps*costheta - E0*eps
+     125             :         // For our purposes, me << E0 --> p0~E0 --> alpha = E0*eps*(costheta - 1) >= 100
+     126           1 :         double Epp = 5.7e-1 * pow(eps / mec2, -0.56) * pow(E / mec2, 0.44) * mec2;
+     127             : 
+     128           1 :         double f = Epp / E;
+     129             : 
+     130           1 :         if (haveElectrons) {
+     131           1 :                 Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     132           1 :                 if (random.rand() < pow(1 - f, thinning)) {
+     133           1 :                         double w = 1. / pow(1 - f, thinning);
+     134           1 :                         candidate->addSecondary(11, Epp / (1 + z), pos, w, interactionTag);
+     135             :                 }
+     136           1 :                 if (random.rand() < pow(f, thinning)) {
+     137           1 :                         double w = 1. / pow(f, thinning);
+     138           1 :                         candidate->addSecondary(-11, Epp / (1 + z), pos, w, interactionTag);
+     139             :                 }
+     140             :         }
+     141             :         // Update the primary particle energy.
+     142             :         // This is done after adding the secondaries to correctly set the secondaries parent
+     143           1 :         candidate->current.setEnergy((E - 2 * Epp) / (1. + z));
+     144             : }
+     145             : 
+     146           1 : void EMTripletPairProduction::process(Candidate *candidate) const {
+     147             :         // check if electron / positron
+     148           1 :         int id = candidate->current.getId();
+     149           1 :         if (abs(id) != 11)
+     150             :                 return;
+     151             : 
+     152             :         // scale the particle energy instead of background photons
+     153           1 :         double z = candidate->getRedshift();
+     154           1 :         double E = (1 + z) * candidate->current.getEnergy();
+     155             : 
+     156             :         // check if in tabulated energy range
+     157           1 :         if ((E < tabEnergy.front()) or (E > tabEnergy.back()))
+     158             :                 return;
+     159             : 
+     160             :         // cosmological scaling of interaction distance (comoving)
+     161           1 :         double scaling = pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
+     162           1 :         double rate = scaling * interpolate(E, tabEnergy, tabRate);
+     163             : 
+     164             :         // run this loop at least once to limit the step size
+     165           1 :         double step = candidate->getCurrentStep();
+     166           1 :         Random &random = Random::instance();
+     167             :         do {
+     168           1 :                 double randDistance = -log(random.rand()) / rate;
+     169             :                 // check for interaction; if it doesn't occur, limit next step
+     170           1 :                 if (step < randDistance) { 
+     171           1 :                         candidate->limitNextStep(limit / rate);
+     172           1 :                         return;
+     173             :                 }
+     174           0 :                 performInteraction(candidate);
+     175           0 :                 step -= randDistance; 
+     176           0 :         } while (step > 0.);
+     177             : }
+     178             : 
+     179           1 : void EMTripletPairProduction::setInteractionTag(std::string tag) {
+     180           1 :         interactionTag = tag;
+     181           1 : }
+     182             : 
+     183           2 : std::string EMTripletPairProduction::getInteractionTag() const {
+     184           2 :         return interactionTag;
+     185             : }
+     186             : 
+     187             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html b/doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html new file mode 100644 index 000000000..222b6680f --- /dev/null +++ b/doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ElasticScattering.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ElasticScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:637090.0 %
Date:2024-04-08 14:58:22Functions:5771.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ElasticScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa17ElasticScattering17getInteractionTagB5cxx11Ev0
_ZNK7crpropa17ElasticScattering7processEPNS_9CandidateE1
_ZN7crpropa17ElasticScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEE2
_ZN7crpropa17ElasticScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE4
_ZN7crpropa17ElasticScattering7initCDFENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
_ZN7crpropa17ElasticScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ElasticScattering.cpp.func.html b/doc/coverageReport/src/module/ElasticScattering.cpp.func.html new file mode 100644 index 000000000..8ecf24e21 --- /dev/null +++ b/doc/coverageReport/src/module/ElasticScattering.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ElasticScattering.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ElasticScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:637090.0 %
Date:2024-04-08 14:58:22Functions:5771.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ElasticScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE4
_ZN7crpropa17ElasticScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa17ElasticScattering7initCDFENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
_ZN7crpropa17ElasticScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
_ZN7crpropa17ElasticScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEE2
_ZNK7crpropa17ElasticScattering17getInteractionTagB5cxx11Ev0
_ZNK7crpropa17ElasticScattering7processEPNS_9CandidateE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html b/doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html new file mode 100644 index 000000000..f5b2d7a8c --- /dev/null +++ b/doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html @@ -0,0 +1,212 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ElasticScattering.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ElasticScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:637090.0 %
Date:2024-04-08 14:58:22Functions:5771.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/ElasticScattering.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/ParticleMass.h"
+       5             : #include "crpropa/Random.h"
+       6             : 
+       7             : #include <cmath>
+       8             : #include <limits>
+       9             : #include <sstream>
+      10             : #include <fstream>
+      11             : #include <stdexcept>
+      12             : 
+      13             : namespace crpropa {
+      14             : 
+      15             : const double ElasticScattering::lgmin = 6.;  // minimum log10(Lorentz-factor)
+      16             : const double ElasticScattering::lgmax = 14.; // maximum log10(Lorentz-factor)
+      17             : const size_t ElasticScattering::nlg = 201;   // number of Lorentz-factor steps
+      18             : const double ElasticScattering::epsmin = log10(2 * eV) + 3;    // log10 minimum photon background energy in nucleus rest frame for elastic scattering
+      19             : const double ElasticScattering::epsmax = log10(2 * eV) + 8.12; // log10 maximum photon background energy in nucleus rest frame for elastic scattering
+      20             : const size_t ElasticScattering::neps = 513; // number of photon background energies in nucleus rest frame
+      21             : 
+      22           2 : ElasticScattering::ElasticScattering(ref_ptr<PhotonField> f) {
+      23           2 :         setPhotonField(f);
+      24           2 : }
+      25             : 
+      26           4 : void ElasticScattering::setPhotonField(ref_ptr<PhotonField> photonField) {
+      27           4 :         this->photonField = photonField;
+      28           4 :         std::string fname = photonField->getFieldName();
+      29           4 :         setDescription("ElasticScattering: " + fname);
+      30          12 :         initRate(getDataPath("ElasticScattering/rate_" + fname.substr(0,3) + ".txt"));
+      31          12 :         initCDF(getDataPath("ElasticScattering/cdf_" + fname.substr(0,3) + ".txt"));
+      32           4 : }
+      33             : 
+      34           4 : void ElasticScattering::initRate(std::string filename) {
+      35           4 :         std::ifstream infile(filename.c_str());
+      36           4 :         if (not infile.good())
+      37           0 :                 throw std::runtime_error("ElasticScattering: could not open file " + filename);
+      38             : 
+      39           4 :         tabRate.clear();
+      40             : 
+      41         824 :         while (infile.good()) {
+      42         824 :                 if (infile.peek() == '#') {
+      43          16 :                         infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+      44          16 :                         continue;
+      45             :                 }
+      46             :                 double r;
+      47             :                 infile >> r;
+      48         808 :                 if (!infile)
+      49             :                         break;
+      50         804 :                 tabRate.push_back(r / Mpc);
+      51             :         }
+      52             : 
+      53           4 :         infile.close();
+      54           4 : }
+      55             : 
+      56           4 : void ElasticScattering::initCDF(std::string filename) {
+      57           4 :         std::ifstream infile(filename.c_str());
+      58           4 :         if (not infile.good())
+      59           0 :                 throw std::runtime_error("ElasticScattering: could not open file " + filename);
+      60             : 
+      61           4 :         tabCDF.clear();
+      62             :         std::string line;
+      63             :         double a;
+      64         820 :         while (std::getline(infile, line)) {
+      65         816 :                 if (line[0] == '#')
+      66          12 :                         continue;
+      67             : 
+      68         804 :                 std::stringstream lineStream(line);
+      69             :                 lineStream >> a;
+      70             : 
+      71         804 :                 std::vector<double> cdf(neps);
+      72      413256 :                 for (size_t i = 0; i < neps; i++) {
+      73             :                         lineStream >> a;
+      74      412452 :                         cdf[i] = a;
+      75             :                 }
+      76         804 :                 tabCDF.push_back(cdf);
+      77         804 :         }
+      78             : 
+      79           4 :         infile.close();
+      80           4 : }
+      81             : 
+      82           1 : void ElasticScattering::process(Candidate *candidate) const {
+      83           1 :         int id = candidate->current.getId();
+      84           1 :         double z = candidate->getRedshift();
+      85             : 
+      86           1 :         if (not isNucleus(id))
+      87             :                 return;
+      88             : 
+      89           1 :         double lg = log10(candidate->current.getLorentzFactor() * (1 + z));
+      90           1 :         if ((lg < lgmin) or (lg > lgmax))
+      91             :                 return;
+      92             : 
+      93           1 :         int A = massNumber(id);
+      94           1 :         int Z = chargeNumber(id);
+      95           1 :         int N = A - Z;
+      96             : 
+      97           1 :         double step = candidate->getCurrentStep();
+      98           8 :         while (step > 0) {
+      99             : 
+     100           8 :                 double rate = interpolateEquidistant(lg, lgmin, lgmax, tabRate);
+     101           8 :                 rate *= Z * N / double(A);  // TRK scaling
+     102           8 :                 rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);  // cosmological scaling
+     103             : 
+     104             :                 // check for interaction
+     105           8 :                 Random &random = Random::instance();
+     106           8 :                 double randDist = -log(random.rand()) / rate;
+     107           8 :                 if (step < randDist)
+     108           1 :                         return;
+     109             : 
+     110             :                 // draw random background photon energy from CDF
+     111           7 :                 size_t i = floor((lg - lgmin) / (lgmax - lgmin) * (nlg - 1)); // index of closest gamma tabulation point
+     112           7 :                 size_t j = random.randBin(tabCDF[i]) - 1; // index of next lower tabulated eps value
+     113             :                 double binWidth = (epsmax - epsmin) / (neps - 1); // logarithmic bin width
+     114           7 :                 double eps = pow(10, epsmin + (j + random.rand()) * binWidth);
+     115             : 
+     116             :                 // boost to lab frame
+     117           7 :                 double cosTheta = 2 * random.rand() - 1;
+     118           7 :                 double E = eps * candidate->current.getLorentzFactor() * (1. - cosTheta);
+     119             : 
+     120           7 :                 Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     121           7 :                 candidate->addSecondary(22, E, pos, 1., interactionTag);
+     122             : 
+     123             :                 // repeat with remaining step
+     124           7 :                 step -= randDist;
+     125             :         }
+     126             : }
+     127             : 
+     128           0 : void ElasticScattering::setInteractionTag(std::string tag) {
+     129           0 :         this -> interactionTag = tag;
+     130           0 : }
+     131             : 
+     132           0 : std::string ElasticScattering::getInteractionTag() const {
+     133           0 :         return interactionTag;
+     134             : }
+     135             : 
+     136             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html new file mode 100644 index 000000000..03ac203cf --- /dev/null +++ b/doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ElectronPairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ElectronPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859292.4 %
Date:2024-04-08 14:58:22Functions:91090.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ElectronPairProduction8setLimitEd0
_ZN7crpropa22ElectronPairProduction12initSpectrumENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22ElectronPairProduction16setHaveElectronsEb1
_ZN7crpropa22ElectronPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa22ElectronPairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa22ElectronPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbd10
_ZN7crpropa22ElectronPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE19
_ZN7crpropa22ElectronPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE19
_ZNK7crpropa22ElectronPairProduction10lossLengthEidd15446
_ZNK7crpropa22ElectronPairProduction7processEPNS_9CandidateE15447
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html b/doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html new file mode 100644 index 000000000..5da0c6c27 --- /dev/null +++ b/doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ElectronPairProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ElectronPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859292.4 %
Date:2024-04-08 14:58:22Functions:91090.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ElectronPairProduction12initSpectrumENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22ElectronPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE19
_ZN7crpropa22ElectronPairProduction16setHaveElectronsEb1
_ZN7crpropa22ElectronPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22ElectronPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE19
_ZN7crpropa22ElectronPairProduction8setLimitEd0
_ZN7crpropa22ElectronPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbd10
_ZNK7crpropa22ElectronPairProduction10lossLengthEidd15446
_ZNK7crpropa22ElectronPairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa22ElectronPairProduction7processEPNS_9CandidateE15447
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html b/doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html new file mode 100644 index 000000000..5204a21c0 --- /dev/null +++ b/doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html @@ -0,0 +1,233 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ElectronPairProduction.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ElectronPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859292.4 %
Date:2024-04-08 14:58:22Functions:91090.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/ElectronPairProduction.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/ParticleMass.h"
+       5             : #include "crpropa/Random.h"
+       6             : 
+       7             : #include <fstream>
+       8             : #include <limits>
+       9             : #include <stdexcept>
+      10             : 
+      11             : namespace crpropa {
+      12             : 
+      13          10 : ElectronPairProduction::ElectronPairProduction(ref_ptr<PhotonField> photonField,
+      14          10 :                 bool haveElectrons, double limit) {
+      15          10 :         this->haveElectrons = haveElectrons;
+      16          10 :         this->limit = limit;
+      17          10 :         setPhotonField(photonField);
+      18          10 : }
+      19             : 
+      20          19 : void ElectronPairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
+      21          19 :         this->photonField = photonField;
+      22          19 :         std::string fname = photonField->getFieldName();
+      23          19 :         setDescription("ElectronPairProduction: " + fname);
+      24          57 :         initRate(getDataPath("ElectronPairProduction/lossrate_" + fname + ".txt"));
+      25          19 :         if (haveElectrons) { // Load secondary spectra only if electrons should be produced
+      26           0 :                 initSpectrum(getDataPath("ElectronPairProduction/spectrum_" + fname.substr(0,3) + ".txt"));
+      27             :         }
+      28          19 : }
+      29             : 
+      30           1 : void ElectronPairProduction::setHaveElectrons(bool haveElectrons) {
+      31           1 :         this->haveElectrons = haveElectrons;
+      32           1 :         if (haveElectrons) { // Load secondary spectra in case haveElectrons was changed to true
+      33           1 :                 std::string fname = photonField->getFieldName();
+      34           3 :                 initSpectrum(getDataPath("ElectronPairProduction/spectrum_" + fname.substr(0,3) + ".txt"));
+      35             :         }
+      36           1 : }
+      37             : 
+      38           0 : void ElectronPairProduction::setLimit(double limit) {
+      39           0 :         this->limit = limit;
+      40           0 : }
+      41             : 
+      42          19 : void ElectronPairProduction::initRate(std::string filename) {
+      43          19 :         std::ifstream infile(filename.c_str());
+      44             : 
+      45          19 :         if (!infile.good())
+      46           0 :                 throw std::runtime_error("ElectronPairProduction: could not open file " + filename);
+      47             : 
+      48             :         // clear previously loaded interaction rates
+      49          19 :         tabLorentzFactor.clear();
+      50          19 :         tabLossRate.clear();
+      51             : 
+      52        2853 :         while (infile.good()) {
+      53        2834 :                 if (infile.peek() != '#') {
+      54             :                         double a, b;
+      55             :                         infile >> a >> b;
+      56        2777 :                         if (infile) {
+      57        2758 :                                 tabLorentzFactor.push_back(pow(10, a));
+      58        2758 :                                 tabLossRate.push_back(b / Mpc);
+      59             :                         }
+      60             :                 }
+      61        2834 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+      62             :         }
+      63          19 :         infile.close();
+      64          19 : }
+      65             : 
+      66           1 : void ElectronPairProduction::initSpectrum(std::string filename) {
+      67           1 :         std::ifstream infile(filename.c_str());
+      68           1 :         if (!infile.good())
+      69           0 :                 throw std::runtime_error("ElectronPairProduction: could not open file " + filename);
+      70             : 
+      71             :         double dNdE;
+      72           1 :         tabSpectrum.resize(70);
+      73          71 :         for (size_t i = 0; i < 70; i++) {
+      74          70 :                 tabSpectrum[i].resize(170);
+      75       11970 :                 for (size_t j = 0; j < 170; j++) {
+      76             :                         infile >> dNdE;
+      77       11900 :                         tabSpectrum[i][j] = dNdE * pow(10, (7 + 0.1 * j)); // read electron distribution pdf(Ee) ~ dN/dEe * Ee
+      78             :                 }
+      79       11900 :                 for (size_t j = 1; j < 170; j++) {
+      80       11830 :                         tabSpectrum[i][j] += tabSpectrum[i][j - 1]; // cdf(Ee), unnormalized
+      81             :                 }
+      82             :         }
+      83           1 :         infile.close();
+      84           1 : }
+      85             : 
+      86       15446 : double ElectronPairProduction::lossLength(int id, double lf, double z) const {
+      87       15446 :         double Z = chargeNumber(id);
+      88       15446 :         if (Z == 0)
+      89             :                 return std::numeric_limits<double>::max(); // no pair production on uncharged particles
+      90             : 
+      91       14944 :         lf *= (1 + z);
+      92       14944 :         if (lf < tabLorentzFactor.front())
+      93             :                 return std::numeric_limits<double>::max(); // below energy threshold
+      94             : 
+      95             :         double rate;
+      96       14921 :         if (lf < tabLorentzFactor.back())
+      97       14921 :                 rate = interpolate(lf, tabLorentzFactor, tabLossRate); // interpolation
+      98             :         else
+      99           0 :                 rate = tabLossRate.back() * pow(lf / tabLorentzFactor.back(), -0.6); // extrapolation
+     100             : 
+     101       14921 :         double A = nuclearMass(id) / mass_proton; // more accurate than massNumber(Id)
+     102       14921 :         rate *= Z * Z / A * pow_integer<3>(1 + z) * photonField->getRedshiftScaling(z);
+     103       14921 :         return 1. / rate;
+     104             : }
+     105             : 
+     106       15447 : void ElectronPairProduction::process(Candidate *c) const {
+     107       15447 :         int id = c->current.getId();
+     108       15447 :         if (not (isNucleus(id)))
+     109             :                 return; // only nuclei
+     110             : 
+     111       15446 :         double lf = c->current.getLorentzFactor();
+     112       15446 :         double z = c->getRedshift();
+     113       15446 :         double losslen = lossLength(id, lf, z);  // energy loss length
+     114       15446 :         if (losslen >= std::numeric_limits<double>::max())
+     115             :                 return;
+     116             : 
+     117       14921 :         double step = c->getCurrentStep() / (1 + z); // step size in local frame
+     118       14921 :         double loss = step / losslen;  // relative energy loss
+     119             : 
+     120       14921 :         if (haveElectrons) {
+     121           1 :                 double dE = c->current.getEnergy() * loss;  // energy loss
+     122           1 :                 int i = round((log10(lf) - 6.05) * 10);  // find closest cdf(Ee|log10(gamma))
+     123           1 :                 i = std::min(std::max(i, 0), 69);
+     124           1 :                 Random &random = Random::instance();
+     125             : 
+     126             :                 // draw pairs as long as their energy is smaller than the pair production energy loss
+     127        6534 :                 while (dE > 0) {
+     128        6534 :                         size_t j = random.randBin(tabSpectrum[i]);
+     129        6534 :                         double Ee = pow(10, 6.95 + (j + random.rand()) * 0.1) * eV;
+     130        6534 :                         double Epair = 2 * Ee; // NOTE: electron and positron in general don't have same lab frame energy, but averaged over many draws the result is consistent
+     131             :                         // if the remaining energy is not sufficient check for random accepting
+     132        6534 :                         if (Epair > dE)
+     133           1 :                                 if (random.rand() > (dE / Epair))
+     134             :                                         break; // not accepted
+     135             : 
+     136             :                         // create pair and repeat with remaining energy
+     137        6533 :                         dE -= Epair;
+     138        6533 :                         Vector3d pos = random.randomInterpolatedPosition(c->previous.getPosition(), c->current.getPosition());
+     139        6533 :                         c->addSecondary( 11, Ee, pos, 1., interactionTag);
+     140        6533 :                         c->addSecondary(-11, Ee, pos, 1., interactionTag);
+     141             :                 }
+     142             :         }
+     143             : 
+     144       14921 :         c->current.setLorentzFactor(lf * (1 - loss));
+     145       14921 :         c->limitNextStep(limit * losslen);
+     146             : }
+     147             : 
+     148           1 : void ElectronPairProduction::setInteractionTag(std::string tag) {
+     149           1 :         interactionTag = tag;
+     150           1 : }
+     151             : 
+     152           2 : std::string ElectronPairProduction::getInteractionTag() const {
+     153           2 :         return interactionTag;
+     154             : }
+     155             : 
+     156             : 
+     157             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html b/doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html new file mode 100644 index 000000000..7c1102518 --- /dev/null +++ b/doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/HDF5Output.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - HDF5Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:122415.0 %
Date:2024-04-08 14:58:22Functions:41428.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10HDF5Output13setFlushLimitEj0
_ZN7crpropa10HDF5Output21insertDoubleAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKd0
_ZN7crpropa10HDF5Output21insertStringAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES8_0
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE0
_ZN7crpropa10HDF5OutputD0Ev0
_ZN7crpropa23variantTypeToH5T_NATIVEENS_7Variant4TypeE0
_ZNK7crpropa10HDF5Output14getDescriptionB5cxx11Ev0
_ZNK7crpropa10HDF5Output5flushEv0
_ZNK7crpropa10HDF5Output7processEPNS_9CandidateE0
_ZN7crpropa10HDF5Output4openERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa10HDF5Output5closeEv1
_ZN7crpropa10HDF5OutputC2Ev1
_ZN7crpropa10HDF5OutputD2Ev1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/HDF5Output.cpp.func.html b/doc/coverageReport/src/module/HDF5Output.cpp.func.html new file mode 100644 index 000000000..23798cfed --- /dev/null +++ b/doc/coverageReport/src/module/HDF5Output.cpp.func.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/HDF5Output.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - HDF5Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:122415.0 %
Date:2024-04-08 14:58:22Functions:41428.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10HDF5Output13setFlushLimitEj0
_ZN7crpropa10HDF5Output21insertDoubleAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKd0
_ZN7crpropa10HDF5Output21insertStringAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES8_0
_ZN7crpropa10HDF5Output4openERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa10HDF5Output5closeEv1
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE0
_ZN7crpropa10HDF5OutputC2Ev1
_ZN7crpropa10HDF5OutputD0Ev0
_ZN7crpropa10HDF5OutputD2Ev1
_ZN7crpropa23variantTypeToH5T_NATIVEENS_7Variant4TypeE0
_ZNK7crpropa10HDF5Output14getDescriptionB5cxx11Ev0
_ZNK7crpropa10HDF5Output5flushEv0
_ZNK7crpropa10HDF5Output7processEPNS_9CandidateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/HDF5Output.cpp.gcov.html b/doc/coverageReport/src/module/HDF5Output.cpp.gcov.html new file mode 100644 index 000000000..653ba85ea --- /dev/null +++ b/doc/coverageReport/src/module/HDF5Output.cpp.gcov.html @@ -0,0 +1,468 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/HDF5Output.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - HDF5Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:122415.0 %
Date:2024-04-08 14:58:22Functions:41428.6 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #ifdef CRPROPA_HAVE_HDF5
+       2             : 
+       3             : #include "crpropa/module/HDF5Output.h"
+       4             : #include "crpropa/Version.h"
+       5             : #include "crpropa/Random.h"
+       6             : #include "kiss/logger.h"
+       7             : 
+       8             : #include <hdf5.h>
+       9             : #include <cstring>
+      10             : 
+      11             : const hsize_t RANK = 1;
+      12             : const hsize_t BUFFER_SIZE = 1024 * 16;
+      13             : 
+      14             : namespace crpropa {
+      15             : 
+      16             : // map variant types to H5T_NATIVE
+      17           0 : hid_t variantTypeToH5T_NATIVE(Variant::Type type) {
+      18             :         if (type == Variant::TYPE_INT64)
+      19           0 :                 return H5T_NATIVE_INT64;
+      20             :         else if(type == Variant::TYPE_BOOL)
+      21           0 :                 return H5T_NATIVE_HBOOL;
+      22             :         else if(type == Variant::TYPE_CHAR)
+      23           0 :                 return H5T_NATIVE_CHAR;
+      24             :         else if(type == Variant::TYPE_UCHAR)
+      25           0 :                 return H5T_NATIVE_UCHAR;
+      26             :         else if(type == Variant::TYPE_INT16)
+      27           0 :                 return H5T_NATIVE_INT16;
+      28             :         else if(type == Variant::TYPE_UINT16)
+      29           0 :                 return H5T_NATIVE_UINT16;
+      30             :         else if(type == Variant::TYPE_INT32)
+      31           0 :                 return H5T_NATIVE_INT32;
+      32             :         else if(type == Variant::TYPE_UINT32)
+      33           0 :                 return H5T_NATIVE_UINT32;
+      34             :         else if(type == Variant::TYPE_INT64)
+      35             :                 return H5T_NATIVE_INT64;
+      36             :         else if(type == Variant::TYPE_UINT64)
+      37           0 :                 return H5T_NATIVE_UINT64;
+      38             :         else if(type == Variant::TYPE_FLOAT)
+      39           0 :                 return H5T_NATIVE_FLOAT;
+      40             :         else if(type == Variant::TYPE_DOUBLE)
+      41           0 :                 return H5T_NATIVE_DOUBLE;
+      42             :         else if(type == Variant::TYPE_STRING)
+      43           0 :                 return H5T_C_S1;
+      44             :         else
+      45             :         {
+      46           0 :                 KISS_LOG_ERROR << "variantTypeToH5T_NATIVE:: Type: " << Variant::getTypeName(type) << " unknown.";
+      47           0 :                 throw std::runtime_error("No matching HDF type for Variant type");
+      48             :         }
+      49             : }
+      50             : 
+      51           1 : HDF5Output::HDF5Output() :  Output(), filename(), file(-1), sid(-1), dset(-1), dataspace(-1), candidatesSinceFlush(0), flushLimit(std::numeric_limits<unsigned int>::max()) {
+      52           1 : }
+      53             : 
+      54           0 : HDF5Output::HDF5Output(const std::string& filename) :  Output(), filename(filename), file(-1), sid(-1), dset(-1), dataspace(-1), candidatesSinceFlush(0), flushLimit(std::numeric_limits<unsigned int>::max()) {
+      55           0 : }
+      56             : 
+      57           0 : HDF5Output::HDF5Output(const std::string& filename, OutputType outputtype) :  Output(outputtype), filename(filename), file(-1), sid(-1), dset(-1), dataspace(-1), candidatesSinceFlush(0), flushLimit(std::numeric_limits<unsigned int>::max()) {
+      58             :         outputtype = outputtype;
+      59           0 : }
+      60             : 
+      61           1 : HDF5Output::~HDF5Output() {
+      62           1 :         close();
+      63           2 : }
+      64             : 
+      65           0 : herr_t HDF5Output::insertStringAttribute(const std::string &key, const std::string &value){
+      66             :         hid_t   strtype, attr_space, version_attr;
+      67           0 :         hsize_t dims = 0;
+      68             :         herr_t  status;
+      69             : 
+      70           0 :         strtype = H5Tcopy(H5T_C_S1);
+      71           0 :         status = H5Tset_size(strtype, value.size());
+      72             : 
+      73           0 :         attr_space = H5Screate_simple(0, &dims, NULL);
+      74           0 :         version_attr = H5Acreate2(dset, key.c_str(), strtype, attr_space, H5P_DEFAULT, H5P_DEFAULT);
+      75           0 :         status = H5Awrite(version_attr, strtype, value.c_str());
+      76           0 :         status = H5Aclose(version_attr);
+      77           0 :         status = H5Sclose(attr_space);
+      78             : 
+      79           0 :         return status;
+      80             : }
+      81             : 
+      82           0 : herr_t HDF5Output::insertDoubleAttribute(const std::string &key, const double &value){
+      83             :         hid_t   type, attr_space, version_attr;
+      84           0 :         hsize_t dims = 0;
+      85             :         herr_t  status;
+      86             : 
+      87           0 :         type = H5Tcopy(H5T_NATIVE_DOUBLE);
+      88             : 
+      89           0 :         attr_space = H5Screate_simple(0, &dims, NULL);
+      90           0 :         version_attr = H5Acreate2(dset, key.c_str(), type, attr_space, H5P_DEFAULT, H5P_DEFAULT);
+      91           0 :         status = H5Awrite(version_attr, type, &value);
+      92           0 :         status = H5Aclose(version_attr);
+      93           0 :         status = H5Sclose(attr_space);
+      94             : 
+      95           0 :         return status;
+      96             : }
+      97             : 
+      98             : 
+      99             : 
+     100           1 : void HDF5Output::open(const std::string& filename) {
+     101           1 :         file = H5Fcreate(filename.c_str(), H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT);
+     102           1 :         if (file < 0)
+     103           2 :                 throw std::runtime_error(std::string("Cannot create file: ") + filename);
+     104             : 
+     105             : 
+     106           0 :         sid = H5Tcreate(H5T_COMPOUND, sizeof(OutputRow));
+     107           0 :         if (fields.test(TrajectoryLengthColumn))
+     108           0 :                 H5Tinsert(sid, "D", HOFFSET(OutputRow, D), H5T_NATIVE_DOUBLE);
+     109           0 :         if (fields.test(RedshiftColumn))
+     110           0 :                 H5Tinsert(sid, "z", HOFFSET(OutputRow, z), H5T_NATIVE_DOUBLE);
+     111           0 :         if (fields.test(SerialNumberColumn))
+     112           0 :                 H5Tinsert(sid, "SN", HOFFSET(OutputRow, SN), H5T_NATIVE_UINT64);
+     113           0 :         if (fields.test(CurrentIdColumn))
+     114           0 :                 H5Tinsert(sid, "ID", HOFFSET(OutputRow, ID), H5T_NATIVE_INT32);
+     115           0 :         if (fields.test(CurrentEnergyColumn))
+     116           0 :                 H5Tinsert(sid, "E", HOFFSET(OutputRow, E), H5T_NATIVE_DOUBLE);
+     117           0 :         if (fields.test(CurrentPositionColumn) && oneDimensional)
+     118           0 :                 H5Tinsert(sid, "X", HOFFSET(OutputRow, X), H5T_NATIVE_DOUBLE);
+     119           0 :         if (fields.test(CurrentPositionColumn) && not oneDimensional) {
+     120           0 :                 H5Tinsert(sid, "X", HOFFSET(OutputRow, X), H5T_NATIVE_DOUBLE);
+     121           0 :                 H5Tinsert(sid, "Y", HOFFSET(OutputRow, Y), H5T_NATIVE_DOUBLE);
+     122           0 :                 H5Tinsert(sid, "Z", HOFFSET(OutputRow, Z), H5T_NATIVE_DOUBLE);
+     123             :         }
+     124           0 :         if (fields.test(CurrentDirectionColumn) && not oneDimensional) {
+     125           0 :                 H5Tinsert(sid, "Px", HOFFSET(OutputRow, Px), H5T_NATIVE_DOUBLE);
+     126           0 :                 H5Tinsert(sid, "Py", HOFFSET(OutputRow, Py), H5T_NATIVE_DOUBLE);
+     127           0 :                 H5Tinsert(sid, "Pz", HOFFSET(OutputRow, Pz), H5T_NATIVE_DOUBLE);
+     128             :         }
+     129           0 :         if (fields.test(SerialNumberColumn))
+     130           0 :                 H5Tinsert(sid, "SN0", HOFFSET(OutputRow, SN0), H5T_NATIVE_UINT64);
+     131           0 :         if (fields.test(SourceIdColumn))
+     132           0 :                 H5Tinsert(sid, "ID0", HOFFSET(OutputRow, ID0), H5T_NATIVE_INT32);
+     133           0 :         if (fields.test(SourceEnergyColumn))
+     134           0 :                 H5Tinsert(sid, "E0", HOFFSET(OutputRow, E0), H5T_NATIVE_DOUBLE);
+     135           0 :         if (fields.test(SourcePositionColumn) && oneDimensional)
+     136           0 :                 H5Tinsert(sid, "X0", HOFFSET(OutputRow, X0), H5T_NATIVE_DOUBLE);
+     137           0 :         if (fields.test(SourcePositionColumn) && not oneDimensional){
+     138           0 :                 H5Tinsert(sid, "X0", HOFFSET(OutputRow, X0), H5T_NATIVE_DOUBLE);
+     139           0 :                 H5Tinsert(sid, "Y0", HOFFSET(OutputRow, Y0), H5T_NATIVE_DOUBLE);
+     140           0 :                 H5Tinsert(sid, "Z0", HOFFSET(OutputRow, Z0), H5T_NATIVE_DOUBLE);
+     141             :         }
+     142           0 :         if (fields.test(SourceDirectionColumn) && not oneDimensional) {
+     143           0 :                 H5Tinsert(sid, "P0x", HOFFSET(OutputRow, P0x), H5T_NATIVE_DOUBLE);
+     144           0 :                 H5Tinsert(sid, "P0y", HOFFSET(OutputRow, P0y), H5T_NATIVE_DOUBLE);
+     145           0 :                 H5Tinsert(sid, "P0z", HOFFSET(OutputRow, P0z), H5T_NATIVE_DOUBLE);
+     146             :         }
+     147           0 :         if (fields.test(SerialNumberColumn))
+     148           0 :                 H5Tinsert(sid, "SN1", HOFFSET(OutputRow, SN1), H5T_NATIVE_UINT64);
+     149           0 :         if (fields.test(CreatedIdColumn))
+     150           0 :                 H5Tinsert(sid, "ID1", HOFFSET(OutputRow, ID1), H5T_NATIVE_INT32);
+     151           0 :         if (fields.test(CreatedEnergyColumn))
+     152           0 :                 H5Tinsert(sid, "E1", HOFFSET(OutputRow, E1), H5T_NATIVE_DOUBLE);
+     153           0 :         if (fields.test(CreatedPositionColumn) && oneDimensional)
+     154           0 :                 H5Tinsert(sid, "X1", HOFFSET(OutputRow, X1), H5T_NATIVE_DOUBLE);
+     155           0 :         if (fields.test(CreatedPositionColumn) && not oneDimensional) {
+     156           0 :                 H5Tinsert(sid, "X1", HOFFSET(OutputRow, X1), H5T_NATIVE_DOUBLE);
+     157           0 :                 H5Tinsert(sid, "Y1", HOFFSET(OutputRow, Y1), H5T_NATIVE_DOUBLE);
+     158           0 :                 H5Tinsert(sid, "Z1", HOFFSET(OutputRow, Z1), H5T_NATIVE_DOUBLE);
+     159             :         }
+     160           0 :         if (fields.test(CreatedDirectionColumn) && not oneDimensional) {
+     161           0 :                 H5Tinsert(sid, "P1x", HOFFSET(OutputRow, P1x), H5T_NATIVE_DOUBLE);
+     162           0 :                 H5Tinsert(sid, "P1y", HOFFSET(OutputRow, P1y), H5T_NATIVE_DOUBLE);
+     163           0 :                 H5Tinsert(sid, "P1z", HOFFSET(OutputRow, P1z), H5T_NATIVE_DOUBLE);
+     164             :         }
+     165           0 :         if (fields.test(WeightColumn))
+     166           0 :                 H5Tinsert(sid, "W", HOFFSET(OutputRow, weight), H5T_NATIVE_DOUBLE);
+     167             :         
+     168           0 :         if (fields.test(CandidateTagColumn)) 
+     169           0 :                 H5Tinsert(sid, "tag", HOFFSET(OutputRow, tag), H5T_C_S1);
+     170             : 
+     171           0 :         size_t pos = 0;
+     172           0 :         for(std::vector<Output::Property>::const_iterator iter = properties.begin();
+     173           0 :                         iter != properties.end(); ++iter)
+     174             :         {
+     175           0 :                         hid_t type = variantTypeToH5T_NATIVE((*iter).defaultValue.getType());
+     176           0 :                         if (type == H5T_C_S1)
+     177             :                         { // set size of string field to size of default value!
+     178           0 :                                 type = H5Tcopy(H5T_C_S1);
+     179           0 :                                 H5Tset_size(type, (*iter).defaultValue.toString().size());
+     180             :                         }
+     181             : 
+     182           0 :                         H5Tinsert(sid, (*iter).name.c_str(), HOFFSET(OutputRow, propertyBuffer) + pos, type);
+     183           0 :                   pos += (*iter).defaultValue.getSize();
+     184             :         }
+     185           0 :         if (pos >= propertyBufferSize)
+     186             :         {
+     187           0 :                 KISS_LOG_ERROR << "Using " << pos << " bytes for properties output. Maximum is " << propertyBufferSize << " bytes.";
+     188           0 :                 throw std::runtime_error("Size of property buffer exceeded");
+     189             :         }
+     190             : 
+     191             :         // chunked prop
+     192           0 :         hid_t plist = H5Pcreate(H5P_DATASET_CREATE);
+     193           0 :         H5Pset_layout(plist, H5D_CHUNKED);
+     194           0 :         hsize_t chunk_dims[RANK] = {BUFFER_SIZE};
+     195           0 :         H5Pset_chunk(plist, RANK, chunk_dims);
+     196           0 :         H5Pset_deflate(plist, 5);
+     197             : 
+     198           0 :         hsize_t dims[RANK] = {0};
+     199           0 :         hsize_t max_dims[RANK] = {H5S_UNLIMITED};
+     200           0 :         dataspace = H5Screate_simple(RANK, dims, max_dims);
+     201             : 
+     202           0 :         dset = H5Dcreate2(file, "CRPROPA3", sid, dataspace, H5P_DEFAULT, plist, H5P_DEFAULT);
+     203             : 
+     204           0 :         insertStringAttribute("OutputType", outputName);
+     205           0 :         insertStringAttribute("Version", g_GIT_DESC);
+     206           0 :         insertDoubleAttribute("LengthScale", this->lengthScale);
+     207           0 :         insertDoubleAttribute("EnergyScale", this->energyScale);
+     208             : 
+     209             :         // add ranom seeds
+     210           0 :         std::vector< std::vector<uint32_t> > seeds = Random::getSeedThreads();
+     211           0 :         for (size_t i = 0; i < seeds.size(); i++)
+     212             :         {
+     213             :                 hid_t   type, attr_space, version_attr;
+     214             :                 herr_t  status;
+     215           0 :                 hsize_t dims[] = {1, 0};
+     216           0 :                 dims[1] = seeds[i].size();
+     217             : 
+     218           0 :                 type = H5Tarray_create(H5T_NATIVE_ULONG, 2, dims);
+     219             : 
+     220           0 :                 attr_space = H5Screate_simple(0, dims, NULL);
+     221             :                 char nameBuffer[256];
+     222             :                 sprintf(nameBuffer, "SEED_%03lu", i);
+     223           0 :                 KISS_LOG_DEBUG << "Creating HDF5 attribute: " << nameBuffer << " with dimensions " << dims[0] << "x" << dims[1] ;
+     224             : 
+     225           0 :                 version_attr = H5Acreate2(dset, nameBuffer, type, attr_space, H5P_DEFAULT, H5P_DEFAULT);
+     226           0 :                 status = H5Awrite(version_attr, type, &seeds[i][0]);
+     227           0 :                 status = H5Aclose(version_attr);
+     228           0 :                 status = H5Sclose(attr_space);
+     229             : 
+     230             :         }
+     231             : 
+     232             : 
+     233           0 :         H5Pclose(plist);
+     234             : 
+     235           0 :         buffer.reserve(BUFFER_SIZE);
+     236           0 :         time(&lastFlush);
+     237           0 : }
+     238             : 
+     239           1 : void HDF5Output::close() {
+     240           1 :         if (file >= 0) {
+     241           0 :                 flush();
+     242           0 :                 H5Dclose(dset);
+     243           0 :                 H5Tclose(sid);
+     244           0 :                 H5Sclose(dataspace);
+     245           0 :                 H5Fclose(file);
+     246           0 :                 file = -1;
+     247             :         }
+     248           1 : }
+     249             : 
+     250           0 : void HDF5Output::process(Candidate* candidate) const {
+     251           0 :         #pragma omp critical
+     252             :         {
+     253           0 :         if (file == -1)
+     254             :                 // This is ugly, but necesary as otherwise the user has to manually open the
+     255             :                 // file before processing the first candidate
+     256           0 :                 const_cast<HDF5Output*>(this)->open(filename);
+     257             :         }
+     258             : 
+     259             :         OutputRow r;
+     260           0 :         r.D = candidate->getTrajectoryLength() / lengthScale;
+     261           0 :         r.z = candidate->getRedshift();
+     262             : 
+     263           0 :         r.SN = candidate->getSerialNumber();
+     264           0 :         r.ID = candidate->current.getId();
+     265           0 :         r.E = candidate->current.getEnergy() / energyScale;
+     266           0 :         Vector3d v = candidate->current.getPosition() / lengthScale;
+     267           0 :         r.X = v.x;
+     268           0 :         r.Y = v.y;
+     269           0 :         r.Z = v.z;
+     270           0 :         v = candidate->current.getDirection();
+     271           0 :         r.Px = v.x;
+     272           0 :         r.Py = v.y;
+     273           0 :         r.Pz = v.z;
+     274             : 
+     275           0 :         r.SN0 = candidate->getSourceSerialNumber();
+     276           0 :         r.ID0 = candidate->source.getId();
+     277           0 :         r.E0 = candidate->source.getEnergy() / energyScale;
+     278           0 :         v = candidate->source.getPosition() / lengthScale;
+     279           0 :         r.X0 = v.x;
+     280           0 :         r.Y0 = v.y;
+     281           0 :         r.Z0 = v.z;
+     282           0 :         v = candidate->source.getDirection();
+     283           0 :         r.P0x = v.x;
+     284           0 :         r.P0y = v.y;
+     285           0 :         r.P0z = v.z;
+     286             : 
+     287           0 :         r.SN1 = candidate->getCreatedSerialNumber();
+     288           0 :         r.ID1 = candidate->created.getId();
+     289           0 :         r.E1 = candidate->created.getEnergy() / energyScale;
+     290           0 :         v = candidate->created.getPosition() / lengthScale;
+     291           0 :         r.X1 = v.x;
+     292           0 :         r.Y1 = v.y;
+     293           0 :         r.Z1 = v.z;
+     294           0 :         v = candidate->created.getDirection();
+     295           0 :         r.P1x = v.x;
+     296           0 :         r.P1y = v.y;
+     297           0 :         r.P1z = v.z;
+     298             : 
+     299           0 :         r.weight= candidate->getWeight();
+     300             : 
+     301           0 :         r.tag = candidate->getTagOrigin();
+     302             : 
+     303             :         size_t pos = 0;
+     304           0 :         for(std::vector<Output::Property>::const_iterator iter = properties.begin();
+     305           0 :                         iter != properties.end(); ++iter)
+     306             :         {
+     307           0 :                   Variant v;
+     308           0 :                         if (candidate->hasProperty((*iter).name))
+     309             :                         {
+     310           0 :                                 v = candidate->getProperty((*iter).name);
+     311             :                         }
+     312             :                         else
+     313             :                         {
+     314           0 :                                 v = (*iter).defaultValue;
+     315             :                         }
+     316           0 :                         pos += v.copyToBuffer(&r.propertyBuffer[pos]);
+     317           0 :         }
+     318             : 
+     319           0 :         #pragma omp critical
+     320             :         {
+     321           0 :                 const_cast<HDF5Output*>(this)->candidatesSinceFlush++;
+     322           0 :                 Output::process(candidate);
+     323             : 
+     324           0 :                 buffer.push_back(r);
+     325             : 
+     326             : 
+     327           0 :                 if (buffer.size() >= buffer.capacity())
+     328             :                 {
+     329           0 :                         KISS_LOG_DEBUG << "HDF5Output: Flush due to buffer capacity exceeded";
+     330           0 :                         flush();
+     331             :                 }
+     332           0 :                 else if (candidatesSinceFlush >= flushLimit)
+     333             :                 {
+     334           0 :                         KISS_LOG_DEBUG << "HDF5Output: Flush due to number of candidates";
+     335           0 :                         flush();
+     336             :                 }
+     337           0 :                 else if (difftime(time(NULL), lastFlush) > 60*10)
+     338             :                 {
+     339           0 :                         KISS_LOG_DEBUG << "HDF5Output: Flush due to time exceeded";
+     340           0 :                         flush();
+     341             :                 }
+     342             :         }
+     343           0 : }
+     344             : 
+     345           0 : void HDF5Output::flush() const {
+     346           0 :         const_cast<HDF5Output*>(this)->lastFlush = time(NULL);
+     347           0 :         const_cast<HDF5Output*>(this)->candidatesSinceFlush = 0;
+     348             : 
+     349             :         hsize_t n = buffer.size();
+     350             : 
+     351           0 :         if (n == 0)
+     352           0 :                 return;
+     353             : 
+     354           0 :         hid_t file_space = H5Dget_space(dset);
+     355           0 :         hsize_t count = H5Sget_simple_extent_npoints(file_space);
+     356             : 
+     357             :         // resize dataset
+     358           0 :         hsize_t new_size[RANK] = {count + n};
+     359           0 :         H5Dset_extent(dset, new_size);
+     360             : 
+     361             :         // get updated filespace
+     362           0 :         H5Sclose(file_space);
+     363           0 :         file_space = H5Dget_space(dset);
+     364             : 
+     365           0 :         hsize_t offset[RANK] = {count};
+     366           0 :         hsize_t cnt[RANK] = {n};
+     367             : 
+     368           0 :         H5Sselect_hyperslab(file_space, H5S_SELECT_SET, offset, NULL, cnt, NULL);
+     369           0 :         hid_t mspace_id = H5Screate_simple(RANK, cnt, NULL);
+     370             : 
+     371           0 :         H5Dwrite(dset, sid, mspace_id, file_space, H5P_DEFAULT, buffer.data());
+     372             : 
+     373           0 :         H5Sclose(mspace_id);
+     374           0 :         H5Sclose(file_space);
+     375             : 
+     376           0 :         buffer.clear();
+     377             : 
+     378           0 :         H5Fflush(file, H5F_SCOPE_GLOBAL);
+     379             : }
+     380             : 
+     381           0 : std::string HDF5Output::getDescription() const  {
+     382           0 :         return "HDF5Output";
+     383             : }
+     384             : 
+     385           0 : void HDF5Output::setFlushLimit(unsigned int N)
+     386             : {
+     387           0 :         flushLimit = N;
+     388           0 : }
+     389             : 
+     390             : } // namespace crpropa
+     391             : 
+     392             : #endif // CRPROPA_HAVE_HDF5
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html b/doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html new file mode 100644 index 000000000..8f9c1026b --- /dev/null +++ b/doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/MomentumDiffusion.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - MomentumDiffusion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:114524.4 %
Date:2024-04-08 14:58:22Functions:31030.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa25ConstantMomentumDiffusionC2Edd0
_ZNK7crpropa25ConstantMomentumDiffusion14getDescriptionB5cxx11Ev0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateAScalarEd0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateBScalarEv0
_ZNK7crpropa25ConstantMomentumDiffusion6getDppEv0
_ZNK7crpropa25ConstantMomentumDiffusion7processEPNS_9CandidateE0
_ZNK7crpropa25ConstantMomentumDiffusion8getLimitEv0
_ZN7crpropa25ConstantMomentumDiffusion6setDppEd1
_ZN7crpropa25ConstantMomentumDiffusionC2Ed1
_ZN7crpropa25ConstantMomentumDiffusion8setLimitEd2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html b/doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html new file mode 100644 index 000000000..377203fb6 --- /dev/null +++ b/doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html @@ -0,0 +1,112 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/MomentumDiffusion.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - MomentumDiffusion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:114524.4 %
Date:2024-04-08 14:58:22Functions:31030.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa25ConstantMomentumDiffusion6setDppEd1
_ZN7crpropa25ConstantMomentumDiffusion8setLimitEd2
_ZN7crpropa25ConstantMomentumDiffusionC2Ed1
_ZN7crpropa25ConstantMomentumDiffusionC2Edd0
_ZNK7crpropa25ConstantMomentumDiffusion14getDescriptionB5cxx11Ev0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateAScalarEd0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateBScalarEv0
_ZNK7crpropa25ConstantMomentumDiffusion6getDppEv0
_ZNK7crpropa25ConstantMomentumDiffusion7processEPNS_9CandidateE0
_ZNK7crpropa25ConstantMomentumDiffusion8getLimitEv0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html b/doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html new file mode 100644 index 000000000..926f0af54 --- /dev/null +++ b/doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html @@ -0,0 +1,147 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/MomentumDiffusion.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - MomentumDiffusion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:114524.4 %
Date:2024-04-08 14:58:22Functions:31030.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/MomentumDiffusion.h"
+       2             : 
+       3             : using namespace crpropa;
+       4             : 
+       5           1 : ConstantMomentumDiffusion::ConstantMomentumDiffusion(double Dpp) {
+       6           1 :         setLimit(0.1);
+       7           1 :         setDpp(Dpp);
+       8           1 : }
+       9             : 
+      10           0 : ConstantMomentumDiffusion::ConstantMomentumDiffusion(double Dpp, double limit) {
+      11           0 :         setLimit(limit);
+      12           0 :         setDpp(Dpp);
+      13           0 : }
+      14             : 
+      15           0 : void ConstantMomentumDiffusion::process(Candidate *c) const {
+      16           0 :         double rig = c->current.getRigidity();
+      17           0 :         if (std::isinf(rig)) {
+      18             :                 return; // Only charged particles
+      19             :         }
+      20             :         
+      21           0 :         double p = c->current.getEnergy() / c_light; // Note we use E=p/c (relativistic limit)
+      22           0 :         double dt = c->getCurrentStep() / c_light;
+      23             :         
+      24           0 :         double eta =  Random::instance().randNorm();
+      25           0 :         double domega = eta * sqrt(dt);
+      26             :         
+      27           0 :         double AScal = calculateAScalar(p);
+      28           0 :         double BScal = calculateBScalar();
+      29             : 
+      30           0 :         double dp = AScal * dt + BScal * domega;
+      31           0 :         c->current.setEnergy((p + dp) * c_light);
+      32             :         
+      33           0 :         c->limitNextStep(limit * p / AScal * c_light);
+      34             : }
+      35             : 
+      36           0 : double ConstantMomentumDiffusion::calculateAScalar(double p) const {
+      37           0 :         double a = + 2. / p * Dpp;
+      38           0 :         return a; 
+      39             : }
+      40             : 
+      41           0 : double ConstantMomentumDiffusion::calculateBScalar() const {
+      42           0 :         double b = sqrt(2 * Dpp);
+      43           0 :         return b;
+      44             : }
+      45             : 
+      46           1 : void ConstantMomentumDiffusion::setDpp(double d) {
+      47           1 :         if (d < 0 )
+      48           0 :                 throw std::runtime_error(
+      49           0 :                                 "ConstantMomentumDiffusion: Dpp must be non-negative");
+      50           1 :         Dpp = d;
+      51           1 : }
+      52             : 
+      53           2 : void ConstantMomentumDiffusion::setLimit(double l) {
+      54           2 :         limit = l;
+      55           2 : }
+      56             : 
+      57           0 : double ConstantMomentumDiffusion::getDpp() const {
+      58           0 :         return Dpp;
+      59             : }
+      60             : 
+      61           0 : double ConstantMomentumDiffusion::getLimit() const {
+      62           0 :         return limit;
+      63             : }
+      64             : 
+      65           0 : std::string ConstantMomentumDiffusion::getDescription() const {
+      66           0 :         std::stringstream s;
+      67           0 :         s << "limit: " << limit << "\n";
+      68           0 :         s << "Dpp: " << Dpp / (meter * meter / second) << " m^2/s";
+      69             : 
+      70           0 :         return s.str();
+      71           0 : }
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html b/doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html new file mode 100644 index 000000000..dde7b40eb --- /dev/null +++ b/doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/NuclearDecay.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - NuclearDecay.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13716881.5 %
Date:2024-04-08 14:58:22Functions:111384.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12NuclearDecay12meanFreePathEid0
_ZN7crpropa12NuclearDecay8setLimitEd0
_ZN7crpropa12NuclearDecay14setHavePhotonsEb1
_ZN7crpropa12NuclearDecay16setHaveNeutrinosEb1
_ZN7crpropa12NuclearDecay17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa12NuclearDecay16setHaveElectronsEb2
_ZNK7crpropa12NuclearDecay17getInteractionTagB5cxx11Ev2
_ZN7crpropa12NuclearDecayC2Ebbbd9
_ZNK7crpropa12NuclearDecay13gammaEmissionEPNS_9CandidateEi11
_ZNK7crpropa12NuclearDecay9betaDecayEPNS_9CandidateEb499
_ZNK7crpropa12NuclearDecay15nucleonEmissionEPNS_9CandidateEii699
_ZNK7crpropa12NuclearDecay18performInteractionEPNS_9CandidateEi984
_ZNK7crpropa12NuclearDecay7processEPNS_9CandidateE7647
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/NuclearDecay.cpp.func.html b/doc/coverageReport/src/module/NuclearDecay.cpp.func.html new file mode 100644 index 000000000..2adf42079 --- /dev/null +++ b/doc/coverageReport/src/module/NuclearDecay.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/NuclearDecay.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - NuclearDecay.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13716881.5 %
Date:2024-04-08 14:58:22Functions:111384.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12NuclearDecay12meanFreePathEid0
_ZN7crpropa12NuclearDecay14setHavePhotonsEb1
_ZN7crpropa12NuclearDecay16setHaveElectronsEb2
_ZN7crpropa12NuclearDecay16setHaveNeutrinosEb1
_ZN7crpropa12NuclearDecay17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa12NuclearDecay8setLimitEd0
_ZN7crpropa12NuclearDecayC2Ebbbd9
_ZNK7crpropa12NuclearDecay13gammaEmissionEPNS_9CandidateEi11
_ZNK7crpropa12NuclearDecay15nucleonEmissionEPNS_9CandidateEii699
_ZNK7crpropa12NuclearDecay17getInteractionTagB5cxx11Ev2
_ZNK7crpropa12NuclearDecay18performInteractionEPNS_9CandidateEi984
_ZNK7crpropa12NuclearDecay7processEPNS_9CandidateE7647
_ZNK7crpropa12NuclearDecay9betaDecayEPNS_9CandidateEb499
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html b/doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html new file mode 100644 index 000000000..a9a87ffa4 --- /dev/null +++ b/doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html @@ -0,0 +1,395 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/NuclearDecay.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - NuclearDecay.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13716881.5 %
Date:2024-04-08 14:58:22Functions:111384.6 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/NuclearDecay.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/ParticleMass.h"
+       5             : #include "crpropa/Random.h"
+       6             : 
+       7             : #include <fstream>
+       8             : #include <limits>
+       9             : #include <cmath>
+      10             : #include <stdexcept>
+      11             : 
+      12             : #include "kiss/logger.h"
+      13             : 
+      14             : namespace crpropa {
+      15             : 
+      16           9 : NuclearDecay::NuclearDecay(bool electrons, bool photons, bool neutrinos, double l) {
+      17           9 :         haveElectrons = electrons;
+      18           9 :         havePhotons = photons;
+      19           9 :         haveNeutrinos = neutrinos;
+      20           9 :         limit = l;
+      21           9 :         setDescription("NuclearDecay");
+      22             : 
+      23             :         // load decay table
+      24          18 :         std::string filename = getDataPath("nuclear_decay.txt");
+      25           9 :         std::ifstream infile(filename.c_str());
+      26           9 :         if (!infile.good())
+      27           0 :                 throw std::runtime_error(
+      28           0 :                                 "crpropa::NuclearDecay: could not open file " + filename);
+      29             : 
+      30           9 :         decayTable.resize(27 * 31);
+      31             :         std::string line;
+      32        8550 :         while (std::getline(infile,line)) {
+      33        8541 :                 std::stringstream stream(line);
+      34        8541 :                 if (stream.peek() == '#')
+      35             :                         continue;
+      36             :                 DecayMode decay;
+      37             :                 int Z, N;
+      38             :                 double lifetime;
+      39        8523 :                 stream >> Z >> N >> decay.channel >> lifetime;
+      40        8523 :                 decay.rate = 1. / lifetime / c_light; // decay rate in [1/m]
+      41             :                 std::vector<double> gamma;
+      42             :                 double val;
+      43       34227 :                 while (stream >> val)
+      44       25704 :                         gamma.push_back(val);
+      45       21375 :                 for (int i = 0; i < gamma.size(); i += 2) {
+      46       12852 :                         decay.energy.push_back(gamma[i] * keV);
+      47       12852 :                         decay.intensity.push_back(gamma[i+1]);
+      48             :                 }
+      49        8523 :                 if (infile)
+      50        8523 :                         decayTable[Z * 31 + N].push_back(decay);
+      51        8541 :         }
+      52           9 :         infile.close();
+      53          18 : }
+      54             : 
+      55           2 : void NuclearDecay::setHaveElectrons(bool b) {
+      56           2 :         haveElectrons = b;
+      57           2 : }
+      58             : 
+      59           1 : void NuclearDecay::setHavePhotons(bool b) {
+      60           1 :         havePhotons = b;
+      61           1 : }
+      62             : 
+      63           1 : void NuclearDecay::setHaveNeutrinos(bool b) {
+      64           1 :         haveNeutrinos = b;
+      65           1 : }
+      66             : 
+      67           0 : void NuclearDecay::setLimit(double l) {
+      68           0 :         limit = l;
+      69           0 : }
+      70             : 
+      71        7647 : void NuclearDecay::process(Candidate *candidate) const {
+      72             :         // the loop should be processed at least once for limiting the next step
+      73        7647 :         double step = candidate->getCurrentStep();
+      74        7647 :         double z = candidate->getRedshift();
+      75             :         do {
+      76             :                 // check if nucleus
+      77        7672 :                 int id = candidate->current.getId();
+      78        7672 :                 if (not (isNucleus(id)))
+      79             :                         return;
+      80             : 
+      81        7671 :                 int A = massNumber(id);
+      82        7671 :                 int Z = chargeNumber(id);
+      83        7671 :                 int N = A - Z;
+      84             : 
+      85             :                 // check if particle can decay
+      86        7671 :                 const std::vector<DecayMode> &decays = decayTable[Z * 31 + N];
+      87        7671 :                 if (decays.size() == 0)
+      88             :                         return;
+      89             : 
+      90             :                 // find interaction mode with minimum random decay distance
+      91         328 :                 Random &random = Random::instance();
+      92             :                 double randDistance = std::numeric_limits<double>::max();
+      93             :                 int channel;
+      94             :                 double totalRate = 0;
+      95             : 
+      96         656 :                 for (size_t i = 0; i < decays.size(); i++) {
+      97         328 :                         double rate = decays[i].rate;
+      98         328 :                         rate /= candidate->current.getLorentzFactor();  // relativistic time dilation
+      99         328 :                         rate /= (1 + z);  // rate per light travel distance -> rate per comoving distance
+     100         328 :                         totalRate += rate;
+     101         328 :                         double d = -log(random.rand()) / rate;
+     102         328 :                         if (d > randDistance)
+     103           0 :                                 continue;
+     104             :                         randDistance = d;
+     105         328 :                         channel = decays[i].channel;
+     106             :                 }
+     107             : 
+     108             :                 // check if interaction doesn't happen
+     109         328 :                 if (step < randDistance) {
+     110             :                         // limit next step to a fraction of the mean free path
+     111         303 :                         candidate->limitNextStep(limit / totalRate);
+     112         303 :                         return;
+     113             :                 }
+     114             : 
+     115             :                 // interact and repeat with remaining step
+     116          25 :                 performInteraction(candidate, channel);
+     117          25 :                 step -= randDistance;
+     118          25 :         } while (step > 0);
+     119             : }
+     120             : 
+     121         984 : void NuclearDecay::performInteraction(Candidate *candidate, int channel) const {
+     122             :         // interpret decay channel
+     123             :         int nBetaMinus = digit(channel, 10000);
+     124             :         int nBetaPlus = digit(channel, 1000);
+     125             :         int nAlpha = digit(channel, 100);
+     126             :         int nProton = digit(channel, 10);
+     127             :         int nNeutron = digit(channel, 1);
+     128             : 
+     129             :         // perform decays
+     130         984 :         if (havePhotons)
+     131          11 :                 gammaEmission(candidate,channel);
+     132        1314 :         for (size_t i = 0; i < nBetaMinus; i++)
+     133         330 :                 betaDecay(candidate, false);
+     134        1153 :         for (size_t i = 0; i < nBetaPlus; i++)
+     135         169 :                 betaDecay(candidate, true);
+     136        1008 :         for (size_t i = 0; i < nAlpha; i++)
+     137          24 :                 nucleonEmission(candidate, 4, 2);
+     138        1319 :         for (size_t i = 0; i < nProton; i++)
+     139         335 :                 nucleonEmission(candidate, 1, 1);
+     140        1324 :         for (size_t i = 0; i < nNeutron; i++)
+     141         340 :                 nucleonEmission(candidate, 1, 0);
+     142         984 : }
+     143             : 
+     144          11 : void NuclearDecay::gammaEmission(Candidate *candidate, int channel) const {
+     145          11 :         int id = candidate->current.getId();
+     146          11 :         int Z = chargeNumber(id);
+     147          11 :         int N = massNumber(id) - Z;
+     148             : 
+     149             :         // get photon energies and emission probabilities for decay channel
+     150          11 :         const std::vector<DecayMode> &decays = decayTable[Z * 31 + N];
+     151             :         size_t idecay = decays.size();
+     152          21 :         while (idecay-- != 0) {
+     153          21 :                 if (decays[idecay].channel == channel)
+     154             :                         break;
+     155             :         }
+     156             : 
+     157             :         const std::vector<double> &energy = decays[idecay].energy;
+     158             :         const std::vector<double> &intensity = decays[idecay].intensity;
+     159             : 
+     160             :         // check if photon emission available
+     161          11 :         if (energy.size() == 0)
+     162           0 :                 return;
+     163             : 
+     164          11 :         Random &random = Random::instance();
+     165          11 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     166             : 
+     167          26 :         for (int i = 0; i < energy.size(); ++i) {
+     168             :                 // check if photon of specific energy is emitted
+     169          15 :                 if (random.rand() > intensity[i])
+     170           5 :                         continue;
+     171             :                 // create secondary photon; boost to lab frame
+     172          10 :                 double cosTheta = 2 * random.rand() - 1;
+     173          10 :                 double E = energy[i] * candidate->current.getLorentzFactor() * (1. - cosTheta);
+     174          10 :                 candidate->addSecondary(22, E, pos, 1., interactionTag);
+     175             :         }
+     176             : }
+     177             : 
+     178         499 : void NuclearDecay::betaDecay(Candidate *candidate, bool isBetaPlus) const {
+     179         499 :         double gamma = candidate->current.getLorentzFactor();
+     180         499 :         int id = candidate->current.getId();
+     181         499 :         int A = massNumber(id);
+     182         499 :         int Z = chargeNumber(id);
+     183             : 
+     184             :         // beta- decay
+     185             :         int electronId = 11; // electron
+     186             :         int neutrinoId = -12; // anti-electron neutrino
+     187             :         int dZ = 1;
+     188             :         // beta+ decay
+     189         499 :         if (isBetaPlus) {
+     190             :                 electronId = -11; // positron
+     191             :                 neutrinoId = 12; // electron neutrino
+     192             :                 dZ = -1;
+     193             :         }
+     194             : 
+     195             :         // update candidate, nuclear recoil negligible
+     196             :         try
+     197             :         {
+     198         499 :                 candidate->current.setId(nucleusId(A, Z + dZ));
+     199             :         }
+     200           0 :         catch (std::runtime_error &e)
+     201             :         {
+     202           0 :                 KISS_LOG_ERROR<< "Something went wrong in the NuclearDecay\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
+     203           0 :                 throw;
+     204           0 :         }
+     205             : 
+     206         499 :         candidate->current.setLorentzFactor(gamma);
+     207             : 
+     208         499 :         if (not (haveElectrons or haveNeutrinos))
+     209         487 :                 return;
+     210             : 
+     211             :         // Q-value of the decay, subtract total energy of emitted photons
+     212          12 :         double m1 = nuclearMass(A, Z);
+     213          12 :         double m2 = nuclearMass(A, Z+dZ);
+     214          12 :         double Q = (m1 - m2 - mass_electron) * c_squared;
+     215             : 
+     216             :         // generate cdf of electron energy, neglecting Coulomb correction
+     217             :         // see Basdevant, Fundamentals in Nuclear Physics, eq. (4.92)
+     218             :         // This leads to deviations from theoretical expectations at low 
+     219             :         // primary energies.
+     220             :         std::vector<double> energies;
+     221             :         std::vector<double> densities; // cdf(E), unnormalized
+     222             : 
+     223          12 :         energies.reserve(51);
+     224          12 :         densities.reserve(51);
+     225             : 
+     226             :         double me = mass_electron * c_squared;
+     227          12 :         double cdf = 0;
+     228         624 :         for (int i = 0; i <= 50; i++) {
+     229         612 :                 double E = me + i / 50. * Q;
+     230         612 :                 cdf += E * sqrt(E * E - me * me) * pow(Q + me - E, 2);
+     231         612 :                 energies.push_back(E);
+     232         612 :                 densities.push_back(cdf);
+     233             :         }
+     234             : 
+     235             :         // draw random electron energy and angle
+     236             :         // assumption of ultra-relativistic particles 
+     237             :         // leads to deviations from theoretical predictions
+     238             :         // is not problematic for usual CRPropa energies E>~TeV
+     239          12 :         Random &random = Random::instance();
+     240          12 :         double E = interpolate(random.rand() * cdf, densities, energies);
+     241          12 :         double p = sqrt(E * E - me * me);  // p*c
+     242          12 :         double cosTheta = 2 * random.rand() - 1;
+     243             : 
+     244             :         // boost to lab frame
+     245          12 :         double Ee = gamma * (E - p * cosTheta);
+     246          12 :         double Enu = gamma * (Q + me - E) * (1 + cosTheta);  // pnu*c ~ Enu
+     247             : 
+     248          12 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     249          12 :         if (haveElectrons)
+     250          12 :                 candidate->addSecondary(electronId, Ee, pos, 1., interactionTag);
+     251          12 :         if (haveNeutrinos)
+     252          10 :                 candidate->addSecondary(neutrinoId, Enu, pos, 1., interactionTag);
+     253             : }
+     254             : 
+     255         699 : void NuclearDecay::nucleonEmission(Candidate *candidate, int dA, int dZ) const {
+     256         699 :         Random &random = Random::instance();
+     257         699 :         int id = candidate->current.getId();
+     258         699 :         int A = massNumber(id);
+     259         699 :         int Z = chargeNumber(id);
+     260         699 :         double EpA = candidate->current.getEnergy() / double(A);
+     261             : 
+     262             :         try
+     263             :         {
+     264         699 :                 candidate->current.setId(nucleusId(A - dA, Z - dZ));
+     265             :         }
+     266           0 :         catch (std::runtime_error &e)
+     267             :         {
+     268           0 :                 KISS_LOG_ERROR<< "Something went wrong in the NuclearDecay\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
+     269           0 :                 throw;
+     270           0 :         }
+     271             : 
+     272         699 :         candidate->current.setEnergy(EpA * (A - dA));
+     273         699 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(),candidate->current.getPosition());
+     274             : 
+     275             :         try
+     276             :         {
+     277         699 :                 candidate->addSecondary(nucleusId(dA, dZ), EpA * dA, pos, 1., interactionTag);
+     278             :         }
+     279           0 :         catch (std::runtime_error &e)
+     280             :         {
+     281           0 :                 KISS_LOG_ERROR<< "Something went wrong in the NuclearDecay\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
+     282           0 :                 throw;
+     283           0 :         }
+     284             : 
+     285         699 : }
+     286             : 
+     287           0 : double NuclearDecay::meanFreePath(int id, double gamma) {
+     288           0 :         if (not (isNucleus(id)))
+     289             :                 return std::numeric_limits<double>::max();
+     290             : 
+     291           0 :         int A = massNumber(id);
+     292           0 :         int Z = chargeNumber(id);
+     293           0 :         int N = A - Z;
+     294             : 
+     295             :         // check if particle can decay
+     296           0 :         const std::vector<DecayMode> &decays = decayTable[Z * 31 + N];
+     297           0 :         if (decays.size() == 0)
+     298             :                 return std::numeric_limits<double>::max();
+     299             : 
+     300             :         double totalRate = 0;
+     301             : 
+     302           0 :         for (size_t i = 0; i < decays.size(); i++) {
+     303           0 :                 double rate = decays[i].rate;
+     304           0 :                 rate /= gamma;
+     305           0 :                 totalRate += rate;
+     306             :         }
+     307             : 
+     308           0 :         return 1. / totalRate;
+     309             : }
+     310             : 
+     311           1 : void NuclearDecay::setInteractionTag(std::string tag) {
+     312           1 :         interactionTag = tag;
+     313           1 : }
+     314             : 
+     315           2 : std::string NuclearDecay::getInteractionTag() const {
+     316           2 :         return interactionTag;
+     317             : }
+     318             : 
+     319             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Observer.cpp.func-sort-c.html b/doc/coverageReport/src/module/Observer.cpp.func-sort-c.html new file mode 100644 index 000000000..7bf409276 --- /dev/null +++ b/doc/coverageReport/src/module/Observer.cpp.func-sort-c.html @@ -0,0 +1,248 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Observer.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Observer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8018044.4 %
Date:2024-04-08 14:58:22Functions:164436.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16ObserverTrackingC2ENS_7Vector3IdEEdd0
_ZN7crpropa21ObserverTimeEvolutionC2Ev0
_ZN7crpropa22ObserverParticleIdVetoC2Ei0
_ZN7crpropa22ObserverRedshiftWindowC2Edd0
_ZNK7crpropa10Observer1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverFeature14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa15ObserverFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverSurface14getDescriptionB5cxx11Ev0
_ZNK7crpropa16ObserverTracking14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa16ObserverTracking14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ObserverDetectAll14getDescriptionB5cxx11Ev0
_ZNK7crpropa18ObserverPhotonVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa18ObserverPhotonVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ObserverNucleusVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa19ObserverNucleusVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverElectronVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverElectronVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverInactiveVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverInactiveVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverNeutrinoVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverNeutrinoVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution8getTimesEv0
_ZNK7crpropa22ObserverParticleIdVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverParticleIdVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa22ObserverRedshiftWindow14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverRedshiftWindow14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Observer14getDescriptionB5cxx11Ev0
_ZN7crpropa21ObserverTimeEvolutionC2Eddd1
_ZN7crpropa21ObserverTimeEvolutionC2Edddb1
_ZN7crpropa15ObserverSurfaceC2EPNS_7SurfaceE2
_ZN7crpropa21ObserverTimeEvolution12addTimeRangeEdddb2
_ZN7crpropa8Observer11onDetectionEPNS_6ModuleEb2
_ZN7crpropa8Observer24setDeactivateOnDetectionEb2
_ZN7crpropa8Observer7setFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_2
_ZNK7crpropa17ObserverDetectAll14checkDetectionEPNS_9CandidateE2
_ZN7crpropa21ObserverTimeEvolution7addTimeERKd4
_ZNK7crpropa15ObserverSurface14checkDetectionEPNS_9CandidateE4
_ZNK7crpropa21ObserverTimeEvolution14checkDetectionEPNS_9CandidateE6
_ZN7crpropa8Observer3addEPNS_15ObserverFeatureE10
_ZN7crpropa8ObserverC2Ev10
_ZNK7crpropa15ObserverFeature11onDetectionEPNS_9CandidateE52
_ZNK7crpropa10Observer1D14checkDetectionEPNS_9CandidateE7664
_ZNK7crpropa8Observer7processEPNS_9CandidateE7681
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Observer.cpp.func.html b/doc/coverageReport/src/module/Observer.cpp.func.html new file mode 100644 index 000000000..d3bea8de7 --- /dev/null +++ b/doc/coverageReport/src/module/Observer.cpp.func.html @@ -0,0 +1,248 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Observer.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Observer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8018044.4 %
Date:2024-04-08 14:58:22Functions:164436.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15ObserverSurfaceC2EPNS_7SurfaceE2
_ZN7crpropa16ObserverTrackingC2ENS_7Vector3IdEEdd0
_ZN7crpropa21ObserverTimeEvolution12addTimeRangeEdddb2
_ZN7crpropa21ObserverTimeEvolution7addTimeERKd4
_ZN7crpropa21ObserverTimeEvolutionC2Eddd1
_ZN7crpropa21ObserverTimeEvolutionC2Edddb1
_ZN7crpropa21ObserverTimeEvolutionC2Ev0
_ZN7crpropa22ObserverParticleIdVetoC2Ei0
_ZN7crpropa22ObserverRedshiftWindowC2Edd0
_ZN7crpropa8Observer11onDetectionEPNS_6ModuleEb2
_ZN7crpropa8Observer24setDeactivateOnDetectionEb2
_ZN7crpropa8Observer3addEPNS_15ObserverFeatureE10
_ZN7crpropa8Observer7setFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_2
_ZN7crpropa8ObserverC2Ev10
_ZNK7crpropa10Observer1D14checkDetectionEPNS_9CandidateE7664
_ZNK7crpropa10Observer1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverFeature11onDetectionEPNS_9CandidateE52
_ZNK7crpropa15ObserverFeature14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa15ObserverFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverSurface14checkDetectionEPNS_9CandidateE4
_ZNK7crpropa15ObserverSurface14getDescriptionB5cxx11Ev0
_ZNK7crpropa16ObserverTracking14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa16ObserverTracking14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ObserverDetectAll14checkDetectionEPNS_9CandidateE2
_ZNK7crpropa17ObserverDetectAll14getDescriptionB5cxx11Ev0
_ZNK7crpropa18ObserverPhotonVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa18ObserverPhotonVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ObserverNucleusVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa19ObserverNucleusVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverElectronVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverElectronVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverInactiveVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverInactiveVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverNeutrinoVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverNeutrinoVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution14checkDetectionEPNS_9CandidateE6
_ZNK7crpropa21ObserverTimeEvolution14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution8getTimesEv0
_ZNK7crpropa22ObserverParticleIdVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverParticleIdVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa22ObserverRedshiftWindow14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverRedshiftWindow14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Observer14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Observer7processEPNS_9CandidateE7681
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Observer.cpp.gcov.html b/doc/coverageReport/src/module/Observer.cpp.gcov.html new file mode 100644 index 000000000..e54a180c9 --- /dev/null +++ b/doc/coverageReport/src/module/Observer.cpp.gcov.html @@ -0,0 +1,427 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Observer.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Observer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8018044.4 %
Date:2024-04-08 14:58:22Functions:164436.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/Observer.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/Cosmology.h"
+       5             : 
+       6             : #include "kiss/logger.h"
+       7             : 
+       8             : #include <iostream>
+       9             : #include <cmath>
+      10             : 
+      11             : namespace crpropa {
+      12             : 
+      13             : // Observer -------------------------------------------------------------------
+      14          10 : Observer::Observer() :
+      15          10 :                 makeInactive(true), clone(false) {
+      16          10 : }
+      17             : 
+      18          10 : void Observer::add(ObserverFeature *feature) {
+      19          10 :         features.push_back(feature);
+      20          10 : }
+      21             : 
+      22           2 : void Observer::onDetection(Module *action, bool clone_) {
+      23           2 :         detectionAction = action;
+      24           2 :         clone = clone_;
+      25           2 : }
+      26             : 
+      27        7681 : void Observer::process(Candidate *candidate) const {
+      28             :         // loop over all features and have them check the particle
+      29             :         DetectionState state = NOTHING;
+      30       15362 :         for (int i = 0; i < features.size(); i++) {
+      31        7681 :                 DetectionState s = features[i]->checkDetection(candidate);
+      32        7681 :                 if (s == VETO)
+      33             :                         state = VETO;
+      34        7681 :                 else if ((s == DETECTED) && (state != VETO))
+      35             :                         state = DETECTED;
+      36             :         }
+      37             : 
+      38        7681 :         if (state == DETECTED) {
+      39         104 :                 for (int i = 0; i < features.size(); i++) {
+      40          52 :                         features[i]->onDetection(candidate);
+      41             :                 }
+      42             : 
+      43          52 :                 if (detectionAction.valid()) {
+      44          38 :                         if (clone)
+      45           0 :                                 detectionAction->process(candidate->clone(false));
+      46             :                         else
+      47          38 :                                 detectionAction->process(candidate);
+      48             :                 }
+      49             : 
+      50          52 :                 if (!flagKey.empty())
+      51           4 :                         candidate->setProperty(flagKey, flagValue);
+      52             : 
+      53          52 :                 if (makeInactive)
+      54          48 :                         candidate->setActive(false);
+      55             :         }
+      56        7681 : }
+      57             : 
+      58           2 : void Observer::setFlag(std::string key, std::string value) {
+      59           2 :         flagKey = key;
+      60           2 :         flagValue = value;
+      61           2 : }
+      62             : 
+      63           0 : std::string Observer::getDescription() const {
+      64           0 :         std::stringstream ss;
+      65           0 :         ss << "Observer";
+      66           0 :         for (int i = 0; i < features.size(); i++)
+      67           0 :                 ss << "\n    " << features[i]->getDescription() << "\n";
+      68           0 :         ss << "    Flag: '" << flagKey << "' -> '" << flagValue << "'\n";
+      69           0 :         ss << "    MakeInactive: " << (makeInactive ? "yes\n" : "no\n");
+      70           0 :         if (detectionAction.valid())
+      71           0 :                 ss << "    Action: " << detectionAction->getDescription() << ", clone: " << (clone ? "yes" : "no");
+      72             : 
+      73           0 :         return ss.str();
+      74           0 : }
+      75             : 
+      76           2 : void Observer::setDeactivateOnDetection(bool deactivate) {
+      77           2 :         makeInactive = deactivate;
+      78           2 : }
+      79             : 
+      80             : // ObserverFeature ------------------------------------------------------------
+      81           0 : DetectionState ObserverFeature::checkDetection(Candidate *candidate) const {
+      82           0 :         return NOTHING;
+      83             : }
+      84             : 
+      85          52 : void ObserverFeature::onDetection(Candidate *candidate) const {
+      86          52 : }
+      87             : 
+      88           0 : std::string ObserverFeature::getDescription() const {
+      89           0 :         return description;
+      90             : }
+      91             : 
+      92             : // ObserverDetectAll ----------------------------------------------------------
+      93           2 : DetectionState ObserverDetectAll::checkDetection(Candidate *candidate) const {
+      94           2 :         return DETECTED;
+      95             : }
+      96             : 
+      97           0 : std::string ObserverDetectAll::getDescription() const {
+      98           0 :         return description;
+      99             : }
+     100             : 
+     101             : // ObserverTracking --------------------------------------------------------
+     102           0 : ObserverTracking::ObserverTracking(Vector3d center, double radius, double stepSize) :
+     103           0 :                 center(center), radius(radius), stepSize(stepSize) {
+     104             :         if (stepSize == 0) {
+     105             :                 stepSize = radius / 10.;
+     106             :         }
+     107           0 : }
+     108             : 
+     109           0 : DetectionState ObserverTracking::checkDetection(Candidate *candidate) const {
+     110             :         // current distance to observer sphere center
+     111           0 :         double d = (candidate->current.getPosition() - center).getR();
+     112             : 
+     113             :         // no detection if outside of observer sphere
+     114           0 :         if (d > radius) {
+     115             :                 // conservatively limit next step to prevent overshooting
+     116           0 :                 candidate->limitNextStep(fabs(d - radius));
+     117             : 
+     118           0 :                 return NOTHING;
+     119             :         } else {
+     120             :                 // limit next step
+     121           0 :                 candidate->limitNextStep(stepSize);
+     122             : 
+     123           0 :                 return DETECTED;
+     124             :         }
+     125             : }
+     126             : 
+     127           0 : std::string ObserverTracking::getDescription() const {
+     128           0 :         std::stringstream ss;
+     129           0 :         ss << "ObserverTracking: ";
+     130           0 :         ss << "center = " << center / Mpc << " Mpc, ";
+     131           0 :         ss << "radius = " << radius / Mpc << " Mpc";
+     132           0 :         ss << "stepSize = " << stepSize / Mpc << " Mpc";
+     133           0 :         return ss.str();
+     134           0 : }
+     135             : 
+     136             : // Observer1D --------------------------------------------------------------
+     137        7664 : DetectionState Observer1D::checkDetection(Candidate *candidate) const {
+     138        7664 :         double x = candidate->current.getPosition().x;
+     139        7664 :         if (x > 0) {
+     140             :                 // Limits the next step size to prevent candidates from overshooting in case of non-detection
+     141        7625 :                 candidate->limitNextStep(x);
+     142        7625 :                 return NOTHING;
+     143             :         }
+     144             :         // Detects particles when reaching x = 0
+     145             :         return DETECTED;
+     146             : }
+     147             : 
+     148           0 : std::string Observer1D::getDescription() const {
+     149           0 :         return "Observer1D: observer at x = 0";
+     150             : }
+     151             : 
+     152             : // ObserverRedshiftWindow -----------------------------------------------------
+     153           0 : ObserverRedshiftWindow::ObserverRedshiftWindow(double zmin, double zmax) :
+     154           0 :                 zmin(zmin), zmax(zmax) {
+     155           0 : }
+     156             : 
+     157           0 : DetectionState ObserverRedshiftWindow::checkDetection(
+     158             :                 Candidate *candidate) const {
+     159           0 :         double z = candidate->getRedshift();
+     160           0 :         if (z > zmax)
+     161             :                 return VETO;
+     162           0 :         if (z < zmin)
+     163           0 :                 return VETO;
+     164             :         return NOTHING;
+     165             : }
+     166             : 
+     167           0 : std::string ObserverRedshiftWindow::getDescription() const {
+     168           0 :         std::stringstream ss;
+     169           0 :         ss << "ObserverRedshiftWindow: z = " << zmin << " - " << zmax;
+     170           0 :         return ss.str();
+     171           0 : }
+     172             : 
+     173             : // ObserverInactiveVeto -------------------------------------------------------
+     174           0 : DetectionState ObserverInactiveVeto::checkDetection(Candidate *c) const {
+     175           0 :         if (not(c->isActive()))
+     176           0 :                 return VETO;
+     177             :         return NOTHING;
+     178             : }
+     179             : 
+     180           0 : std::string ObserverInactiveVeto::getDescription() const {
+     181           0 :         return "ObserverInactiveVeto";
+     182             : }
+     183             : 
+     184             : // ObserverNucleusVeto --------------------------------------------------------
+     185           0 : DetectionState ObserverNucleusVeto::checkDetection(Candidate *c) const {
+     186           0 :         if (isNucleus(c->current.getId()))
+     187           0 :                 return VETO;
+     188             :         return NOTHING;
+     189             : }
+     190             : 
+     191           0 : std::string ObserverNucleusVeto::getDescription() const {
+     192           0 :         return "ObserverNucleusVeto";
+     193             : }
+     194             : 
+     195             : // ObserverNeutrinoVeto -------------------------------------------------------
+     196           0 : DetectionState ObserverNeutrinoVeto::checkDetection(Candidate *c) const {
+     197           0 :         int id = abs(c->current.getId());
+     198           0 :         if ((id == 12) or (id == 14) or (id == 16))
+     199           0 :                 return VETO;
+     200             :         return NOTHING;
+     201             : }
+     202             : 
+     203           0 : std::string ObserverNeutrinoVeto::getDescription() const {
+     204           0 :         return "ObserverNeutrinoVeto";
+     205             : }
+     206             : 
+     207             : // ObserverPhotonVeto ---------------------------------------------------------
+     208           0 : DetectionState ObserverPhotonVeto::checkDetection(Candidate *c) const {
+     209           0 :         if (c->current.getId() == 22)
+     210           0 :                 return VETO;
+     211             :         return NOTHING;
+     212             : }
+     213             : 
+     214           0 : std::string ObserverPhotonVeto::getDescription() const {
+     215           0 :         return "ObserverPhotonVeto";
+     216             : }
+     217             : 
+     218             : // ObserverElectronVeto ---------------------------------------------------------
+     219           0 : DetectionState ObserverElectronVeto::checkDetection(Candidate *c) const {
+     220           0 :         if (abs(c->current.getId()) == 11)
+     221           0 :                 return VETO;
+     222             :         return NOTHING;
+     223             : }
+     224             : 
+     225           0 : std::string ObserverElectronVeto::getDescription() const {
+     226           0 :         return "ObserverElectronVeto";
+     227             : }
+     228             : 
+     229             : // ObserverCustomVeto -------------------------------------------------------
+     230           0 : ObserverParticleIdVeto::ObserverParticleIdVeto(int pId) {
+     231           0 :         vetoParticleId = pId;
+     232           0 : }
+     233             : 
+     234           0 : DetectionState ObserverParticleIdVeto::checkDetection(Candidate *c) const {
+     235           0 :         if (c->current.getId() == vetoParticleId)
+     236           0 :                 return VETO;
+     237             :         return NOTHING;
+     238             : }
+     239             : 
+     240           0 : std::string ObserverParticleIdVeto::getDescription() const {
+     241           0 :         return "ObserverParticleIdVeto";
+     242             : }
+     243             : 
+     244             : 
+     245             : // ObserverTimeEvolution --------------------------------------------------------
+     246           0 : ObserverTimeEvolution::ObserverTimeEvolution() {}
+     247             : 
+     248           1 : ObserverTimeEvolution::ObserverTimeEvolution(double min, double dist, double numb) {
+     249           1 :         double max = min + numb * dist;
+     250             :         bool log = false;
+     251           1 :         addTimeRange(min, max, numb, log);
+     252           1 : }
+     253             : 
+     254           1 : ObserverTimeEvolution::ObserverTimeEvolution(double min, double max, double numb, bool log) {
+     255           1 :         addTimeRange(min, max, numb, log);
+     256           1 : }
+     257             : 
+     258             : 
+     259           6 : DetectionState ObserverTimeEvolution::checkDetection(Candidate *c) const {
+     260             : 
+     261           6 :         if (detList.size()) {
+     262           6 :                 double length = c->getTrajectoryLength();
+     263             :                 size_t index;
+     264           6 :                 const std::string DI = "DetectionIndex";
+     265             :                 std::string value;
+     266             : 
+     267             :                 // Load the last detection index
+     268           6 :                 if (c->hasProperty(DI)) {
+     269           4 :                         index = c->getProperty(DI).asUInt64();
+     270             :                 }
+     271             :                 else {
+     272             :                         index = 0;
+     273             :                 }
+     274             : 
+     275             :                 // Break if the particle has been detected once for all detList entries.
+     276           6 :                 if (index > detList.size()) {
+     277             :                         return NOTHING;
+     278             :                 }
+     279             : 
+     280             :                 // Calculate the distance to next detection
+     281           6 :                 double distance = length - detList[index];
+     282             : 
+     283             :                 // Limit next step and detect candidate.
+     284             :                 // Increase the index by one in case of detection
+     285           6 :                 if (distance < 0.) {
+     286           2 :                         c->limitNextStep(-distance);
+     287             :                         return NOTHING;
+     288             :                 }
+     289             :                 else {
+     290             : 
+     291           4 :                         if (index < detList.size()-1) {
+     292           2 :                                 c->limitNextStep(detList[index+1]-length);
+     293             :                         }
+     294           4 :                         c->setProperty(DI, Variant::fromUInt64(index+1));
+     295             : 
+     296           4 :                         return DETECTED;
+     297             :                 }
+     298             :         }
+     299             :         return NOTHING;
+     300             : }
+     301             : 
+     302           4 : void ObserverTimeEvolution::addTime(const double& t) {
+     303           4 :         detList.push_back(t);
+     304           4 : }
+     305             : 
+     306           2 : void ObserverTimeEvolution::addTimeRange(double min, double max, double numb, bool log) {
+     307           6 :         for (size_t i = 0; i < numb; i++) {
+     308           4 :                 if (log == true) {
+     309           2 :                         addTime(min * pow(max / min, i / (numb - 1.0)));
+     310             :                 } else {
+     311           2 :                         addTime(min + i * (max - min) / numb);
+     312             :                 }
+     313             :         }
+     314           2 : }
+     315             : 
+     316           0 : const std::vector<double>& ObserverTimeEvolution::getTimes() const {
+     317           0 :         return detList;
+     318             : }
+     319             : 
+     320           0 : std::string ObserverTimeEvolution::getDescription() const {
+     321           0 :         std::stringstream s;
+     322           0 :         s << "List of Detection lengths in kpc";
+     323           0 :         for (size_t i = 0; i < detList.size(); i++)
+     324           0 :           s << "  - " << detList[i] / kpc;
+     325           0 :         return s.str();
+     326           0 : }
+     327             : 
+     328             : // ObserverSurface--------------------------------------------------------------
+     329           2 : ObserverSurface::ObserverSurface(Surface* _surface) : surface(_surface) { }
+     330             : 
+     331           4 : DetectionState ObserverSurface::checkDetection(Candidate *candidate) const
+     332             : {
+     333           4 :                 double currentDistance = surface->distance(candidate->current.getPosition());
+     334           4 :                 double previousDistance = surface->distance(candidate->previous.getPosition());
+     335           4 :                 candidate->limitNextStep(fabs(currentDistance));
+     336             : 
+     337           4 :                 if (currentDistance * previousDistance > 0)
+     338             :                         return NOTHING;
+     339           2 :                 else if (previousDistance == 0)
+     340             :                         return NOTHING;
+     341             :                 else
+     342           2 :                         return DETECTED;
+     343             : }
+     344             : 
+     345           0 : std::string ObserverSurface::getDescription() const {
+     346           0 :         std::stringstream ss;
+     347           0 :         ss << "ObserverSurface: << " << surface->getDescription();
+     348           0 :         return ss.str();
+     349           0 : }
+     350             : 
+     351             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Output.cpp.func-sort-c.html b/doc/coverageReport/src/module/Output.cpp.func-sort-c.html new file mode 100644 index 000000000..8aa2d21bc --- /dev/null +++ b/doc/coverageReport/src/module/Output.cpp.func-sort-c.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Output.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:889889.8 %
Date:2024-04-08 14:58:22Functions:141687.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Output14setEnergyScaleEd0
_ZN7crpropa6Output14setLengthScaleEd0
_ZN7crpropa6Output10disableAllEv1
_ZN7crpropa6Output14enablePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantES8_1
_ZN7crpropa6Output7disableENS0_12OutputColumnE1
_ZNK7crpropa6Output4sizeEv1
_ZN7crpropa6Output6enableENS0_12OutputColumnE2
_ZN7crpropa6OutputC2Ev4
_ZN7crpropa6Output9enableAllEv5
_ZN7crpropa6Output13setOutputTypeENS0_10OutputTypeE8
_ZN7crpropa6OutputC2ENS0_10OutputTypeE8
_ZN7crpropa6Output5set1DEb9
_ZN7crpropa6Output14OutputTypeNameB5cxx11ENS0_10OutputTypeE12
_ZN7crpropa6Output3setENS0_12OutputColumnEb38
_ZNK7crpropa6Output7processEPNS_9CandidateE59
_ZN7crpropa6Output6modifyEv65
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Output.cpp.func.html b/doc/coverageReport/src/module/Output.cpp.func.html new file mode 100644 index 000000000..e967462c5 --- /dev/null +++ b/doc/coverageReport/src/module/Output.cpp.func.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Output.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:889889.8 %
Date:2024-04-08 14:58:22Functions:141687.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Output10disableAllEv1
_ZN7crpropa6Output13setOutputTypeENS0_10OutputTypeE8
_ZN7crpropa6Output14OutputTypeNameB5cxx11ENS0_10OutputTypeE12
_ZN7crpropa6Output14enablePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantES8_1
_ZN7crpropa6Output14setEnergyScaleEd0
_ZN7crpropa6Output14setLengthScaleEd0
_ZN7crpropa6Output3setENS0_12OutputColumnEb38
_ZN7crpropa6Output5set1DEb9
_ZN7crpropa6Output6enableENS0_12OutputColumnE2
_ZN7crpropa6Output6modifyEv65
_ZN7crpropa6Output7disableENS0_12OutputColumnE1
_ZN7crpropa6Output9enableAllEv5
_ZN7crpropa6OutputC2ENS0_10OutputTypeE8
_ZN7crpropa6OutputC2Ev4
_ZNK7crpropa6Output4sizeEv1
_ZNK7crpropa6Output7processEPNS_9CandidateE59
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Output.cpp.gcov.html b/doc/coverageReport/src/module/Output.cpp.gcov.html new file mode 100644 index 000000000..d08f567ad --- /dev/null +++ b/doc/coverageReport/src/module/Output.cpp.gcov.html @@ -0,0 +1,210 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Output.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:889889.8 %
Date:2024-04-08 14:58:22Functions:141687.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/Output.h"
+       2             : #include "crpropa/Units.h"
+       3             : 
+       4             : #include <stdexcept>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           4 : Output::Output() : outputName(OutputTypeName(Everything)), lengthScale(Mpc), energyScale(EeV), oneDimensional(false), count(0) {
+       9           4 :         enableAll();
+      10           4 : }
+      11             : 
+      12           8 : Output::Output(OutputType outputType) : outputName(OutputTypeName(outputType)), lengthScale(Mpc), energyScale(EeV), oneDimensional(false), count(0) {
+      13           8 :         setOutputType(outputType);
+      14           8 : }
+      15             : 
+      16          12 : std::string Output::OutputTypeName(OutputType outputType) {
+      17          12 :         if (outputType == Trajectory1D)
+      18           1 :                 return "Trajectory1D";
+      19          11 :         if (outputType == Event1D)
+      20           4 :                 return "Event1D";
+      21           7 :         if (outputType == Trajectory3D)
+      22           1 :                 return "Trajectory3D";
+      23           6 :         if (outputType == Event3D)
+      24           1 :                 return "Event3D";
+      25           5 :         return "Everything";
+      26             : }
+      27             : 
+      28          65 : void Output::modify() {
+      29          65 :         if (count > 0)
+      30           0 :                 throw std::runtime_error("Output: cannot change Output parameters after data has been written to file.");
+      31          65 : }
+      32             : 
+      33          59 : void Output::process(Candidate *c) const {
+      34          59 :         count++;
+      35          59 : }
+      36             : 
+      37           8 : void Output::setOutputType(OutputType outputtype) {
+      38           8 :         modify();
+      39           8 :         if (outputtype == Trajectory1D) {
+      40             :                 // X, ID, E
+      41           1 :                 set(CurrentPositionColumn, true);
+      42           1 :                 set(CurrentIdColumn, true);
+      43           1 :                 set(CurrentEnergyColumn, true);
+      44           1 :                 set1D(true);
+      45           7 :         } else if (outputtype == Event1D) {
+      46             :                 // D, ID, E, ID0, E0
+      47           4 :                 set(TrajectoryLengthColumn, true);
+      48           4 :                 set(CurrentIdColumn, true);
+      49           4 :                 set(CurrentEnergyColumn, true);
+      50           4 :                 set(SourceIdColumn, true);
+      51           4 :                 set(SourceEnergyColumn, true);
+      52           4 :                 set1D(true);
+      53           3 :         } else if (outputtype == Trajectory3D) {
+      54             :                 // D, ID, E, X, Y, Z, Px, Py, Pz
+      55           1 :                 set(TrajectoryLengthColumn, true);
+      56           1 :                 set(CurrentIdColumn, true);
+      57           1 :                 set(CurrentEnergyColumn, true);
+      58           1 :                 set(CurrentPositionColumn, true);
+      59           1 :                 set(CurrentDirectionColumn, true);
+      60           1 :                 set1D(false);
+      61           2 :         } else if (outputtype == Event3D) {
+      62             :                 // D, ID, E, X, Y, Z, Px, Py, Pz, ID0, E0, X0, Y0, Z0, P0x, P0y, P0z
+      63           1 :                 set(TrajectoryLengthColumn, true);
+      64           1 :                 set(CurrentIdColumn, true);
+      65           1 :                 set(CurrentEnergyColumn, true);
+      66           1 :                 set(CurrentPositionColumn, true);
+      67           1 :                 set(CurrentDirectionColumn, true);
+      68           1 :                 set(SourceIdColumn, true);
+      69           1 :                 set(SourceEnergyColumn, true);
+      70           1 :                 set(SourcePositionColumn, true);
+      71           1 :                 set(SourceDirectionColumn, true);
+      72           1 :                 set1D(false);
+      73           1 :         } else if (outputtype == Everything) {
+      74           1 :                 enableAll();
+      75           1 :                 set1D(false);
+      76             :         } else {
+      77           0 :                 throw std::runtime_error("Output: unknown output type");
+      78             :         }
+      79           8 : }
+      80             : 
+      81           0 : void Output::setEnergyScale(double scale) {
+      82           0 :         modify();
+      83           0 :         energyScale = scale;
+      84           0 : }
+      85             : 
+      86           0 : void Output::setLengthScale(double scale) {
+      87           0 :         modify();
+      88           0 :         lengthScale = scale;
+      89           0 : }
+      90             : 
+      91           9 : void Output::set1D(bool value) {
+      92           9 :         modify();
+      93           9 :         oneDimensional = value;
+      94           9 : }
+      95             : 
+      96           2 : void Output::enable(OutputColumn field) {
+      97           2 :         modify();
+      98           2 :         fields.set(field, true);
+      99           2 : }
+     100             : 
+     101           1 : void Output::disable(OutputColumn field) {
+     102           1 :         modify();
+     103           1 :         fields.set(field, false);
+     104           1 : }
+     105             : 
+     106          38 : void Output::set(OutputColumn field, bool value) {
+     107          38 :         modify();
+     108          38 :         fields.set(field, value);
+     109          38 : }
+     110             : 
+     111           5 : void Output::enableAll() {
+     112           5 :         modify();
+     113             :         fields.set();
+     114           5 : }
+     115             : 
+     116           1 : void Output::disableAll() {
+     117           1 :         modify();
+     118             :         fields.reset();
+     119           1 : }
+     120             : 
+     121           1 : size_t Output::size() const {
+     122           1 :         return count;
+     123             : }
+     124             : 
+     125           1 : void Output::enableProperty(const std::string &property, const Variant &defaultValue, const std::string &comment) {
+     126           1 :         modify();
+     127           1 :         Property prop;
+     128             :         prop.name = property;
+     129             :         prop.comment = comment;
+     130           1 :         prop.defaultValue = defaultValue;
+     131           1 :         properties.push_back(prop);
+     132           1 : };
+     133             : 
+     134             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html b/doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html new file mode 100644 index 000000000..98f8d83aa --- /dev/null +++ b/doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/OutputShell.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - OutputShell.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa11ShellOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ShellOutput7processEPNS_9CandidateE0
_ZNK7crpropa13ShellOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ShellOutput1D7processEPNS_9CandidateE0
_ZNK7crpropa19ShellPropertyOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ShellPropertyOutput7processEPNS_9CandidateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/OutputShell.cpp.func.html b/doc/coverageReport/src/module/OutputShell.cpp.func.html new file mode 100644 index 000000000..2ba776c67 --- /dev/null +++ b/doc/coverageReport/src/module/OutputShell.cpp.func.html @@ -0,0 +1,96 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/OutputShell.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - OutputShell.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa11ShellOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ShellOutput7processEPNS_9CandidateE0
_ZNK7crpropa13ShellOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ShellOutput1D7processEPNS_9CandidateE0
_ZNK7crpropa19ShellPropertyOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ShellPropertyOutput7processEPNS_9CandidateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/OutputShell.cpp.gcov.html b/doc/coverageReport/src/module/OutputShell.cpp.gcov.html new file mode 100644 index 000000000..5ac2e949a --- /dev/null +++ b/doc/coverageReport/src/module/OutputShell.cpp.gcov.html @@ -0,0 +1,134 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/OutputShell.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - OutputShell.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/OutputShell.h"
+       2             : #include "crpropa/Units.h"
+       3             : 
+       4             : #include <iomanip>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8           0 : void ShellOutput::process(Candidate* c) const {
+       9           0 : #pragma omp critical
+      10             :         {
+      11             :                 std::cout << std::fixed << std::showpoint << std::setprecision(3)
+      12             :                                 << std::setw(6);
+      13           0 :                 std::cout << c->getTrajectoryLength() / Mpc << " Mpc,  ";
+      14           0 :                 std::cout << c->getRedshift() << ",  ";
+      15           0 :                 std::cout << c->current.getId() << ",  ";
+      16           0 :                 std::cout << c->current.getEnergy() / EeV << " EeV,  ";
+      17           0 :                 std::cout << c->current.getPosition() / Mpc << " Mpc,  ";
+      18           0 :                 std::cout << c->current.getDirection();
+      19             :                 std::cout << std::endl;
+      20             :         }
+      21           0 : }
+      22             : 
+      23           0 : std::string ShellOutput::getDescription() const {
+      24           0 :         return "Shell output";
+      25             : }
+      26             : 
+      27           0 : void ShellOutput1D::process(Candidate* c) const {
+      28           0 : #pragma omp critical
+      29             :         {
+      30             :                 std::cout << std::fixed << std::showpoint << std::setprecision(3)
+      31             :                                 << std::setw(6);
+      32           0 :                 std::cout << c->current.getPosition().x / Mpc << " Mpc,  ";
+      33           0 :                 std::cout << c->getRedshift() << ",  ";
+      34           0 :                 std::cout << c->current.getId() << ",  ";
+      35           0 :                 std::cout << c->current.getEnergy() / EeV << " EeV";
+      36             :                 std::cout << std::endl;
+      37             :         }
+      38           0 : }
+      39             : 
+      40           0 : std::string ShellOutput1D::getDescription() const {
+      41           0 :         return "Shell output for 1D";
+      42             : }
+      43             : 
+      44           0 : void ShellPropertyOutput::process(Candidate* c) const {
+      45             :         Candidate::PropertyMap::const_iterator i = c->properties.begin();
+      46           0 : #pragma omp critical
+      47             :         {
+      48           0 :                 for ( ; i != c->properties.end(); i++) {
+      49           0 :                         std::cout << "  " << i->first << ", " << i->second << std::endl;
+      50             :                 }
+      51             :         }
+      52           0 : }
+      53             : 
+      54           0 : std::string ShellPropertyOutput::getDescription() const {
+      55           0 :         return "Shell property output";
+      56             : }
+      57             : 
+      58             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html b/doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html new file mode 100644 index 000000000..066818d57 --- /dev/null +++ b/doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html @@ -0,0 +1,168 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ParticleCollector.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ParticleCollector.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:547275.0 %
Date:2024-04-08 14:58:22Functions:172470.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ParticleCollectorC2Em0
_ZN7crpropa17ParticleCollectorC2Emb0
_ZN7crpropa17ParticleCollectorC2Embb0
_ZNK7crpropa17ParticleCollector14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ParticleCollector3endEv0
_ZNK7crpropa17ParticleCollector5beginEv0
_ZNK7crpropa17ParticleCollector8getCloneEv0
_ZN7crpropa17ParticleCollector4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17ParticleCollector13getTrajectoryENS_7ref_ptrINS_10ModuleListEEEmNS1_INS_6ModuleEEE1
_ZNK7crpropa17ParticleCollector13getTrajectoryEPNS_10ModuleListEmPNS_6ModuleE1
_ZNK7crpropa17ParticleCollector4dumpERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa17ParticleCollector8setCloneEb2
_ZNK7crpropa17ParticleCollector12getContainerEv2
_ZNK7crpropa17ParticleCollector9reprocessEPNS_6ModuleE2
_ZN7crpropa17ParticleCollector5beginEv5
_ZNK7crpropa17ParticleCollector4sizeEv6
_ZN7crpropa17ParticleCollectorD0Ev8
_ZNK7crpropa17ParticleCollectorixEm8
_ZN7crpropa17ParticleCollector14clearContainerEv14
_ZN7crpropa17ParticleCollectorC2Ev14
_ZN7crpropa17ParticleCollectorD2Ev14
_ZN7crpropa17ParticleCollector3endEv30
_ZNK7crpropa17ParticleCollector7processENS_7ref_ptrINS_9CandidateEEE30
_ZNK7crpropa17ParticleCollector7processEPNS_9CandidateE3206
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ParticleCollector.cpp.func.html b/doc/coverageReport/src/module/ParticleCollector.cpp.func.html new file mode 100644 index 000000000..a393ca64a --- /dev/null +++ b/doc/coverageReport/src/module/ParticleCollector.cpp.func.html @@ -0,0 +1,168 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ParticleCollector.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ParticleCollector.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:547275.0 %
Date:2024-04-08 14:58:22Functions:172470.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ParticleCollector14clearContainerEv14
_ZN7crpropa17ParticleCollector3endEv30
_ZN7crpropa17ParticleCollector4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa17ParticleCollector5beginEv5
_ZN7crpropa17ParticleCollector8setCloneEb2
_ZN7crpropa17ParticleCollectorC2Em0
_ZN7crpropa17ParticleCollectorC2Emb0
_ZN7crpropa17ParticleCollectorC2Embb0
_ZN7crpropa17ParticleCollectorC2Ev14
_ZN7crpropa17ParticleCollectorD0Ev8
_ZN7crpropa17ParticleCollectorD2Ev14
_ZNK7crpropa17ParticleCollector12getContainerEv2
_ZNK7crpropa17ParticleCollector13getTrajectoryENS_7ref_ptrINS_10ModuleListEEEmNS1_INS_6ModuleEEE1
_ZNK7crpropa17ParticleCollector13getTrajectoryEPNS_10ModuleListEmPNS_6ModuleE1
_ZNK7crpropa17ParticleCollector14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ParticleCollector3endEv0
_ZNK7crpropa17ParticleCollector4dumpERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17ParticleCollector4sizeEv6
_ZNK7crpropa17ParticleCollector5beginEv0
_ZNK7crpropa17ParticleCollector7processENS_7ref_ptrINS_9CandidateEEE30
_ZNK7crpropa17ParticleCollector7processEPNS_9CandidateE3206
_ZNK7crpropa17ParticleCollector8getCloneEv0
_ZNK7crpropa17ParticleCollector9reprocessEPNS_6ModuleE2
_ZNK7crpropa17ParticleCollectorixEm8
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html b/doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html new file mode 100644 index 000000000..b881f5f25 --- /dev/null +++ b/doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html @@ -0,0 +1,194 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/ParticleCollector.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - ParticleCollector.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:547275.0 %
Date:2024-04-08 14:58:22Functions:172470.8 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/ParticleCollector.h"
+       2             : #include "crpropa/module/TextOutput.h"
+       3             : #include "crpropa/Units.h"
+       4             : 
+       5             : namespace crpropa {
+       6             : 
+       7          14 : ParticleCollector::ParticleCollector() : nBuffer(10e6), clone(false), recursive(false)  {
+       8          14 :         container.reserve(nBuffer); // for 1e6 candidates ~ 500MB of RAM
+       9          14 : }
+      10             : 
+      11           0 : ParticleCollector::ParticleCollector(const std::size_t nBuffer) : clone(false), recursive(false)  {
+      12           0 :         container.reserve(nBuffer);
+      13           0 : }
+      14             : 
+      15           0 : ParticleCollector::ParticleCollector(const std::size_t nBuffer, const bool clone) : recursive(false) {
+      16           0 :         container.reserve(nBuffer);
+      17           0 : }
+      18             : 
+      19           0 : ParticleCollector::ParticleCollector(const std::size_t nBuffer, const bool clone, const bool recursive) {
+      20           0 :         container.reserve(nBuffer);
+      21           0 : }
+      22             : 
+      23        3206 : void ParticleCollector::process(Candidate *c) const {
+      24        6412 : #pragma omp critical
+      25             :         {
+      26        3206 :                 if(clone)
+      27          50 :                         container.push_back(c->clone(recursive));
+      28             :                 else
+      29        6362 :                         container.push_back(c);
+      30             :         }
+      31        3206 : }
+      32             : 
+      33          30 : void ParticleCollector::process(ref_ptr<Candidate> c) const {
+      34          30 :         ParticleCollector::process((Candidate*) c);
+      35          30 : }
+      36             : 
+      37           2 : void ParticleCollector::reprocess(Module *action) const {
+      38          14 :         for (ParticleCollector::iterator itr = container.begin(); itr != container.end(); ++itr){
+      39          12 :                 if (clone)
+      40           0 :                         action->process((*(itr->get())).clone(false));
+      41             :                 else
+      42          12 :                         action->process(itr->get());
+      43             :         }
+      44           2 : }
+      45             : 
+      46           1 : void ParticleCollector::dump(const std::string &filename) const {
+      47           1 :         TextOutput output(filename.c_str(), Output::Everything);
+      48           1 :         reprocess(&output);
+      49           1 :         output.close();
+      50           1 : }
+      51             : 
+      52           1 : void ParticleCollector::load(const std::string &filename){
+      53           1 :         TextOutput::load(filename.c_str(), this);
+      54           1 : }
+      55             : 
+      56          22 : ParticleCollector::~ParticleCollector() {
+      57          14 :         clearContainer();
+      58          22 : }
+      59             : 
+      60           6 : std::size_t ParticleCollector::size() const {
+      61           6 :         return container.size();
+      62             : }
+      63             : 
+      64           8 : ref_ptr<Candidate> ParticleCollector::operator[](const std::size_t i) const {
+      65           8 :         return container[i];
+      66             : }
+      67             : 
+      68          14 : void ParticleCollector::clearContainer() {
+      69          14 :         container.clear();
+      70          14 : }
+      71             : 
+      72           2 : std::vector<ref_ptr<Candidate> >& ParticleCollector::getContainer() const {
+      73           2 :         return container;
+      74             : }
+      75             : 
+      76           2 : void ParticleCollector::setClone(bool b) {
+      77           2 :         clone = b;
+      78           2 : }
+      79             : 
+      80           0 : bool ParticleCollector::getClone() const {
+      81           0 :         return clone;
+      82             : }
+      83             : 
+      84           0 : std::string ParticleCollector::getDescription() const {
+      85           0 :         return "ParticleCollector";
+      86             : }
+      87             : 
+      88           5 : ParticleCollector::iterator ParticleCollector::begin() {
+      89           5 :         return container.begin();
+      90             : }
+      91             : 
+      92           0 : ParticleCollector::const_iterator ParticleCollector::begin() const {
+      93           0 :         return container.begin();
+      94             : }
+      95             : 
+      96          30 : ParticleCollector::iterator ParticleCollector::end() {
+      97          30 :         return container.end();
+      98             : }
+      99             : 
+     100           0 : ParticleCollector::const_iterator ParticleCollector::end() const {
+     101           0 :         return container.end();
+     102             : }
+     103             : 
+     104           1 : void ParticleCollector::getTrajectory(ModuleList* mlist, std::size_t i, Module *output) const {
+     105           1 :         ref_ptr<Candidate> c_tmp = container[i]->clone();
+     106             : 
+     107           1 :         c_tmp->restart();
+     108             : 
+     109           1 :         mlist->add(output);
+     110           1 :         mlist->run(c_tmp);
+     111           1 :         mlist->remove(mlist->size()-1);
+     112           1 : }
+     113             : 
+     114           1 : void ParticleCollector::getTrajectory(ref_ptr<ModuleList> mlist, std::size_t i, ref_ptr<Module> output) const {
+     115           1 :         ParticleCollector::getTrajectory((ModuleList*) mlist, i, (Module*) output);
+     116           1 : }
+     117             : 
+     118             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html b/doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html new file mode 100644 index 000000000..3a3f0982b --- /dev/null +++ b/doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html @@ -0,0 +1,120 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotoDisintegration.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotoDisintegration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:14017580.0 %
Date:2024-04-08 14:58:22Functions:101283.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoDisintegration10lossLengthEidd0
_ZN7crpropa19PhotoDisintegration8setLimitEd0
_ZN7crpropa19PhotoDisintegration14setHavePhotonsEb1
_ZN7crpropa19PhotoDisintegration17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa19PhotoDisintegration17getInteractionTagB5cxx11Ev2
_ZN7crpropa19PhotoDisintegrationC2ENS_7ref_ptrINS_11PhotonFieldEEEbd11
_ZN7crpropa19PhotoDisintegration13initBranchingENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoDisintegration18initPhotonEmissionENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZNK7crpropa19PhotoDisintegration18performInteractionEPNS_9CandidateEi265
_ZNK7crpropa19PhotoDisintegration7processEPNS_9CandidateE16849
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html b/doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html new file mode 100644 index 000000000..7207f6b5b --- /dev/null +++ b/doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html @@ -0,0 +1,120 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotoDisintegration.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotoDisintegration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:14017580.0 %
Date:2024-04-08 14:58:22Functions:101283.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoDisintegration10lossLengthEidd0
_ZN7crpropa19PhotoDisintegration13initBranchingENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration14setHavePhotonsEb1
_ZN7crpropa19PhotoDisintegration14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoDisintegration17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa19PhotoDisintegration18initPhotonEmissionENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration8setLimitEd0
_ZN7crpropa19PhotoDisintegrationC2ENS_7ref_ptrINS_11PhotonFieldEEEbd11
_ZNK7crpropa19PhotoDisintegration17getInteractionTagB5cxx11Ev2
_ZNK7crpropa19PhotoDisintegration18performInteractionEPNS_9CandidateEi265
_ZNK7crpropa19PhotoDisintegration7processEPNS_9CandidateE16849
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html b/doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html new file mode 100644 index 000000000..9d6164c97 --- /dev/null +++ b/doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html @@ -0,0 +1,406 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotoDisintegration.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotoDisintegration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:14017580.0 %
Date:2024-04-08 14:58:22Functions:101283.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/PhotoDisintegration.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/ParticleMass.h"
+       5             : #include "crpropa/Random.h"
+       6             : #include "kiss/logger.h"
+       7             : 
+       8             : #include <cmath>
+       9             : #include <limits>
+      10             : #include <sstream>
+      11             : #include <fstream>
+      12             : #include <stdexcept>
+      13             : 
+      14             : namespace crpropa {
+      15             : 
+      16             : const double PhotoDisintegration::lgmin = 6;  // minimum log10(Lorentz-factor)
+      17             : const double PhotoDisintegration::lgmax = 14; // maximum log10(Lorentz-factor)
+      18             : const size_t PhotoDisintegration::nlg = 201;  // number of Lorentz-factor steps
+      19             : 
+      20          11 : PhotoDisintegration::PhotoDisintegration(ref_ptr<PhotonField> f, bool havePhotons, double limit) {
+      21          11 :         setPhotonField(f);
+      22          11 :         this->havePhotons = havePhotons;
+      23          11 :         this->limit = limit;
+      24          11 : }
+      25             : 
+      26          22 : void PhotoDisintegration::setPhotonField(ref_ptr<PhotonField> photonField) {
+      27          22 :         this->photonField = photonField;
+      28          22 :         std::string fname = photonField->getFieldName();
+      29          22 :         setDescription("PhotoDisintegration: " + fname);
+      30          66 :         initRate(getDataPath("Photodisintegration/rate_" + fname + ".txt"));
+      31          66 :         initBranching(getDataPath("Photodisintegration/branching_" + fname + ".txt"));
+      32          66 :         initPhotonEmission(getDataPath("Photodisintegration/photon_emission_" + fname.substr(0,3) + ".txt"));
+      33          22 : }
+      34             : 
+      35           1 : void PhotoDisintegration::setHavePhotons(bool havePhotons) {
+      36           1 :         this->havePhotons = havePhotons;
+      37           1 : }
+      38             : 
+      39           0 : void PhotoDisintegration::setLimit(double limit) {
+      40           0 :         this->limit = limit;
+      41           0 : }
+      42             : 
+      43          22 : void PhotoDisintegration::initRate(std::string filename) {
+      44          22 :         std::ifstream infile(filename.c_str());
+      45          22 :         if (not infile.good())
+      46           0 :                 throw std::runtime_error("PhotoDisintegration: could not open file " + filename);
+      47             : 
+      48             :         // clear previously loaded interaction rates
+      49          22 :         pdRate.clear();
+      50          22 :         pdRate.resize(27 * 31);
+      51             : 
+      52             :         std::string line;
+      53        4158 :         while (std::getline(infile, line)) {
+      54        4136 :                 if (line[0] == '#')
+      55          66 :                         continue;
+      56        4070 :                 std::stringstream lineStream(line);
+      57             : 
+      58             :                 int Z, N;
+      59        4070 :                 lineStream >> Z;
+      60        4070 :                 lineStream >> N;
+      61             : 
+      62             :                 double r;
+      63      822140 :                 for (size_t i = 0; i < nlg; i++) {
+      64             :                         lineStream >> r;
+      65      818070 :                         pdRate[Z * 31 + N].push_back(r / Mpc);
+      66             :                 }
+      67        4070 :         }
+      68          22 :         infile.close();
+      69          22 : }
+      70             : 
+      71          22 : void PhotoDisintegration::initBranching(std::string filename) {
+      72          22 :         std::ifstream infile(filename.c_str());
+      73          22 :         if (not infile.good())
+      74           0 :                 throw std::runtime_error("PhotoDisintegration: could not open file " + filename);
+      75             : 
+      76             :         // clear previously loaded interaction rates
+      77          22 :         pdBranch.clear();
+      78          22 :         pdBranch.resize(27 * 31);
+      79             : 
+      80             :         std::string line;
+      81       48532 :         while (std::getline(infile, line)) {
+      82       48510 :                 if (line[0] == '#')
+      83          66 :                         continue;
+      84             : 
+      85       48444 :                 std::stringstream lineStream(line);
+      86             : 
+      87             :                 int Z, N;
+      88       48444 :                 lineStream >> Z;
+      89       48444 :                 lineStream >> N;
+      90             : 
+      91             :                 Branch branch;
+      92       48444 :                 lineStream >> branch.channel;
+      93             : 
+      94             :                 double r;
+      95     9785688 :                 for (size_t i = 0; i < nlg; i++) {
+      96             :                         lineStream >> r;
+      97     9737244 :                         branch.branchingRatio.push_back(r);
+      98             :                 }
+      99             : 
+     100       48444 :                 pdBranch[Z * 31 + N].push_back(branch);
+     101       48444 :         }
+     102             : 
+     103          22 :         infile.close();
+     104          22 : }
+     105             : 
+     106          22 : void PhotoDisintegration::initPhotonEmission(std::string filename) {
+     107          22 :         std::ifstream infile(filename.c_str());
+     108          22 :         if (not infile.good())
+     109           0 :                 throw std::runtime_error("PhotoDisintegration: could not open file " + filename);
+     110             : 
+     111             :         // clear previously loaded emission probabilities
+     112          22 :         pdPhoton.clear();
+     113             : 
+     114             :         std::string line;
+     115      209154 :         while (std::getline(infile, line)) {
+     116      209132 :                 if (line[0] == '#')
+     117          66 :                         continue;
+     118             : 
+     119      209066 :                 std::stringstream lineStream(line);
+     120             : 
+     121             :                 int Z, N, Zd, Nd;
+     122      209066 :                 lineStream >> Z;
+     123      209066 :                 lineStream >> N;
+     124      209066 :                 lineStream >> Zd;
+     125      209066 :                 lineStream >> Nd;
+     126             : 
+     127             :                 PhotonEmission em;
+     128             :                 lineStream >> em.energy;
+     129      209066 :                 em.energy *= eV;
+     130             : 
+     131             :                 double r;
+     132    42231332 :                 for (size_t i = 0; i < nlg; i++) {
+     133             :                         lineStream >> r;
+     134    42022266 :                         em.emissionProbability.push_back(r);
+     135             :                 }
+     136             : 
+     137      209066 :                 int key = Z * 1000000 + N * 10000 + Zd * 100 + Nd;
+     138      209066 :                 if (pdPhoton.find(key) == pdPhoton.end()) {
+     139             :                         std::vector<PhotonEmission> emissions;
+     140       41096 :                         pdPhoton[key] = emissions;
+     141       41096 :                 }
+     142      209066 :                 pdPhoton[key].push_back(em);
+     143      209066 :         }
+     144             : 
+     145          22 :         infile.close();
+     146          22 : }
+     147             : 
+     148       16849 : void PhotoDisintegration::process(Candidate *candidate) const {
+     149             :         // execute the loop at least once for limiting the next step
+     150       16849 :         double step = candidate->getCurrentStep();
+     151             :         do {
+     152             :                 // check if nucleus
+     153       17112 :                 int id = candidate->current.getId();
+     154       17112 :                 if (not isNucleus(id))
+     155             :                         return;
+     156             : 
+     157       17111 :                 int A = massNumber(id);
+     158       17111 :                 int Z = chargeNumber(id);
+     159       17111 :                 int N = A - Z;
+     160       17111 :                 size_t idx = Z * 31 + N;
+     161             : 
+     162             :                 // check if disintegration data available
+     163       17111 :                 if ((Z > 26) or (N > 30))
+     164             :                         return;
+     165       17111 :                 if (pdRate[idx].size() == 0)
+     166             :                         return;
+     167             : 
+     168             :                 // check if in tabulated energy range
+     169        1517 :                 double z = candidate->getRedshift();
+     170        1517 :                 double lg = log10(candidate->current.getLorentzFactor() * (1 + z));
+     171        1517 :                 if ((lg <= lgmin) or (lg >= lgmax))
+     172             :                         return;
+     173             : 
+     174        1517 :                 double rate = interpolateEquidistant(lg, lgmin, lgmax, pdRate[idx]);
+     175        1517 :                 rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z); // cosmological scaling, rate per comoving distance
+     176             : 
+     177             :                 // check if interaction occurs in this step
+     178             :                 // otherwise limit next step to a fraction of the mean free path
+     179        1517 :                 Random &random = Random::instance();
+     180        1517 :                 double randDist = -log(random.rand()) / rate;
+     181        1517 :                 if (step < randDist) {
+     182        1254 :                         candidate->limitNextStep(limit / rate);
+     183        1254 :                         return;
+     184             :                 }
+     185             : 
+     186             :                 // select channel and interact
+     187             :                 const std::vector<Branch> &branches = pdBranch[idx];
+     188         263 :                 double cmp = random.rand();
+     189         263 :                 int l = round((lg - lgmin) / (lgmax - lgmin) * (nlg - 1)); // index of closest tabulation point
+     190             :                 size_t i = 0;
+     191        2133 :                 while ((i < branches.size()) and (cmp > 0)) {
+     192        1870 :                         cmp -= branches[i].branchingRatio[l];
+     193        1870 :                         i++;
+     194             :                 }
+     195         263 :                 performInteraction(candidate, branches[i-1].channel);
+     196             : 
+     197             :                 // repeat with remaining step
+     198         263 :                 step -= randDist;
+     199         263 :         } while (step > 0);
+     200             : }
+     201             : 
+     202         265 : void PhotoDisintegration::performInteraction(Candidate *candidate, int channel) const {
+     203         265 :         KISS_LOG_DEBUG << "Photodisintegration::performInteraction. Channel " <<  channel << " on candidate " << candidate->getDescription(); 
+     204             :         // parse disintegration channel
+     205             :         int nNeutron = digit(channel, 100000);
+     206             :         int nProton = digit(channel, 10000);
+     207             :         int nH2 = digit(channel, 1000);
+     208             :         int nH3 = digit(channel, 100);
+     209             :         int nHe3 = digit(channel, 10);
+     210             :         int nHe4 = digit(channel, 1);
+     211             : 
+     212         265 :         int dA = -nNeutron - nProton - 2 * nH2 - 3 * nH3 - 3 * nHe3 - 4 * nHe4;
+     213         265 :         int dZ = -nProton - nH2 - nH3 - 2 * nHe3 - 2 * nHe4;
+     214             : 
+     215         265 :         int id = candidate->current.getId();
+     216         265 :         int A = massNumber(id);
+     217         265 :         int Z = chargeNumber(id);
+     218         265 :         double EpA = candidate->current.getEnergy() / A;
+     219             : 
+     220             :         // create secondaries
+     221         265 :         Random &random = Random::instance();
+     222         265 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     223             :         try
+     224             :         {
+     225         458 :                 for (size_t i = 0; i < nNeutron; i++)
+     226         193 :                         candidate->addSecondary(nucleusId(1, 0), EpA, pos, 1., interactionTag);
+     227         379 :                 for (size_t i = 0; i < nProton; i++)
+     228         114 :                         candidate->addSecondary(nucleusId(1, 1), EpA, pos, 1., interactionTag);
+     229         265 :                 for (size_t i = 0; i < nH2; i++)
+     230           0 :                         candidate->addSecondary(nucleusId(2, 1), EpA * 2, pos, 1., interactionTag);
+     231         267 :                 for (size_t i = 0; i < nH3; i++)
+     232           2 :                         candidate->addSecondary(nucleusId(3, 1), EpA * 3, pos, 1., interactionTag);
+     233         265 :                 for (size_t i = 0; i < nHe3; i++)
+     234           0 :                         candidate->addSecondary(nucleusId(3, 2), EpA * 3, pos, 1., interactionTag);
+     235         309 :                 for (size_t i = 0; i < nHe4; i++)
+     236          44 :                         candidate->addSecondary(nucleusId(4, 2), EpA * 4, pos, 1., interactionTag);
+     237             : 
+     238             : 
+     239             :         // update particle
+     240             :           candidate->created = candidate->current;
+     241         265 :                 candidate->current.setId(nucleusId(A + dA, Z + dZ));
+     242         265 :                 candidate->current.setEnergy(EpA * (A + dA));
+     243             :         }
+     244           0 :         catch (std::runtime_error &e)
+     245             :         {
+     246           0 :                 KISS_LOG_ERROR << "Something went wrong in the PhotoDisentigration\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
+     247           0 :                 throw;
+     248           0 :         }
+     249             : 
+     250         265 :         if (not havePhotons)
+     251             :                 return;
+     252             : 
+     253             :         // create photons
+     254          32 :         double z = candidate->getRedshift();
+     255          32 :         double lg = log10(candidate->current.getLorentzFactor() * (1 + z));
+     256          32 :         double lf = candidate->current.getLorentzFactor();
+     257             : 
+     258          32 :         int l = round((lg - lgmin) / (lgmax - lgmin) * (nlg - 1));  // index of closest tabulation point
+     259          32 :         int key = Z*1e6 + (A-Z)*1e4 + (Z+dZ)*1e2 + (A+dA) - (Z+dZ);
+     260             : 
+     261         227 :         for (int i = 0; i < pdPhoton[key].size(); i++) {
+     262             :                 // check for random emission
+     263         195 :                 if (random.rand() > pdPhoton[key][i].emissionProbability[l])
+     264         162 :                         continue;
+     265             : 
+     266             :                 // boost to lab frame
+     267          33 :                 double cosTheta = 2 * random.rand() - 1;
+     268          33 :                 double E = pdPhoton[key][i].energy * lf * (1 - cosTheta);
+     269          33 :                 candidate->addSecondary(22, E, pos, 1., interactionTag);
+     270             :         }
+     271             : }
+     272             : 
+     273           0 : double PhotoDisintegration::lossLength(int id, double gamma, double z) {
+     274             :         // check if nucleus
+     275           0 :         if (not (isNucleus(id)))
+     276             :                 return std::numeric_limits<double>::max();
+     277             : 
+     278           0 :         int A = massNumber(id);
+     279           0 :         int Z = chargeNumber(id);
+     280           0 :         int N = A - Z;
+     281           0 :         size_t idx = Z * 31 + N;
+     282             : 
+     283             :         // check if disintegration data available
+     284           0 :         if ((Z > 26) or (N > 30))
+     285             :                 return std::numeric_limits<double>::max();
+     286             :         const std::vector<double> &rate = pdRate[idx];
+     287           0 :         if (rate.size() == 0)
+     288             :                 return std::numeric_limits<double>::max();
+     289             : 
+     290             :         // check if in tabulated energy range
+     291           0 :         double lg = log10(gamma * (1 + z));
+     292           0 :         if ((lg <= lgmin) or (lg >= lgmax))
+     293             :                 return std::numeric_limits<double>::max();
+     294             : 
+     295             :         // total interaction rate
+     296           0 :         double lossRate = interpolateEquidistant(lg, lgmin, lgmax, rate);
+     297             : 
+     298             :         // comological scaling, rate per physical distance
+     299           0 :         lossRate *= pow_integer<3>(1 + z) * photonField->getRedshiftScaling(z);
+     300             : 
+     301             :         // average number of nucleons lost for all disintegration channels
+     302             :         double avg_dA = 0;
+     303             :         const std::vector<Branch> &branches = pdBranch[idx];
+     304           0 :         for (size_t i = 0; i < branches.size(); i++) {
+     305           0 :                 int channel = branches[i].channel;
+     306             :                 int dA = 0;
+     307             :                 dA += 1 * digit(channel, 100000);
+     308           0 :                 dA += 1 * digit(channel, 10000);
+     309           0 :                 dA += 2 * digit(channel, 1000);
+     310           0 :                 dA += 3 * digit(channel, 100);
+     311           0 :                 dA += 3 * digit(channel, 10);
+     312           0 :                 dA += 4 * digit(channel, 1);
+     313             : 
+     314           0 :                 double br = interpolateEquidistant(lg, lgmin, lgmax, branches[i].branchingRatio);
+     315           0 :                 avg_dA += br * dA;
+     316             :         }
+     317             : 
+     318           0 :         lossRate *= avg_dA / A;
+     319           0 :         return 1 / lossRate;
+     320             : }
+     321             : 
+     322           1 : void PhotoDisintegration::setInteractionTag(std::string tag) {
+     323           1 :         interactionTag = tag;
+     324           1 : }
+     325             : 
+     326           2 : std::string PhotoDisintegration::getInteractionTag() const {
+     327           2 :         return interactionTag;
+     328             : }
+     329             : 
+     330             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html new file mode 100644 index 000000000..7b6272449 --- /dev/null +++ b/doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html @@ -0,0 +1,232 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotoPionProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotoPionProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:24638763.6 %
Date:2024-04-08 14:58:22Functions:244060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoPionProduction10lossLengthEidd0
_ZN7crpropa19PhotoPionProduction12setSampleLogEb0
_ZN7crpropa19PhotoPionProduction16setHaveElectronsEb0
_ZN7crpropa19PhotoPionProduction16setHaveNeutrinosEb0
_ZN7crpropa19PhotoPionProduction19setCorrectionFactorEd0
_ZN7crpropa19PhotoPionProduction19setHaveAntiNucleonsEb0
_ZN7crpropa19PhotoPionProduction25setHaveRedshiftDependenceEb0
_ZN7crpropa19PhotoPionProduction8setLimitEd0
_ZNK7crpropa19PhotoPionProduction11sophiaEventEbdd0
_ZNK7crpropa19PhotoPionProduction12getSampleLogEv0
_ZNK7crpropa19PhotoPionProduction14getHavePhotonsEv0
_ZNK7crpropa19PhotoPionProduction16getHaveElectronsEv0
_ZNK7crpropa19PhotoPionProduction16getHaveNeutrinosEv0
_ZNK7crpropa19PhotoPionProduction19getHaveAntiNucleonsEv0
_ZNK7crpropa19PhotoPionProduction25getHaveRedshiftDependenceEv0
_ZNK7crpropa19PhotoPionProduction8getLimitEv0
_ZN7crpropa19PhotoPionProduction14setHavePhotonsEb1
_ZN7crpropa19PhotoPionProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa19PhotoPionProduction14getPhotonFieldEv1
_ZNK7crpropa19PhotoPionProduction19getCorrectionFactorEv1
_ZNK7crpropa19PhotoPionProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa19PhotoPionProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbbbbdb11
_ZN7crpropa19PhotoPionProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoPionProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZNK7crpropa19PhotoPionProduction17epsMinInteractionEbd28
_ZNK7crpropa19PhotoPionProduction18performInteractionEPNS_9CandidateEb28
_ZNK7crpropa19PhotoPionProduction9sampleEpsEbdd28
_ZNK7crpropa19PhotoPionProduction10probEpsMaxEbdddd29
_ZNK7crpropa19PhotoPionProduction7probEpsEdbdd10689
_ZNK7crpropa19PhotoPionProduction8momentumEbd10717
_ZNK7crpropa19PhotoPionProduction7processEPNS_9CandidateE15289
_ZNK7crpropa19PhotoPionProduction10nucleonMFPEddb16206
_ZNK7crpropa19PhotoPionProduction18nucleiModificationEii16206
_ZNK7crpropa19PhotoPionProduction11crossectionEdb170560
_ZNK7crpropa19PhotoPionProduction6functsEdb170560
_ZNK7crpropa19PhotoPionProduction4sMinEv191909
_ZNK7crpropa19PhotoPionProduction2PlEdddd320502
_ZNK7crpropa19PhotoPionProduction11breitwignerEddddb1442259
_ZNK7crpropa19PhotoPionProduction2EfEddd1612819
_ZNK7crpropa19PhotoPionProduction4massEb1815502
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html b/doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html new file mode 100644 index 000000000..4e52c0c59 --- /dev/null +++ b/doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html @@ -0,0 +1,232 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotoPionProduction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotoPionProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:24638763.6 %
Date:2024-04-08 14:58:22Functions:244060.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoPionProduction10lossLengthEidd0
_ZN7crpropa19PhotoPionProduction12setSampleLogEb0
_ZN7crpropa19PhotoPionProduction14setHavePhotonsEb1
_ZN7crpropa19PhotoPionProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoPionProduction16setHaveElectronsEb0
_ZN7crpropa19PhotoPionProduction16setHaveNeutrinosEb0
_ZN7crpropa19PhotoPionProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa19PhotoPionProduction19setCorrectionFactorEd0
_ZN7crpropa19PhotoPionProduction19setHaveAntiNucleonsEb0
_ZN7crpropa19PhotoPionProduction25setHaveRedshiftDependenceEb0
_ZN7crpropa19PhotoPionProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoPionProduction8setLimitEd0
_ZN7crpropa19PhotoPionProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbbbbdb11
_ZNK7crpropa19PhotoPionProduction10nucleonMFPEddb16206
_ZNK7crpropa19PhotoPionProduction10probEpsMaxEbdddd29
_ZNK7crpropa19PhotoPionProduction11breitwignerEddddb1442259
_ZNK7crpropa19PhotoPionProduction11crossectionEdb170560
_ZNK7crpropa19PhotoPionProduction11sophiaEventEbdd0
_ZNK7crpropa19PhotoPionProduction12getSampleLogEv0
_ZNK7crpropa19PhotoPionProduction14getHavePhotonsEv0
_ZNK7crpropa19PhotoPionProduction14getPhotonFieldEv1
_ZNK7crpropa19PhotoPionProduction16getHaveElectronsEv0
_ZNK7crpropa19PhotoPionProduction16getHaveNeutrinosEv0
_ZNK7crpropa19PhotoPionProduction17epsMinInteractionEbd28
_ZNK7crpropa19PhotoPionProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa19PhotoPionProduction18nucleiModificationEii16206
_ZNK7crpropa19PhotoPionProduction18performInteractionEPNS_9CandidateEb28
_ZNK7crpropa19PhotoPionProduction19getCorrectionFactorEv1
_ZNK7crpropa19PhotoPionProduction19getHaveAntiNucleonsEv0
_ZNK7crpropa19PhotoPionProduction25getHaveRedshiftDependenceEv0
_ZNK7crpropa19PhotoPionProduction2EfEddd1612819
_ZNK7crpropa19PhotoPionProduction2PlEdddd320502
_ZNK7crpropa19PhotoPionProduction4massEb1815502
_ZNK7crpropa19PhotoPionProduction4sMinEv191909
_ZNK7crpropa19PhotoPionProduction6functsEdb170560
_ZNK7crpropa19PhotoPionProduction7probEpsEdbdd10689
_ZNK7crpropa19PhotoPionProduction7processEPNS_9CandidateE15289
_ZNK7crpropa19PhotoPionProduction8getLimitEv0
_ZNK7crpropa19PhotoPionProduction8momentumEbd10717
_ZNK7crpropa19PhotoPionProduction9sampleEpsEbdd28
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html b/doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html new file mode 100644 index 000000000..5a80e6b6b --- /dev/null +++ b/doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html @@ -0,0 +1,758 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotoPionProduction.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotoPionProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:24638763.6 %
Date:2024-04-08 14:58:22Functions:244060.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/PhotoPionProduction.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/Random.h"
+       5             : 
+       6             : #include "kiss/convert.h"
+       7             : #include "kiss/logger.h"
+       8             : #include "sophia.h"
+       9             : 
+      10             : #include <limits>
+      11             : #include <cmath>
+      12             : #include <sstream>
+      13             : #include <fstream>
+      14             : #include <stdexcept>
+      15             : 
+      16             : namespace crpropa {
+      17             : 
+      18          11 : PhotoPionProduction::PhotoPionProduction(ref_ptr<PhotonField> field, bool photons, bool neutrinos, bool electrons, bool antiNucleons, double l, bool redshift) {
+      19          11 :         havePhotons = photons;
+      20          11 :         haveNeutrinos = neutrinos;
+      21          11 :         haveElectrons = electrons;
+      22          11 :         haveAntiNucleons = antiNucleons;
+      23          11 :         haveRedshiftDependence = redshift;
+      24          11 :         limit = l;
+      25          11 :         setPhotonField(field);
+      26          11 : }
+      27             : 
+      28          22 : void PhotoPionProduction::setPhotonField(ref_ptr<PhotonField> field) {
+      29          22 :         photonField = field;
+      30          22 :         std::string fname = photonField->getFieldName();
+      31          22 :         if (haveRedshiftDependence) {
+      32           0 :                 if (photonField->hasRedshiftDependence() == false){
+      33           0 :                         std::cout << "PhotoPionProduction: tabulated redshift dependence not needed for " + fname + ", switching off" << std::endl;
+      34           0 :                         haveRedshiftDependence = false;
+      35             :                 }
+      36             :                 else {
+      37           0 :                         KISS_LOG_WARNING << "PhotoPionProduction: You are using the 2-dimensional tabulated redshift evolution, which is not available for other interactions. To be consistent across all interactions you may deactivate this <setHaveRedshiftDependence(False)>.";
+      38             :                 }
+      39             :         }
+      40             :         
+      41          22 :         setDescription("PhotoPionProduction: " + fname);
+      42          22 :         if (haveRedshiftDependence){
+      43           0 :                 initRate(getDataPath("PhotoPionProduction/rate_" + fname.replace(0, 3, "IRBz") + ".txt"));
+      44             :         }
+      45             :         else
+      46          66 :                 initRate(getDataPath("PhotoPionProduction/rate_" + fname + ".txt"));
+      47          22 : }
+      48             : 
+      49           1 : void PhotoPionProduction::setHavePhotons(bool b) {
+      50           1 :         havePhotons = b;
+      51           1 : }
+      52             :         
+      53           0 : void PhotoPionProduction::setHaveElectrons(bool b) {
+      54           0 :         haveElectrons = b;
+      55           0 : }
+      56             : 
+      57           0 : void PhotoPionProduction::setHaveNeutrinos(bool b) {
+      58           0 :         haveNeutrinos = b;
+      59           0 : }
+      60             : 
+      61           0 : void PhotoPionProduction::setHaveAntiNucleons(bool b) {
+      62           0 :         haveAntiNucleons = b;
+      63           0 : }
+      64             : 
+      65           0 : void PhotoPionProduction::setHaveRedshiftDependence(bool b) {
+      66           0 :         haveRedshiftDependence = b;
+      67           0 :         setPhotonField(photonField);
+      68           0 : }
+      69             : 
+      70           0 : void PhotoPionProduction::setLimit(double l) {
+      71           0 :         limit = l;
+      72           0 : }
+      73             : 
+      74          22 : void PhotoPionProduction::initRate(std::string filename) {
+      75             :         // clear previously loaded tables
+      76          22 :         tabLorentz.clear();
+      77          22 :         tabRedshifts.clear();
+      78          22 :         tabProtonRate.clear();
+      79          22 :         tabNeutronRate.clear();
+      80             : 
+      81          22 :         std::ifstream infile(filename.c_str());
+      82          22 :         if (!infile.good())
+      83           0 :                 throw std::runtime_error("PhotoPionProduction: could not open file " + filename);
+      84             : 
+      85          22 :         if (haveRedshiftDependence) {
+      86             :                 double zOld = -1, aOld = -1;
+      87           0 :                 while (infile.good()) {
+      88           0 :                         if (infile.peek() == '#') {
+      89           0 :                                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+      90           0 :                                 continue;
+      91             :                         }
+      92             :                         double z, a, b, c;
+      93             :                         infile >> z >> a >> b >> c;
+      94           0 :                         if (!infile)
+      95             :                                 break;
+      96           0 :                         if (z > zOld) {
+      97           0 :                                 tabRedshifts.push_back(z);
+      98           0 :                                 zOld = z;
+      99             :                         }
+     100           0 :                         if (a > aOld) {
+     101           0 :                                 tabLorentz.push_back(pow(10, a));
+     102           0 :                                 aOld = a;
+     103             :                         }
+     104           0 :                         tabProtonRate.push_back(b / Mpc);
+     105           0 :                         tabNeutronRate.push_back(c / Mpc);
+     106             :                 }
+     107             :         } else {
+     108        5610 :                 while (infile.good()) {
+     109        5610 :                         if (infile.peek() == '#') {
+     110          66 :                                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+     111          66 :                                 continue;
+     112             :                         }
+     113             :                         double a, b, c;
+     114             :                         infile >> a >> b >> c;
+     115        5544 :                         if (!infile)
+     116             :                                 break;
+     117        5522 :                         tabLorentz.push_back(pow(10, a));
+     118        5522 :                         tabProtonRate.push_back(b / Mpc);
+     119        5522 :                         tabNeutronRate.push_back(c / Mpc);
+     120             :                 }
+     121             :         }
+     122             : 
+     123          22 :         infile.close();
+     124          22 : }
+     125             : 
+     126       16206 : double PhotoPionProduction::nucleonMFP(double gamma, double z, bool onProton) const {
+     127       16206 :         const std::vector<double> &tabRate = (onProton)? tabProtonRate : tabNeutronRate;
+     128             : 
+     129             :         // scale nucleus energy instead of background photon energy
+     130       16206 :         gamma *= (1 + z);
+     131       16206 :         if (gamma < tabLorentz.front() or (gamma > tabLorentz.back()))
+     132             :                 return std::numeric_limits<double>::max();
+     133             : 
+     134             :         double rate;
+     135       16206 :         if (haveRedshiftDependence)
+     136           0 :                 rate = interpolate2d(z, gamma, tabRedshifts, tabLorentz, tabRate);
+     137             :         else
+     138       16206 :                 rate = interpolate(gamma, tabLorentz, tabRate) * photonField->getRedshiftScaling(z);
+     139             : 
+     140             :         // cosmological scaling
+     141       16206 :         rate *= pow_integer<2>(1 + z);
+     142             : 
+     143       16206 :         return 1. / rate;
+     144             : }
+     145             : 
+     146       16206 : double PhotoPionProduction::nucleiModification(int A, int X) const {
+     147       16206 :         if (A == 1)
+     148             :                 return 1.;
+     149        1801 :         if (A <= 8)
+     150         453 :                 return 0.85 * pow(X, 2. / 3.);
+     151        1348 :         return 0.85 * X;
+     152             : }
+     153             : 
+     154       15289 : void PhotoPionProduction::process(Candidate *candidate) const {
+     155       15289 :         double step = candidate->getCurrentStep();
+     156       15289 :         double z = candidate->getRedshift();
+     157             :         // the loop is processed at least once for limiting the next step
+     158             :         do {
+     159             :                 // check if nucleus
+     160       15307 :                 int id = candidate->current.getId();
+     161       15307 :                 if (!isNucleus(id))
+     162             :                         return;
+     163             : 
+     164             :                 // find interaction with minimum random distance
+     165       15306 :                 Random &random = Random::instance();
+     166             :                 double randDistance = std::numeric_limits<double>::max();
+     167             :                 double meanFreePath;
+     168             :                 double totalRate = 0;
+     169             :                 bool onProton = true; // interacting particle: proton or neutron
+     170             : 
+     171       15306 :                 int A = massNumber(id);
+     172       15306 :                 int Z = chargeNumber(id);
+     173       15306 :                 int N = A - Z;
+     174       15306 :                 double gamma = candidate->current.getLorentzFactor();
+     175             : 
+     176             :                 // check for interaction on protons
+     177       15306 :                 if (Z > 0) {
+     178       14758 :                         meanFreePath = nucleonMFP(gamma, z, true) / nucleiModification(A, Z);
+     179       14758 :                         randDistance = -log(random.rand()) * meanFreePath;
+     180       14758 :                         totalRate += 1. / meanFreePath;
+     181             :                 }
+     182             :                 // check for interaction on neutrons
+     183       15306 :                 if (N > 0) {
+     184        1448 :                         meanFreePath = nucleonMFP(gamma, z, false) / nucleiModification(A, N);
+     185        1448 :                         totalRate += 1. / meanFreePath;
+     186        1448 :                         double d = -log(random.rand()) * meanFreePath;
+     187        1448 :                         if (d < randDistance) {
+     188             :                                 randDistance = d;
+     189             :                                 onProton = false;
+     190             :                         }
+     191             :                 }
+     192             : 
+     193             :                 // check if interaction does not happen
+     194       15306 :                 if (step < randDistance) {
+     195       15288 :                         if (totalRate > 0.)
+     196       15288 :                                 candidate->limitNextStep(limit / totalRate);
+     197       15288 :                         return;
+     198             :                 }
+     199             : 
+     200             :                 // interact and repeat with remaining step
+     201          18 :                 performInteraction(candidate, onProton);
+     202          18 :                 step -= randDistance;
+     203          18 :         } while (step > 0);
+     204             : }
+     205             : 
+     206          28 : void PhotoPionProduction::performInteraction(Candidate *candidate, bool onProton) const {
+     207          28 :         int id = candidate->current.getId();
+     208          28 :         int A = massNumber(id);
+     209          28 :         int Z = chargeNumber(id);
+     210          28 :         double E = candidate->current.getEnergy();
+     211          28 :         double EpA = E / A;
+     212          28 :         double z = candidate->getRedshift();
+     213             : 
+     214             :         // SOPHIA simulates interactions only for protons / neutrons.
+     215             :         // For anti-protons / neutrons assume charge symmetry and change all
+     216             :         // interaction products from particle <--> anti-particle (sign)
+     217          28 :         int sign = (id > 0) ? 1 : -1;
+     218             : 
+     219             :         // check if below SOPHIA's energy threshold
+     220          56 :         double E_threshold = (photonField->getFieldName() == "CMB") ? 3.72e18 * eV : 5.83e15 * eV;
+     221          28 :         if (EpA * (1 + z) < E_threshold)
+     222           0 :                 return;
+     223             : 
+     224             :         // SOPHIA - input:
+     225          28 :         int nature = 1 - static_cast<int>(onProton);  // 0=proton, 1=neutron
+     226          28 :         double Ein = EpA / GeV;  // GeV is the SOPHIA standard unit
+     227          28 :         double eps = sampleEps(onProton, EpA, z) / GeV;  // GeV for SOPHIA
+     228             : 
+     229             :         // SOPHIA - output:
+     230             :         double outputEnergy[5][2000];  // [GeV/c, GeV/c, GeV/c, GeV, GeV/c^2]
+     231             :         int outPartID[2000];
+     232             :         int nParticles;
+     233             : 
+     234          56 : #pragma omp critical
+     235             :         {
+     236          28 :                 sophiaevent_(nature, Ein, eps, outputEnergy, outPartID, nParticles);
+     237             :         }
+     238             : 
+     239          28 :         Random &random = Random::instance();
+     240          28 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     241             :         std::vector<int> pnType;  // filled with either 13 (proton) or 14 (neutron)
+     242             :         std::vector<double> pnEnergy;  // corresponding energies of proton or neutron
+     243          28 :         if (nParticles == 0)
+     244             :                 return;
+     245         146 :         for (int i = 0; i < nParticles; i++) { // loop over out-going particles
+     246         118 :                 double Eout = outputEnergy[3][i] * GeV; // only the energy is used; could be changed for more detail
+     247         118 :                 int pType = outPartID[i];
+     248         118 :                 switch (pType) {
+     249          28 :                 case 13: // proton
+     250             :                 case 14: // neutron
+     251             :                         // proton and neutron data is taken to determine primary particle in a later step
+     252          28 :                         pnType.push_back(pType);
+     253          28 :                         pnEnergy.push_back(Eout);
+     254             :                         break;
+     255           0 :                 case -13: // anti-proton
+     256             :                 case -14: // anti-neutron
+     257           0 :                         if (haveAntiNucleons)
+     258             :                                 try
+     259             :                                 {
+     260           0 :                                         candidate->addSecondary(-sign * nucleusId(1, 14 + pType), Eout, pos, 1., interactionTag);
+     261             :                                 }
+     262           0 :                                 catch (std::runtime_error &e)
+     263             :                                 {
+     264           0 :                                         KISS_LOG_ERROR<< "Something went wrong in the PhotoPionProduction (anti-nucleon production)\n" << "Something went wrong in the PhotoPionProduction\n"<< "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
+     265           0 :                                         throw;
+     266           0 :                                 }
+     267             :                         break;
+     268          22 :                 case 1: // photon
+     269          22 :                         if (havePhotons)
+     270          14 :                                 candidate->addSecondary(22, Eout, pos, 1., interactionTag);
+     271             :                         break;
+     272          12 :                 case 2: // positron
+     273          12 :                         if (haveElectrons)
+     274           2 :                                 candidate->addSecondary(sign * -11, Eout, pos, 1., interactionTag);
+     275             :                         break;
+     276           5 :                 case 3: // electron
+     277           5 :                         if (haveElectrons)
+     278           2 :                                 candidate->addSecondary(sign * 11, Eout, pos, 1., interactionTag);
+     279             :                         break;
+     280          12 :                 case 15: // nu_e
+     281          12 :                         if (haveNeutrinos)
+     282           2 :                                 candidate->addSecondary(sign * 12, Eout, pos, 1., interactionTag);
+     283             :                         break;
+     284           5 :                 case 16: // anti-nu_e
+     285           5 :                         if (haveNeutrinos)
+     286           2 :                                 candidate->addSecondary(sign * -12, Eout, pos, 1., interactionTag);
+     287             :                         break;
+     288          17 :                 case 17: // nu_mu
+     289          17 :                         if (haveNeutrinos)
+     290           4 :                                 candidate->addSecondary(sign * 14, Eout, pos, 1., interactionTag);
+     291             :                         break;
+     292          17 :                 case 18: // anti-nu_mu
+     293          17 :                         if (haveNeutrinos)
+     294           4 :                                 candidate->addSecondary(sign * -14, Eout, pos, 1., interactionTag);
+     295             :                         break;
+     296           0 :                 default:
+     297           0 :                         throw std::runtime_error("PhotoPionProduction: unexpected particle " + kiss::str(pType));
+     298             :                 }
+     299             :         }
+     300          28 :         double maxEnergy = *std::max_element(pnEnergy.begin(), pnEnergy.end());  // criterion for being declared primary
+     301          56 :         for (int i = 0; i < pnEnergy.size(); ++i) {
+     302          28 :                 if (pnEnergy[i] == maxEnergy) {  // nucleon is primary particle
+     303          28 :                         if (A == 1) {
+     304             :                                 // single interacting nucleon
+     305          25 :                                 candidate->current.setEnergy(pnEnergy[i]);
+     306             :                                 try
+     307             :                                 {
+     308          25 :                                         candidate->current.setId(sign * nucleusId(1, 14 - pnType[i]));
+     309             :                                 }
+     310           0 :                                 catch (std::runtime_error &e)
+     311             :                                 {
+     312           0 :                                         KISS_LOG_ERROR<< "Something went wrong in the PhotoPionProduction (primary particle, A==1)\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
+     313           0 :                                         throw;
+     314           0 :                                 }
+     315             :                         } else {
+     316             :                                 // interacting nucleon is part of nucleus: it is emitted from the nucleus
+     317           3 :                                 candidate->current.setEnergy(E - EpA);
+     318             :                                 try
+     319             :                                 {
+     320           3 :                                         candidate->current.setId(sign * nucleusId(A - 1, Z - int(onProton)));
+     321           3 :                                         candidate->addSecondary(sign * nucleusId(1, 14 - pnType[i]), pnEnergy[i], pos, 1., interactionTag);
+     322             :                                 }
+     323           0 :                                 catch (std::runtime_error &e)
+     324             :                                 {
+     325           0 :                                         KISS_LOG_ERROR<< "Something went wrong in the PhotoPionProduction (primary particle, A!=1)\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
+     326           0 :                                         throw;
+     327           0 :                                 }
+     328             :                         }
+     329             :                 } else {  // nucleon is secondary proton or neutron
+     330           0 :                         candidate->addSecondary(sign * nucleusId(1, 14 - pnType[i]), pnEnergy[i], pos, 1., interactionTag);
+     331             :                 }
+     332             :         }
+     333             : }
+     334             : 
+     335           0 : double PhotoPionProduction::lossLength(int id, double gamma, double z) {
+     336           0 :         int A = massNumber(id);
+     337           0 :         int Z = chargeNumber(id);
+     338           0 :         int N = A - Z;
+     339             : 
+     340             :         double lossRate = 0;
+     341           0 :         if (Z > 0)
+     342           0 :                 lossRate += 1 / nucleonMFP(gamma, z, true) * nucleiModification(A, Z);
+     343           0 :         if (N > 0)
+     344           0 :                 lossRate += 1 / nucleonMFP(gamma, z, false) * nucleiModification(A, N);
+     345             : 
+     346             :         // approximate the relative energy loss
+     347             :         // - nucleons keep the fraction of mass to delta-resonance mass
+     348             :         // - nuclei lose the energy 1/A the interacting nucleon is carrying
+     349           0 :         double relativeEnergyLoss = (A == 1) ? 1 - 938. / 1232. : 1. / A;
+     350           0 :         lossRate *= relativeEnergyLoss;
+     351             : 
+     352             :         // scaling factor: interaction rate --> energy loss rate
+     353           0 :         lossRate *= (1 + z);
+     354             : 
+     355           0 :         return 1. / lossRate;
+     356             : }
+     357             : 
+     358           0 : SophiaEventOutput PhotoPionProduction::sophiaEvent(bool onProton, double Ein, double eps) const {
+     359             :         // SOPHIA - input:
+     360           0 :         int nature = 1 - static_cast<int>(onProton);  // 0=proton, 1=neutron
+     361           0 :         Ein /= GeV;  // GeV is the SOPHIA standard unit
+     362           0 :         eps /= GeV;  // GeV for SOPHIA
+     363             : 
+     364             :         // SOPHIA - output:
+     365             :         double outputEnergy[5][2000];  // [Px GeV/c, Py GeV/c, Pz GeV/c, E GeV, m0 GeV/c^2]
+     366             :         int outPartID[2000];
+     367             :         int nParticles;
+     368             : 
+     369           0 :         sophiaevent_(nature, Ein, eps, outputEnergy, outPartID, nParticles);
+     370             : 
+     371             :         // convert SOPHIA IDs to PDG naming convention & create particles
+     372             :         SophiaEventOutput output;
+     373           0 :         output.nParticles = nParticles;
+     374           0 :         for (int i = 0; i < nParticles; ++i) {
+     375           0 :                 int id = 0;
+     376           0 :                 int partType = outPartID[i];
+     377           0 :                 switch (partType) {
+     378           0 :                         case 13:  // proton
+     379             :                         case 14:  // neutron
+     380           0 :                                 id = nucleusId(1, 14 - partType);
+     381           0 :                                 break;
+     382           0 :                         case -13:  // anti-proton
+     383             :                         case -14:  // anti-neutron
+     384           0 :                                 id = -nucleusId(1, 14 + partType);
+     385           0 :                                 break;
+     386           0 :                         case 1:  // photon
+     387           0 :                                 id = 22;
+     388           0 :                                 break;
+     389           0 :                         case 2:  // positron
+     390           0 :                                 id = -11;
+     391           0 :                                 break;
+     392           0 :                         case 3:  // electron
+     393           0 :                                 id = 11;
+     394           0 :                                 break;
+     395           0 :                         case 15:  // nu_e
+     396           0 :                                 id = 12;
+     397           0 :                                 break;
+     398           0 :                         case 16:  // anti-nu_e
+     399           0 :                                 id = -12;
+     400           0 :                                 break;
+     401           0 :                         case 17:  // nu_mu
+     402           0 :                                 id = 14;
+     403           0 :                                 break;
+     404           0 :                         case 18:  // anti-nu_mu
+     405           0 :                                 id = -14;
+     406           0 :                                 break;
+     407           0 :                         default:
+     408           0 :                                 throw std::runtime_error("PhotoPionProduction: unexpected particle " + kiss::str(partType));
+     409             :                 }
+     410           0 :                 output.energy.push_back(outputEnergy[3][i] * GeV); // only the energy is used; could be changed for more detail
+     411           0 :                 output.id.push_back(id);
+     412             :         }
+     413           0 :         return output;
+     414           0 : }
+     415             : 
+     416          28 : double PhotoPionProduction::sampleEps(bool onProton, double E, double z) const {
+     417             :         // sample eps between epsMin ... epsMax
+     418          28 :         double Ein = E / GeV;
+     419          56 :         double epsMin = std::max(photonField -> getMinimumPhotonEnergy(z) / eV, epsMinInteraction(onProton, Ein));
+     420          28 :         double epsMax = photonField -> getMaximumPhotonEnergy(z) / eV;
+     421          28 :         double pEpsMax = probEpsMax(onProton, Ein, z, epsMin, epsMax);
+     422             : 
+     423          28 :         Random &random = Random::instance();
+     424        5034 :         for (int i = 0; i < 1000000; i++) {
+     425        5034 :                 double eps = epsMin + random.rand() * (epsMax - epsMin);
+     426        5034 :                 double pEps = probEps(eps, onProton, Ein, z);
+     427        5034 :                 if (random.rand() * pEpsMax < pEps)
+     428          28 :                         return eps * eV;
+     429             :         }
+     430           0 :         throw std::runtime_error("error: no photon found in sampleEps, please make sure that photon field provides photons for the interaction by adapting the energy range of the tabulated photon field.");
+     431             : }
+     432             : 
+     433          28 : double PhotoPionProduction::epsMinInteraction(bool onProton, double Ein) const {
+     434             :         // labframe energy of least energetic photon where PPP can occur
+     435             :         // this kind-of ties samplingEps to the PPP and SOPHIA
+     436          28 :         const double m = mass(onProton);
+     437          28 :         const double p = momentum(onProton, Ein);
+     438          28 :         double epsMin = 1.e9 * (1.1646 - m * m) / 2. / (Ein + p); // eV
+     439          28 :         return epsMin;
+     440             : }
+     441             : 
+     442          29 : double PhotoPionProduction::probEpsMax(bool onProton, double Ein, double z, double epsMin, double epsMax) const {
+     443             :         // find pEpsMax by testing photon energies (eps) for their interaction
+     444             :         // probabilities (p) in order to find the maximum (max) probability
+     445             :         const int nrSteps = 100;
+     446             :         double pEpsMaxTested = 0.;
+     447             :         double step = 0.;
+     448          29 :         if (sampleLog){
+     449             :                 // sample in logspace with stepsize that is at max Δlog(E/eV) = 0.01 or otherwise dep. on size of energy range with nrSteps+1 steps log. equidis. spaced
+     450          29 :                 step = std::min(0.01, std::log10(epsMax / epsMin) / nrSteps);
+     451             :         } else
+     452           0 :                 step = (epsMax - epsMin) / nrSteps;
+     453             : 
+     454             :         double epsDummy = 0.;
+     455             :         int i = 0;
+     456        5684 :         while (epsDummy < epsMax) {
+     457        5655 :                 if (sampleLog)
+     458        5655 :                         epsDummy = epsMin * pow(10, step * i);
+     459             :                 else
+     460           0 :                         epsDummy = epsMin + step * i;
+     461        5655 :                 double p = probEps(epsDummy, onProton, Ein, z);
+     462        5655 :                 if(p > pEpsMaxTested)
+     463             :                         pEpsMaxTested = p;
+     464        5655 :                 i++;
+     465             :         }
+     466             :         // the following factor corrects for only trying to find the maximum on nrIteration photon energies
+     467             :         // the factor should be determined in convergence tests
+     468          29 :         double pEpsMax = pEpsMaxTested * correctionFactor;
+     469             : 
+     470          29 :         if(pEpsMax == 0) {
+     471           0 :                 KISS_LOG_WARNING << "pEpsMax is 0 in the following configuration: \n"
+     472           0 :                         << "\t" << "onProton: " << onProton << "\n"
+     473           0 :                         << "\t" << "Ein: " << Ein << " [GeV] \n"
+     474           0 :                         << "\t" << "epsRange [eV] " << epsMin << "\t" << epsMax << "\n"
+     475           0 :                         << "\t" << "redshift: " << z << "\n"
+     476           0 :                         << "\t" << "sample Log " << sampleLog << " with step " << step << " [eV] \n";
+     477             :         }
+     478             : 
+     479          29 :         return pEpsMax;
+     480             : }
+     481             : 
+     482       10689 : double PhotoPionProduction::probEps(double eps, bool onProton, double Ein, double z) const {
+     483             :         // probEps returns "probability to encounter a photon of energy eps", given a primary nucleon
+     484             :         // note, probEps does not return a normalized probability [0,...,1]
+     485       10689 :         double photonDensity = photonField->getPhotonDensity(eps * eV, z) * ccm / eps;
+     486       10689 :         if (photonDensity != 0.) {
+     487       10689 :                 const double p = momentum(onProton, Ein);
+     488       10689 :                 const double sMax = mass(onProton) * mass(onProton) + 2. * eps * (Ein + p) / 1.e9;
+     489       10689 :                 if (sMax <= sMin())
+     490             :                         return 0;
+     491       95940 :                 double sIntegr = gaussInt([this, onProton](double s) { return this->functs(s, onProton); }, sMin(), sMax);
+     492       10660 :                 return photonDensity * sIntegr / eps / eps / p / 8. * 1.e18 * 1.e6;
+     493             :         }
+     494             :         return 0;
+     495             : }
+     496             : 
+     497       10717 : double PhotoPionProduction::momentum(bool onProton, double Ein) const {
+     498       10717 :         const double m = mass(onProton);
+     499       10717 :         const double momentumHadron = sqrt(Ein * Ein - m * m);  // GeV/c
+     500       10717 :         return momentumHadron;
+     501             : }
+     502             : 
+     503      170560 : double PhotoPionProduction::crossection(double eps, bool onProton) const {
+     504      170560 :         const double m = mass(onProton);
+     505      170560 :         const double s = m * m + 2. * m * eps;
+     506      170560 :         if (s < sMin())
+     507             :                 return 0.;
+     508             :         double cross_res = 0.;
+     509             :         double cross_dir = 0.;
+     510             :         double cross_dir1 = 0.;
+     511             :         double cross_dir2 = 0.;
+     512             :         double sig_res[9];
+     513             : 
+     514             :         // first half of array: 9x proton resonance data | second half of array 9x neutron resonance data
+     515             :         static const double AMRES[18] = {1.231, 1.440, 1.515, 1.525, 1.675, 1.680, 1.690, 1.895, 1.950, 1.231, 1.440, 1.515, 1.525, 1.675, 1.675, 1.690, 1.895, 1.950};
+     516             :         static const double BGAMMA[18] = {5.6, 0.5, 4.6, 2.5, 1.0, 2.1, 2.0, 0.2, 1.0, 6.1, 0.3, 4.0, 2.5, 0.0, 0.2, 2.0, 0.2, 1.0};
+     517             :         static const double WIDTH[18] = {0.11, 0.35, 0.11, 0.1, 0.16, 0.125, 0.29, 0.35, 0.3, 0.11, 0.35, 0.11, 0.1, 0.16, 0.150, 0.29, 0.35, 0.3};
+     518             :         static const double RATIOJ[18] = {1., 0.5, 1., 0.5, 0.5, 1.5, 1., 1.5, 2., 1., 0.5, 1., 0.5, 0.5, 1.5, 1., 1.5, 2.};
+     519             :         static const double AM2[2] = {0.882792, 0.880351};
+     520             : 
+     521      170560 :         const int idx = onProton? 0 : 9;
+     522             :         double SIG0[9];
+     523     1705600 :         for (int i = 0; i < 9; ++i) {
+     524     1535040 :                 SIG0[i] = 4.893089117 / AM2[int(onProton)] * RATIOJ[i + idx] * BGAMMA[i + idx];
+     525             :         }
+     526      170560 :         if (eps <= 10.) {
+     527      160251 :                 cross_res = breitwigner(SIG0[0], WIDTH[0 + idx], AMRES[0 + idx], eps, onProton) * Ef(eps, 0.152, 0.17);
+     528             :                 sig_res[0] = cross_res;
+     529     1442259 :                 for (int i = 1; i < 9; ++i) {
+     530     1282008 :                         sig_res[i] = breitwigner(SIG0[i], WIDTH[i + idx], AMRES[i + idx], eps, onProton) * Ef(eps, 0.15, 0.38);
+     531     1282008 :                         cross_res += sig_res[i];
+     532             :                 }
+     533             :                 // direct channel
+     534      160251 :                 if ((eps > 0.1) && (eps < 0.6)) {
+     535       66492 :                         cross_dir1 = 92.7 * Pl(eps, 0.152, 0.25, 2.0)  // single pion production
+     536       66492 :                                            + 40. * std::exp(-(eps - 0.29) * (eps - 0.29) / 0.002)
+     537       66492 :                                            - 15. * std::exp(-(eps - 0.37) * (eps - 0.37) / 0.002);
+     538             :                 } else {
+     539       93759 :                         cross_dir1 = 92.7 * Pl(eps, 0.152, 0.25, 2.0);  // single pion production
+     540             :                 }
+     541      160251 :                 cross_dir2 = 37.7 * Pl(eps, 0.4, 0.6, 2.0);  // double pion production
+     542      160251 :                 cross_dir = cross_dir1 + cross_dir2;
+     543             :         }
+     544             :         // fragmentation 2:
+     545      170560 :         double cross_frag2 = onProton? 80.3 : 60.2;
+     546      170560 :         cross_frag2 *= Ef(eps, 0.5, 0.1) * std::pow(s, -0.34);
+     547             :         // multipion production/fragmentation 1 cross section
+     548             :         double cs_multidiff = 0.;
+     549             :         double cs_multi = 0.;
+     550             :         double cross_diffr1 = 0.;
+     551             :         double cross_diffr2 = 0.;
+     552             :         double cross_diffr = 0.;
+     553      170560 :         if (eps > 0.85) {
+     554       92272 :                 double ss1 = (eps - 0.85) / 0.69;
+     555       92272 :                 double ss2 = onProton? 29.3 : 26.4;
+     556       92272 :                 ss2 *= std::pow(s, -0.34) + 59.3 * std::pow(s, 0.095);
+     557       92272 :                 cs_multidiff = (1. - std::exp(-ss1)) * ss2;
+     558       92272 :                 cs_multi = 0.89 * cs_multidiff;
+     559             :                 // diffractive scattering:
+     560             :                 cross_diffr1 = 0.099 * cs_multidiff;
+     561             :                 cross_diffr2 = 0.011 * cs_multidiff;
+     562       92272 :                 cross_diffr = 0.11 * cs_multidiff;
+     563             :                 // **************************************
+     564       92272 :                 ss1 = std::pow(eps - 0.85, 0.75) / 0.64;
+     565       92272 :                 ss2 = 74.1 * std::pow(eps, -0.44) + 62. * std::pow(s, 0.08);
+     566       92272 :                 double cs_tmp = 0.96 * (1. - std::exp(-ss1)) * ss2;
+     567       92272 :                 cross_diffr1 = 0.14 * cs_tmp;
+     568       92272 :                 cross_diffr2 = 0.013 * cs_tmp;
+     569       92272 :                 double cs_delta = cross_frag2 - (cross_diffr1 + cross_diffr2 - cross_diffr);
+     570       92272 :                 if (cs_delta < 0.) {
+     571             :                         cross_frag2 = 0.;
+     572           0 :                         cs_multi += cs_delta;
+     573             :                 } else {
+     574             :                         cross_frag2 = cs_delta;
+     575             :                 }
+     576             :                 cross_diffr = cross_diffr1 + cross_diffr2;
+     577       92272 :                 cs_multidiff = cs_multi + cross_diffr;
+     578             :         // in the original SOPHIA code, here is a switch for the return argument.
+     579             :         // Here, only one case (compare in SOPHIA: NDIR=3) is needed.
+     580             :         }
+     581      170560 :         return cross_res + cross_dir + cs_multidiff + cross_frag2;
+     582             : }
+     583             : 
+     584      320502 : double PhotoPionProduction::Pl(double eps, double epsTh, double epsMax, double alpha) const {
+     585      320502 :         if (epsTh > eps)
+     586             :                 return 0.;
+     587      266687 :         const double a = alpha * epsMax / epsTh;
+     588      266687 :         const double prod1 = std::pow((eps - epsTh) / (epsMax - epsTh), a - alpha);
+     589      266687 :         const double prod2 = std::pow(eps / epsMax, -a);
+     590      266687 :         return prod1 * prod2;
+     591             : }
+     592             : 
+     593     1612819 : double PhotoPionProduction::Ef(double eps, double epsTh, double w) const {
+     594     1612819 :         const double wTh = w + epsTh;
+     595     1612819 :         if (eps <= epsTh) {
+     596             :                 return 0.;
+     597     1551121 :         } else if ((eps > epsTh) && (eps < wTh)) {
+     598      547581 :                 return (eps - epsTh) / w;
+     599     1003540 :         } else if (eps >= wTh) {
+     600             :                 return 1.;
+     601             :         } else {
+     602           0 :                 throw std::runtime_error("error in function Ef");
+     603             :         }
+     604             : }
+     605             : 
+     606     1442259 : double PhotoPionProduction::breitwigner(double sigma0, double gamma, double DMM, double epsPrime, bool onProton) const {
+     607     1442259 :         const double m = mass(onProton);
+     608     1442259 :         const double s = m * m + 2. * m * epsPrime;
+     609     1442259 :         const double gam2s = gamma * gamma * s;
+     610     1442259 :         return sigma0 * (s / epsPrime / epsPrime) * gam2s / ((s - DMM * DMM) * (s - DMM * DMM) + gam2s);
+     611             : }
+     612             : 
+     613      170560 : double PhotoPionProduction::functs(double s, bool onProton) const {
+     614      170560 :         const double m = mass(onProton);
+     615      170560 :         const double factor = s - m * m;
+     616      170560 :         const double epsPrime = factor / 2. / m;
+     617      170560 :         const double sigmaPg = crossection(epsPrime, onProton);
+     618      170560 :         return factor * sigmaPg;
+     619             : }
+     620             : 
+     621     1815502 : double PhotoPionProduction::mass(bool onProton) const {
+     622     1815502 :         const double m =  onProton ? mass_proton : mass_neutron;
+     623     1815502 :         return m / GeV * c_squared;
+     624             : }
+     625             : 
+     626      191909 : double PhotoPionProduction::sMin() const {
+     627      191909 :         return 1.1646; // [GeV^2] head-on collision
+     628             : }
+     629             : 
+     630           0 : void PhotoPionProduction::setSampleLog(bool b) {
+     631           0 :         sampleLog = b;
+     632           0 : }
+     633             : 
+     634           0 : void PhotoPionProduction::setCorrectionFactor(double factor) {
+     635           0 :         correctionFactor = factor;
+     636           0 : }
+     637             : 
+     638           1 : ref_ptr<PhotonField> PhotoPionProduction::getPhotonField() const {
+     639           1 :         return photonField;
+     640             : }
+     641             : 
+     642           0 : bool PhotoPionProduction::getHavePhotons() const {
+     643           0 :         return havePhotons;
+     644             : }
+     645             : 
+     646           0 : bool PhotoPionProduction::getHaveNeutrinos() const {
+     647           0 :         return haveNeutrinos;
+     648             : }
+     649             : 
+     650           0 : bool PhotoPionProduction::getHaveElectrons() const {
+     651           0 :         return haveElectrons;
+     652             : }
+     653             : 
+     654           0 : bool PhotoPionProduction::getHaveAntiNucleons() const {
+     655           0 :         return haveAntiNucleons;
+     656             : }
+     657             : 
+     658           0 : bool PhotoPionProduction::getHaveRedshiftDependence() const {
+     659           0 :         return haveRedshiftDependence;
+     660             : }
+     661             : 
+     662           0 : double PhotoPionProduction::getLimit() const {
+     663           0 :         return limit;
+     664             : }
+     665             : 
+     666           0 : bool PhotoPionProduction::getSampleLog() const {
+     667           0 :         return sampleLog;
+     668             : }
+     669             : 
+     670           1 : double PhotoPionProduction::getCorrectionFactor() const {
+     671           1 :         return correctionFactor;
+     672             : }
+     673             : 
+     674           1 : void PhotoPionProduction::setInteractionTag(std::string tag) {
+     675           1 :         interactionTag = tag;
+     676           1 : }
+     677             : 
+     678           2 : std::string PhotoPionProduction::getInteractionTag() const {
+     679           2 :         return interactionTag;
+     680             : }
+     681             : 
+     682             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html b/doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html new file mode 100644 index 000000000..20fda8338 --- /dev/null +++ b/doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html @@ -0,0 +1,108 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotonOutput1D.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotonOutput1D.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0560.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14PhotonOutput1D4gzipEv0
_ZN7crpropa14PhotonOutput1D5closeEv0
_ZN7crpropa14PhotonOutput1DC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa14PhotonOutput1DC2ERSo0
_ZN7crpropa14PhotonOutput1DC2Ev0
_ZN7crpropa14PhotonOutput1DD0Ev0
_ZN7crpropa14PhotonOutput1DD2Ev0
_ZNK7crpropa14PhotonOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa14PhotonOutput1D7processEPNS_9CandidateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html b/doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html new file mode 100644 index 000000000..bb7a35aac --- /dev/null +++ b/doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html @@ -0,0 +1,108 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotonOutput1D.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotonOutput1D.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0560.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14PhotonOutput1D4gzipEv0
_ZN7crpropa14PhotonOutput1D5closeEv0
_ZN7crpropa14PhotonOutput1DC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa14PhotonOutput1DC2ERSo0
_ZN7crpropa14PhotonOutput1DC2Ev0
_ZN7crpropa14PhotonOutput1DD0Ev0
_ZN7crpropa14PhotonOutput1DD2Ev0
_ZNK7crpropa14PhotonOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa14PhotonOutput1D7processEPNS_9CandidateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html b/doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html new file mode 100644 index 000000000..18cb674db --- /dev/null +++ b/doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html @@ -0,0 +1,180 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PhotonOutput1D.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PhotonOutput1D.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0560.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/PhotonOutput1D.h"
+       2             : #include "crpropa/Units.h"
+       3             : 
+       4             : #include <iostream>
+       5             : #include <sstream>
+       6             : #include <cstdio>
+       7             : #include <stdexcept>
+       8             : 
+       9             : #include "kiss/string.h"
+      10             : #include "kiss/logger.h"
+      11             : 
+      12             : #ifdef CRPROPA_HAVE_ZLIB
+      13             : #include <ozstream.hpp>
+      14             : #endif
+      15             : 
+      16             : using namespace std;
+      17             : 
+      18             : namespace crpropa {
+      19             : 
+      20           0 : PhotonOutput1D::PhotonOutput1D() : out(&std::cout) {
+      21           0 :         KISS_LOG_WARNING << "PhotonOutput1D is deprecated and will be removed in the future. Replace with TextOutput or HDF5Output with features ObserverNucleusVeto + ObserverDetectAll";
+      22           0 : }
+      23             : 
+      24           0 : PhotonOutput1D::PhotonOutput1D(std::ostream &out) : out(&out) {
+      25           0 :         KISS_LOG_WARNING << "PhotonOutput1D is deprecated and will be removed in the future. Replace with TextOutput or HDF5Output with features ObserverNucleusVeto + ObserverDetectAll";
+      26           0 : }
+      27             : 
+      28           0 : PhotonOutput1D::PhotonOutput1D(const std::string &filename) : outfile(
+      29           0 :         filename.c_str(), std::ios::binary), out(&outfile), filename(filename) {
+      30           0 :         KISS_LOG_WARNING << "PhotonOutput1D is deprecated and will be removed in the future. Replace with TextOutput or HDF5Output with features ObserverNucleusVeto + ObserverDetectAll";
+      31           0 :         if (kiss::ends_with(filename, ".gz"))
+      32           0 :                 gzip();
+      33             : 
+      34           0 :         *out << "#ID\tE\tD\tpID\tpE\tiID\tiE\tiD\n";
+      35           0 :         *out << "#\n";
+      36           0 :         *out << "# ID          Id of particle (photon, electron, positron)\n";
+      37           0 :         *out << "# E           Energy [EeV]\n";
+      38           0 :         *out << "# D           Comoving distance to origin [Mpc]\n";
+      39           0 :         *out << "# pID         Id of parent particle\n";
+      40           0 :         *out << "# pE          Energy [EeV] of parent particle\n";
+      41           0 :         *out << "# iID         Id of source particle\n";
+      42           0 :         *out << "# iE          Energy [EeV] of source particle\n";
+      43           0 :         *out << "# iD          Comoving distance [Mpc] to source\n";
+      44           0 :         *out << "#\n";
+      45           0 : }
+      46             : 
+      47           0 : void PhotonOutput1D::process(Candidate *candidate) const {
+      48           0 :         int pid = candidate->current.getId();
+      49           0 :         if ((pid != 22) and (abs(pid) != 11))
+      50           0 :                 return;
+      51             : 
+      52             :         char buffer[1024];
+      53             :         size_t p = 0;
+      54             : 
+      55           0 :         p += std::sprintf(buffer + p, "%4i\t", pid);
+      56           0 :         p += std::sprintf(buffer + p, "%g\t", candidate->current.getEnergy() / EeV);
+      57           0 :         p += std::sprintf(buffer + p, "%8.4f\t", candidate->current.getPosition().getR() / Mpc);
+      58             : 
+      59           0 :         p += std::sprintf(buffer + p, "%10i\t", candidate->created.getId());
+      60           0 :         p += std::sprintf(buffer + p, "%8.4f\t", candidate->created.getEnergy() / EeV);
+      61             : 
+      62           0 :         p += std::sprintf(buffer + p, "%10i\t", candidate->source.getId());
+      63           0 :         p += std::sprintf(buffer + p, "%8.4f\t", candidate->source.getEnergy() / EeV);
+      64           0 :         p += std::sprintf(buffer + p, "%8.4f\n", candidate->source.getPosition().getR() / Mpc);
+      65             : 
+      66           0 : #pragma omp critical
+      67             :         {
+      68           0 :                 out->write(buffer, p);
+      69             :         }
+      70             : 
+      71           0 :         candidate->setActive(false);
+      72             : }
+      73             : 
+      74           0 : void PhotonOutput1D::close() {
+      75             :         #ifdef CRPROPA_HAVE_ZLIB
+      76           0 :                 zstream::ogzstream *zs = dynamic_cast<zstream::ogzstream *>(out);
+      77           0 :                 if (zs) {
+      78           0 :                         zs->close();
+      79           0 :                         delete out;
+      80           0 :                         out = 0;
+      81             :                 }
+      82             :         #endif
+      83           0 :         outfile.flush();
+      84           0 : }
+      85             : 
+      86           0 : string PhotonOutput1D::getDescription() const {
+      87           0 :         std::stringstream s;
+      88             :         s << "PhotonOutput1D: Output file = " << filename;
+      89           0 :         return s.str();
+      90           0 : }
+      91             : 
+      92           0 : PhotonOutput1D::~PhotonOutput1D() {
+      93           0 :         close();
+      94           0 : }
+      95             : 
+      96           0 : void PhotonOutput1D::gzip() {
+      97             :         #ifdef CRPROPA_HAVE_ZLIB
+      98           0 :                 out = new zstream::ogzstream(*out);
+      99             :         #else
+     100             :                 throw std::runtime_error("CRPropa was build without Zlib compression!");
+     101             :         #endif
+     102           0 : }
+     103             : 
+     104             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html b/doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html new file mode 100644 index 000000000..ba52b0e12 --- /dev/null +++ b/doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PropagationBP.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PropagationBP.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9210488.5 %
Date:2024-04-08 14:58:22Functions:151693.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13PropagationBP14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationBP12getToleranceEv2
_ZNK7crpropa13PropagationBP14getMinimumStepEv2
_ZNK7crpropa13PropagationBP8getFieldEv2
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEddd5
_ZNK7crpropa13PropagationBP14getMaximumStepEv5
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEd10
_ZN7crpropa13PropagationBP8setFieldENS_7ref_ptrINS_13MagneticFieldEEE16
_ZN7crpropa13PropagationBP12setToleranceEd22
_ZN7crpropa13PropagationBP14setMaximumStepEd22
_ZN7crpropa13PropagationBP14setMinimumStepEd24
_ZNK7crpropa13PropagationBP15errorEstimationENS_7Vector3IdEES2_d28
_ZNK7crpropa13PropagationBP7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEddd28
_ZNK7crpropa13PropagationBP7processEPNS_9CandidateE37
_ZNK7crpropa13PropagationBP2dYENS_7Vector3IdEES2_dddd103
_ZNK7crpropa13PropagationBP18getFieldAtPositionENS_7Vector3IdEEd104
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PropagationBP.cpp.func.html b/doc/coverageReport/src/module/PropagationBP.cpp.func.html new file mode 100644 index 000000000..d14b61859 --- /dev/null +++ b/doc/coverageReport/src/module/PropagationBP.cpp.func.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PropagationBP.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PropagationBP.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9210488.5 %
Date:2024-04-08 14:58:22Functions:151693.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13PropagationBP12setToleranceEd22
_ZN7crpropa13PropagationBP14setMaximumStepEd22
_ZN7crpropa13PropagationBP14setMinimumStepEd24
_ZN7crpropa13PropagationBP8setFieldENS_7ref_ptrINS_13MagneticFieldEEE16
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEd10
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEddd5
_ZNK7crpropa13PropagationBP12getToleranceEv2
_ZNK7crpropa13PropagationBP14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationBP14getMaximumStepEv5
_ZNK7crpropa13PropagationBP14getMinimumStepEv2
_ZNK7crpropa13PropagationBP15errorEstimationENS_7Vector3IdEES2_d28
_ZNK7crpropa13PropagationBP18getFieldAtPositionENS_7Vector3IdEEd104
_ZNK7crpropa13PropagationBP2dYENS_7Vector3IdEES2_dddd103
_ZNK7crpropa13PropagationBP7processEPNS_9CandidateE37
_ZNK7crpropa13PropagationBP7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEddd28
_ZNK7crpropa13PropagationBP8getFieldEv2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PropagationBP.cpp.gcov.html b/doc/coverageReport/src/module/PropagationBP.cpp.gcov.html new file mode 100644 index 000000000..8e1869baf --- /dev/null +++ b/doc/coverageReport/src/module/PropagationBP.cpp.gcov.html @@ -0,0 +1,285 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PropagationBP.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PropagationBP.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9210488.5 %
Date:2024-04-08 14:58:22Functions:151693.8 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/PropagationBP.h"
+       2             : 
+       3             : #include <sstream>
+       4             : #include <stdexcept>
+       5             : #include <vector>
+       6             : 
+       7             : namespace crpropa {
+       8          28 :         void PropagationBP::tryStep(const Y &y, Y &out, Y &error, double h,
+       9             :                         ParticleState &particle, double z, double q, double m) const {
+      10          28 :                 out = dY(y.x, y.u, h, z, q, m);  // 1 step with h
+      11             : 
+      12          28 :                 Y outHelp = dY(y.x, y.u, h/2, z, q, m);  // 2 steps with h/2
+      13          28 :                 Y outCompare = dY(outHelp.x, outHelp.u, h/2, z, q, m);
+      14             : 
+      15          28 :                 error = errorEstimation(out.x , outCompare.x , h);
+      16          28 :         }
+      17             : 
+      18             : 
+      19         103 :         PropagationBP::Y PropagationBP::dY(Vector3d pos, Vector3d dir, double step,
+      20             :                         double z, double q, double m) const {
+      21             :                 // half leap frog step in the position
+      22             :                 pos += dir * step / 2.;
+      23             : 
+      24             :                 // get B field at particle position
+      25         103 :                 Vector3d B = getFieldAtPosition(pos, z);
+      26             : 
+      27             :                 // Boris help vectors
+      28             :                 Vector3d t = B * q / 2 / m * step / c_light;
+      29         103 :                 Vector3d s = t * 2 / (1 + t.dot(t));
+      30             :                 Vector3d v_help;
+      31             : 
+      32             :                 // Boris push
+      33             :                 v_help = dir + dir.cross(t);
+      34             :                 dir = dir + v_help.cross(s);
+      35             : 
+      36             :                 // the other half leap frog step in the position
+      37             :                 pos += dir * step / 2.;
+      38         103 :                 return Y(pos, dir);
+      39             :         }
+      40             : 
+      41             : 
+      42             :         // with a fixed step size
+      43          10 :         PropagationBP::PropagationBP(ref_ptr<MagneticField> field, double fixedStep) :
+      44          10 :                         minStep(0) {
+      45          10 :                 setField(field);
+      46          10 :                 setTolerance(0.42);
+      47          10 :                 setMaximumStep(fixedStep);
+      48          10 :                 setMinimumStep(fixedStep);
+      49          10 :         }
+      50             : 
+      51             : 
+      52             :         // with adaptive step size
+      53           5 :         PropagationBP::PropagationBP(ref_ptr<MagneticField> field, double tolerance, double minStep, double maxStep) :
+      54           5 :                         minStep(0) {
+      55           7 :                 setField(field);
+      56           5 :                 setTolerance(tolerance);
+      57           4 :                 setMaximumStep(maxStep);
+      58           4 :                 setMinimumStep(minStep);
+      59           3 :         }
+      60             : 
+      61             : 
+      62          37 :         void PropagationBP::process(Candidate *candidate) const {
+      63             :                 // save the new previous particle state
+      64          37 :                 ParticleState &current = candidate->current;
+      65             :                 candidate->previous = current;
+      66             : 
+      67          37 :                 Y yIn(current.getPosition(), current.getDirection());
+      68             : 
+      69             :                 // calculate charge of particle
+      70          37 :                 double q = current.getCharge();
+      71          37 :                 double step = maxStep;
+      72             : 
+      73             :                 // rectilinear propagation for neutral particles
+      74          37 :                 if (q == 0) {
+      75           2 :                         step = clip(candidate->getNextStep(), minStep, maxStep);
+      76           1 :                         current.setPosition(yIn.x + yIn.u * step);
+      77           1 :                         candidate->setCurrentStep(step);
+      78           1 :                         candidate->setNextStep(maxStep);
+      79             :                         return;
+      80             :                 }
+      81             : 
+      82             :                 Y yOut, yErr;
+      83          36 :                 double newStep = step;
+      84          36 :                 double z = candidate->getRedshift();
+      85          36 :                 double m = current.getEnergy()/(c_light * c_light);
+      86             : 
+      87             :                 // if minStep is the same as maxStep the adaptive algorithm with its error
+      88             :                 // estimation is not needed and the computation time can be saved:
+      89          36 :                 if (minStep == maxStep){
+      90          19 :                         yOut = dY(yIn.x, yIn.u, step, z, q, m);
+      91             :                 } else {
+      92          17 :                         step = clip(candidate->getNextStep(), minStep, maxStep);
+      93          17 :                         newStep = step;
+      94             :                         double r = 42;  // arbitrary value
+      95             : 
+      96             :                         // try performing step until the target error (tolerance) or the minimum/maximum step size has been reached
+      97             :                         while (true) {
+      98          28 :                                 tryStep(yIn, yOut, yErr, step, current, z, q, m);
+      99          28 :                                 r = yErr.u.getR() / tolerance;  // ratio of absolute direction error and tolerance
+     100          28 :                                 if (r > 1) {  // large direction error relative to tolerance, try to decrease step size
+     101          18 :                                         if (step == minStep)  // already minimum step size
+     102             :                                                 break;
+     103             :                                         else {
+     104          11 :                                                 newStep = step * 0.95 * pow(r, -0.2);
+     105          19 :                                                 newStep = std::max(newStep, 0.1 * step); // limit step size decrease
+     106          11 :                                                 newStep = std::max(newStep, minStep); // limit step size to minStep
+     107             :                                                 step = newStep;
+     108             :                                         }
+     109             :                                 } else {  // small direction error relative to tolerance, try to increase step size
+     110          10 :                                         if (step != maxStep) {  // only update once if maximum step size yet not reached
+     111          10 :                                                 newStep = step * 0.95 * pow(r, -0.2);
+     112          17 :                                                 newStep = std::min(newStep, 5 * step); // limit step size increase
+     113          10 :                                                 newStep = std::min(newStep, maxStep); // limit step size to maxStep
+     114             :                                         }
+     115             :                                         break;
+     116             :                                 }
+     117             :                         }
+     118             :                 }
+     119             : 
+     120          36 :                 current.setPosition(yOut.x);
+     121          36 :                 current.setDirection(yOut.u.getUnitVector());
+     122          36 :                 candidate->setCurrentStep(step);
+     123          36 :                 candidate->setNextStep(newStep);
+     124             :         }
+     125             : 
+     126             : 
+     127          16 :         void PropagationBP::setField(ref_ptr<MagneticField> f) {
+     128          16 :                 field = f;
+     129          16 :         }
+     130             : 
+     131             : 
+     132           2 :         ref_ptr<MagneticField> PropagationBP::getField() const {
+     133           2 :                 return field;
+     134             :         }
+     135             : 
+     136             : 
+     137         104 :         Vector3d PropagationBP::getFieldAtPosition(Vector3d pos, double z) const {
+     138             :                 Vector3d B(0, 0, 0);
+     139             :                 try {
+     140             :                         // check if field is valid and use the field vector at the
+     141             :                         // position pos with the redshift z
+     142         104 :                         if (field.valid())
+     143         104 :                                 B = field->getField(pos, z);
+     144           0 :                 } catch (std::exception &e) {
+     145           0 :                         KISS_LOG_ERROR  << "PropagationBP: Exception in PropagationBP::getFieldAtPosition.\n"
+     146           0 :                                         << e.what();
+     147           0 :                 }       
+     148         104 :                 return B;
+     149             :         }
+     150             : 
+     151             : 
+     152          28 :         double PropagationBP::errorEstimation(const Vector3d x1, const Vector3d x2, double step) const {
+     153             :                 // compare the position after one step with the position after two steps with step/2.
+     154             :                 Vector3d diff = (x1 - x2);
+     155             : 
+     156          28 :                 double S = diff.getR() / (step * (1 - 1/4.) );  // 1/4 = (1/2)²  number of steps for x1 divided by number of steps for x2 to the power of p (order)
+     157             : 
+     158          28 :                 return S;
+     159             :         }
+     160             : 
+     161             : 
+     162          22 :         void PropagationBP::setTolerance(double tol) {
+     163          22 :                 if ((tol > 1) or (tol < 0))
+     164           2 :                         throw std::runtime_error(
+     165           4 :                                         "PropagationBP: target error not in range 0-1");
+     166          20 :                 tolerance = tol;
+     167          20 :         }
+     168             : 
+     169             : 
+     170          24 :         void PropagationBP::setMinimumStep(double min) {
+     171          24 :                 if (min < 0)
+     172           1 :                         throw std::runtime_error("PropagationBP: minStep < 0 ");
+     173          23 :                 if (min > maxStep)
+     174           2 :                         throw std::runtime_error("PropagationBP: minStep > maxStep");
+     175          21 :                 minStep = min;
+     176          21 :         }
+     177             : 
+     178             : 
+     179          22 :         void PropagationBP::setMaximumStep(double max) {
+     180          22 :                 if (max < minStep)
+     181           1 :                         throw std::runtime_error("PropagationBP: maxStep < minStep");
+     182          21 :                 maxStep = max;
+     183          21 :         }
+     184             : 
+     185             : 
+     186           2 :         double PropagationBP::getTolerance() const {
+     187           2 :                 return tolerance;
+     188             :         }
+     189             : 
+     190             : 
+     191           2 :         double PropagationBP::getMinimumStep() const {
+     192           2 :                 return minStep;
+     193             :         }
+     194             : 
+     195             : 
+     196           5 :         double PropagationBP::getMaximumStep() const {
+     197           5 :                 return maxStep;
+     198             :         }
+     199             : 
+     200             : 
+     201           0 :         std::string PropagationBP::getDescription() const {
+     202           0 :                 std::stringstream s;
+     203           0 :                 s << "Propagation in magnetic fields using the adaptive Boris push method.";
+     204           0 :                 s << " Target error: " << tolerance;
+     205           0 :                 s << ", Minimum Step: " << minStep / kpc << " kpc";
+     206           0 :                 s << ", Maximum Step: " << maxStep / kpc << " kpc";
+     207           0 :                 return s.str();
+     208           0 :         }
+     209             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html b/doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html new file mode 100644 index 000000000..01527a79b --- /dev/null +++ b/doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PropagationCK.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PropagationCK.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859787.6 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13PropagationCK14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationCK12getToleranceEv2
_ZNK7crpropa13PropagationCK14getMinimumStepEv2
_ZNK7crpropa13PropagationCK8getFieldEv2
_ZNK7crpropa13PropagationCK14getMaximumStepEv3
_ZN7crpropa13PropagationCKC2ENS_7ref_ptrINS_13MagneticFieldEEEddd13
_ZN7crpropa13PropagationCK8setFieldENS_7ref_ptrINS_13MagneticFieldEEE14
_ZN7crpropa13PropagationCK12setToleranceEd18
_ZN7crpropa13PropagationCK14setMaximumStepEd19
_ZN7crpropa13PropagationCK14setMinimumStepEd22
_ZNK7crpropa13PropagationCK7processEPNS_9CandidateE34
_ZNK7crpropa13PropagationCK7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEd42
_ZNK7crpropa13PropagationCK4dYdtERKNS0_1YERNS_13ParticleStateEd252
_ZNK7crpropa13PropagationCK18getFieldAtPositionENS_7Vector3IdEEd253
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PropagationCK.cpp.func.html b/doc/coverageReport/src/module/PropagationCK.cpp.func.html new file mode 100644 index 000000000..6461ce48c --- /dev/null +++ b/doc/coverageReport/src/module/PropagationCK.cpp.func.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PropagationCK.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PropagationCK.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859787.6 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13PropagationCK12setToleranceEd18
_ZN7crpropa13PropagationCK14setMaximumStepEd19
_ZN7crpropa13PropagationCK14setMinimumStepEd22
_ZN7crpropa13PropagationCK8setFieldENS_7ref_ptrINS_13MagneticFieldEEE14
_ZN7crpropa13PropagationCKC2ENS_7ref_ptrINS_13MagneticFieldEEEddd13
_ZNK7crpropa13PropagationCK12getToleranceEv2
_ZNK7crpropa13PropagationCK14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationCK14getMaximumStepEv3
_ZNK7crpropa13PropagationCK14getMinimumStepEv2
_ZNK7crpropa13PropagationCK18getFieldAtPositionENS_7Vector3IdEEd253
_ZNK7crpropa13PropagationCK4dYdtERKNS0_1YERNS_13ParticleStateEd252
_ZNK7crpropa13PropagationCK7processEPNS_9CandidateE34
_ZNK7crpropa13PropagationCK7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEd42
_ZNK7crpropa13PropagationCK8getFieldEv2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/PropagationCK.cpp.gcov.html b/doc/coverageReport/src/module/PropagationCK.cpp.gcov.html new file mode 100644 index 000000000..037e88d09 --- /dev/null +++ b/doc/coverageReport/src/module/PropagationCK.cpp.gcov.html @@ -0,0 +1,278 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/PropagationCK.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - PropagationCK.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859787.6 %
Date:2024-04-08 14:58:22Functions:131492.9 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/PropagationCK.h"
+       2             : 
+       3             : #include <limits>
+       4             : #include <sstream>
+       5             : #include <stdexcept>
+       6             : #include <vector>
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10             : // Cash-Karp coefficients
+      11             : const double cash_karp_a[] = {
+      12             :         0., 0., 0., 0., 0., 0.,
+      13             :         1. / 5., 0., 0., 0., 0., 0.,
+      14             :         3. / 40., 9. / 40., 0., 0., 0., 0.,
+      15             :         3. / 10., -9. / 10., 6. / 5., 0., 0., 0.,
+      16             :         -11. / 54., 5. / 2., -70. / 27., 35. / 27., 0., 0.,
+      17             :         1631. / 55296., 175. / 512., 575. / 13824., 44275. / 110592., 253. / 4096., 0.
+      18             : };
+      19             : 
+      20             : const double cash_karp_b[] = {
+      21             :         37. / 378., 0, 250. / 621., 125. / 594., 0., 512. / 1771.
+      22             : };
+      23             : 
+      24             : const double cash_karp_bs[] = {
+      25             :         2825. / 27648., 0., 18575. / 48384., 13525. / 55296., 277. / 14336., 1. / 4.
+      26             : };
+      27             : 
+      28          42 : void PropagationCK::tryStep(const Y &y, Y &out, Y &error, double h,
+      29             :                 ParticleState &particle, double z) const {
+      30             :         std::vector<Y> k;
+      31          42 :         k.reserve(6);
+      32             : 
+      33             :         out = y;
+      34             :         error = Y(0);
+      35             : 
+      36             :         // calculate the sum of b_i * k_i
+      37         294 :         for (size_t i = 0; i < 6; i++) {
+      38             : 
+      39             :                 Y y_n = y;
+      40         882 :                 for (size_t j = 0; j < i; j++)
+      41         630 :                         y_n += k[j] * a[i * 6 + j] * h;
+      42             : 
+      43             :                 // update k_i
+      44         252 :                 k[i] = dYdt(y_n, particle, z);
+      45             : 
+      46         252 :                 out += k[i] * b[i] * h;
+      47         252 :                 error += k[i] * (b[i] - bs[i]) * h;
+      48             :         }
+      49          42 : }
+      50             : 
+      51         252 : PropagationCK::Y PropagationCK::dYdt(const Y &y, ParticleState &p, double z) const {
+      52             :         // normalize direction vector to prevent numerical losses
+      53         252 :         Vector3d velocity = y.u.getUnitVector() * c_light;
+      54             :         
+      55             :         // get B field at particle position
+      56         252 :         Vector3d B = getFieldAtPosition(y.x, z);
+      57             : 
+      58             :         // Lorentz force: du/dt = q*c/E * (v x B)
+      59         252 :         Vector3d dudt = p.getCharge() * c_light / p.getEnergy() * velocity.cross(B);
+      60         252 :         return Y(velocity, dudt);
+      61             : }
+      62             : 
+      63          13 : PropagationCK::PropagationCK(ref_ptr<MagneticField> field, double tolerance,
+      64          13 :                 double minStep, double maxStep) :
+      65          13 :                 minStep(0) {
+      66          15 :         setField(field);
+      67          13 :         setTolerance(tolerance);
+      68          12 :         setMaximumStep(maxStep);
+      69          12 :         setMinimumStep(minStep);
+      70             : 
+      71             :         // load Cash-Karp coefficients
+      72             :         a.assign(cash_karp_a, cash_karp_a + 36);
+      73             :         b.assign(cash_karp_b, cash_karp_b + 6);
+      74             :         bs.assign(cash_karp_bs, cash_karp_bs + 6);
+      75          11 : }
+      76             : 
+      77          34 : void PropagationCK::process(Candidate *candidate) const {
+      78             :         // save the new previous particle state
+      79          34 :         ParticleState &current = candidate->current;
+      80             :         candidate->previous = current;
+      81             : 
+      82          34 :         Y yIn(current.getPosition(), current.getDirection());
+      83          34 :         double step = maxStep;
+      84             : 
+      85             :         // rectilinear propagation for neutral particles
+      86          34 :         if (current.getCharge() == 0) {
+      87           2 :                 step = clip(candidate->getNextStep(), minStep, maxStep);
+      88           1 :                 current.setPosition(yIn.x + yIn.u * step);
+      89           1 :                 candidate->setCurrentStep(step);
+      90           1 :                 candidate->setNextStep(maxStep);
+      91             :                 return;
+      92             :         }
+      93             : 
+      94             :         Y yOut, yErr;
+      95          33 :         double newStep = step;
+      96          33 :         double z = candidate->getRedshift();
+      97             : 
+      98             : 
+      99             :         // if minStep is the same as maxStep the adaptive algorithm with its error
+     100             :         // estimation is not needed and the computation time can be saved:
+     101          33 :         if (minStep == maxStep){
+     102          10 :                 tryStep(yIn, yOut, yErr, step / c_light, current, z);
+     103             :         } else {
+     104          23 :                 step = clip(candidate->getNextStep(), minStep, maxStep);
+     105          23 :                 newStep = step;
+     106             :                 double r = 42;  // arbitrary value
+     107             : 
+     108             :                 // try performing step until the target error (tolerance) or the minimum/maximum step size has been reached
+     109             :                 while (true) {
+     110          32 :                         tryStep(yIn, yOut, yErr, step / c_light, current, z);
+     111          32 :                         r = yErr.u.getR() / tolerance;  // ratio of absolute direction error and tolerance
+     112          32 :                         if (r > 1) {  // large direction error relative to tolerance, try to decrease step size
+     113          10 :                                 if (step == minStep)  // already minimum step size
+     114             :                                         break;
+     115             :                                 else {
+     116           9 :                                         newStep = step * 0.95 * pow(r, -0.2);
+     117          17 :                                         newStep = std::max(newStep, 0.1 * step); // limit step size decrease
+     118           9 :                                         newStep = std::max(newStep, minStep); // limit step size to minStep
+     119             :                                         step = newStep;
+     120             :                                 }
+     121             :                         } else {  // small direction error relative to tolerance, try to increase step size
+     122          22 :                                 if (step != maxStep) {  // only update once if maximum step size yet not reached
+     123          22 :                                         newStep = step * 0.95 * pow(r, -0.2);
+     124          35 :                                         newStep = std::min(newStep, 5 * step); // limit step size increase
+     125          22 :                                         newStep = std::min(newStep, maxStep); // limit step size to maxStep
+     126             :                                 }
+     127             :                                 break;
+     128             :                         }
+     129             :                 }
+     130             :         }
+     131             : 
+     132          33 :         current.setPosition(yOut.x);
+     133          33 :         current.setDirection(yOut.u.getUnitVector());
+     134          33 :         candidate->setCurrentStep(step);
+     135          33 :         candidate->setNextStep(newStep);
+     136             : }
+     137             : 
+     138          14 : void PropagationCK::setField(ref_ptr<MagneticField> f) {
+     139          14 :         field = f;
+     140          14 : }
+     141             : 
+     142           2 : ref_ptr<MagneticField> PropagationCK::getField() const {
+     143           2 :         return field;
+     144             : }
+     145             : 
+     146         253 : Vector3d PropagationCK::getFieldAtPosition(Vector3d pos, double z) const {
+     147             :         Vector3d B(0, 0, 0);
+     148             :         try {
+     149             :                 // check if field is valid and use the field vector at the
+     150             :                 // position pos with the redshift z
+     151         253 :                 if (field.valid())
+     152         253 :                         B = field->getField(pos, z);
+     153           0 :         } catch (std::exception &e) {
+     154           0 :                 KISS_LOG_ERROR  << "PropagationCK: Exception in PropagationCK::getFieldAtPosition.\n"
+     155           0 :                                 << e.what();
+     156           0 :         }       
+     157         253 :         return B;
+     158             : }
+     159             : 
+     160          18 : void PropagationCK::setTolerance(double tol) {
+     161          18 :         if ((tol > 1) or (tol < 0))
+     162           2 :                 throw std::runtime_error(
+     163           4 :                                 "PropagationCK: target error not in range 0-1");
+     164          16 :         tolerance = tol;
+     165          16 : }
+     166             : 
+     167          22 : void PropagationCK::setMinimumStep(double min) {
+     168          22 :         if (min < 0)
+     169           1 :                 throw std::runtime_error("PropagationCK: minStep < 0 ");
+     170          21 :         if (min > maxStep)
+     171           2 :                 throw std::runtime_error("PropagationCK: minStep > maxStep");
+     172          19 :         minStep = min;
+     173          19 : }
+     174             : 
+     175          19 : void PropagationCK::setMaximumStep(double max) {
+     176          19 :         if (max < minStep)
+     177           1 :                 throw std::runtime_error("PropagationCK: maxStep < minStep");
+     178          18 :         maxStep = max;
+     179          18 : }
+     180             : 
+     181           2 : double PropagationCK::getTolerance() const {
+     182           2 :         return tolerance;
+     183             : }
+     184             : 
+     185           2 : double PropagationCK::getMinimumStep() const {
+     186           2 :         return minStep;
+     187             : }
+     188             : 
+     189           3 : double PropagationCK::getMaximumStep() const {
+     190           3 :         return maxStep;
+     191             : }
+     192             : 
+     193           0 : std::string PropagationCK::getDescription() const {
+     194           0 :         std::stringstream s;
+     195           0 :         s << "Propagation in magnetic fields using the Cash-Karp method.";
+     196           0 :         s << " Target error: " << tolerance;
+     197           0 :         s << ", Minimum Step: " << minStep / kpc << " kpc";
+     198           0 :         s << ", Maximum Step: " << maxStep / kpc << " kpc";
+     199           0 :         return s.str();
+     200           0 : }
+     201             : 
+     202             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html b/doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html new file mode 100644 index 000000000..8258b1e94 --- /dev/null +++ b/doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Redshift.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Redshift.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:92832.1 %
Date:2024-04-08 14:58:22Functions:1425.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa14FutureRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa14FutureRedshift7processEPNS_9CandidateE0
_ZNK7crpropa8Redshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Redshift7processEPNS_9CandidateE7644
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Redshift.cpp.func.html b/doc/coverageReport/src/module/Redshift.cpp.func.html new file mode 100644 index 000000000..39944b158 --- /dev/null +++ b/doc/coverageReport/src/module/Redshift.cpp.func.html @@ -0,0 +1,88 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Redshift.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Redshift.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:92832.1 %
Date:2024-04-08 14:58:22Functions:1425.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa14FutureRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa14FutureRedshift7processEPNS_9CandidateE0
_ZNK7crpropa8Redshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Redshift7processEPNS_9CandidateE7644
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Redshift.cpp.gcov.html b/doc/coverageReport/src/module/Redshift.cpp.gcov.html new file mode 100644 index 000000000..f41db2d01 --- /dev/null +++ b/doc/coverageReport/src/module/Redshift.cpp.gcov.html @@ -0,0 +1,138 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Redshift.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Redshift.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:92832.1 %
Date:2024-04-08 14:58:22Functions:1425.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/Redshift.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Cosmology.h"
+       4             : 
+       5             : #include <limits>
+       6             : 
+       7             : namespace crpropa {
+       8             : 
+       9        7644 : void Redshift::process(Candidate *c) const {
+      10        7644 :         double z = c->getRedshift();
+      11             : 
+      12             :         // check if z = 0
+      13        7644 :         if (z <= std::numeric_limits<double>::min())
+      14          21 :                 return;
+      15             : 
+      16             :         // use small step approximation:  dz = H(z) / c * ds
+      17        7623 :         double dz = hubbleRate(z) / c_light * c->getCurrentStep();
+      18             : 
+      19             :         // prevent dz > z
+      20        7623 :         dz = std::min(dz, z);
+      21             : 
+      22             :         // update redshift
+      23        7623 :         c->setRedshift(z - dz);
+      24             : 
+      25             :         // adiabatic energy loss: dE / dz = E / (1 + z)
+      26        7623 :         double E = c->current.getEnergy();
+      27        7623 :         c->current.setEnergy(E * (1 - dz / (1 + z)));
+      28             : }
+      29             : 
+      30           0 : std::string Redshift::getDescription() const {
+      31           0 :         std::stringstream s;
+      32           0 :         s << "Redshift: h0 = " << hubbleRate() / 1e5 * Mpc << ", omegaL = "
+      33           0 :                         << omegaL() << ", omegaM = " << omegaM();
+      34           0 :         return s.str();
+      35           0 : }
+      36             : 
+      37           0 : void FutureRedshift::process(Candidate *c) const {
+      38           0 :         double z = c->getRedshift();
+      39             : 
+      40             :         // check if z = -1
+      41           0 :         if (z <= -1)
+      42             :                 return;
+      43             : 
+      44             :         // use small step approximation:  dz = H(z) / c * ds
+      45           0 :         double dz = hubbleRate(z) / c_light * c->getCurrentStep();
+      46             : 
+      47             :         // update redshift
+      48           0 :         c->setRedshift(z - dz);
+      49             : 
+      50             :         // adiabatic energy loss: dE / dz = E / (1 + z)
+      51           0 :         double E = c->current.getEnergy();
+      52           0 :         c->current.setEnergy(E * (1 - dz / (1 + z)));
+      53             : }
+      54             : 
+      55           0 : std::string FutureRedshift::getDescription() const {
+      56           0 :         std::stringstream s;
+      57           0 :         s << "FutureRedshift: h0 = " << hubbleRate() / 1e5 * Mpc << ", omegaL = "
+      58           0 :                         << omegaL() << ", omegaM = " << omegaM();
+      59           0 :         return s.str();
+      60           0 : }
+      61             : 
+      62             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html b/doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html new file mode 100644 index 000000000..89ada30d6 --- /dev/null +++ b/doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/RestrictToRegion.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - RestrictToRegion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:61250.0 %
Date:2024-04-08 14:58:22Functions:2366.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa16RestrictToRegion14getDescriptionB5cxx11Ev0
_ZN7crpropa16RestrictToRegionC2EPNS_6ModuleEPNS_7SurfaceE1
_ZNK7crpropa16RestrictToRegion7processEPNS_9CandidateE2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/RestrictToRegion.cpp.func.html b/doc/coverageReport/src/module/RestrictToRegion.cpp.func.html new file mode 100644 index 000000000..6024c3ad3 --- /dev/null +++ b/doc/coverageReport/src/module/RestrictToRegion.cpp.func.html @@ -0,0 +1,84 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/RestrictToRegion.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - RestrictToRegion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:61250.0 %
Date:2024-04-08 14:58:22Functions:2366.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16RestrictToRegionC2EPNS_6ModuleEPNS_7SurfaceE1
_ZNK7crpropa16RestrictToRegion14getDescriptionB5cxx11Ev0
_ZNK7crpropa16RestrictToRegion7processEPNS_9CandidateE2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html b/doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html new file mode 100644 index 000000000..38282b565 --- /dev/null +++ b/doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html @@ -0,0 +1,101 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/RestrictToRegion.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - RestrictToRegion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:61250.0 %
Date:2024-04-08 14:58:22Functions:2366.7 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/RestrictToRegion.h" 
+       2             : 
+       3             : #include <sstream>
+       4             : 
+       5             : namespace crpropa {
+       6             : 
+       7           1 : RestrictToRegion::RestrictToRegion(Module* _module, Surface* _surface) : module(_module), surface(_surface) { 
+       8           1 : };
+       9             : 
+      10           2 : void RestrictToRegion::process(Candidate *candidate) const {
+      11           2 :         if (surface->distance(candidate->current.getPosition()) <= 0) {
+      12           1 :                 module->process(candidate);
+      13             :         }
+      14           2 : };
+      15             : 
+      16           0 : std::string RestrictToRegion::getDescription() const {
+      17           0 :         std::stringstream s;
+      18             :         s << "RestrictToArea:\n"
+      19           0 :                 << "  Module: " << module->getDescription() << std::endl
+      20           0 :                 << "  Region: " << surface->getDescription() << std::endl;
+      21           0 :         return s.str();
+      22           0 : };
+      23             : 
+      24             : 
+      25             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html b/doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html new file mode 100644 index 000000000..1d24c0fb2 --- /dev/null +++ b/doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/SimplePropagation.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - SimplePropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:123336.4 %
Date:2024-04-08 14:58:22Functions:2728.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17SimplePropagation14setMaximumStepEd0
_ZN7crpropa17SimplePropagation14setMinimumStepEd0
_ZNK7crpropa17SimplePropagation14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SimplePropagation14getMaximumStepEv0
_ZNK7crpropa17SimplePropagation14getMinimumStepEv0
_ZN7crpropa17SimplePropagationC2Edd12
_ZNK7crpropa17SimplePropagation7processEPNS_9CandidateE19294
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/SimplePropagation.cpp.func.html b/doc/coverageReport/src/module/SimplePropagation.cpp.func.html new file mode 100644 index 000000000..2f86027c0 --- /dev/null +++ b/doc/coverageReport/src/module/SimplePropagation.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/SimplePropagation.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - SimplePropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:123336.4 %
Date:2024-04-08 14:58:22Functions:2728.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17SimplePropagation14setMaximumStepEd0
_ZN7crpropa17SimplePropagation14setMinimumStepEd0
_ZN7crpropa17SimplePropagationC2Edd12
_ZNK7crpropa17SimplePropagation14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SimplePropagation14getMaximumStepEv0
_ZNK7crpropa17SimplePropagation14getMinimumStepEv0
_ZNK7crpropa17SimplePropagation7processEPNS_9CandidateE19294
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html b/doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html new file mode 100644 index 000000000..c01c7f1d1 --- /dev/null +++ b/doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/SimplePropagation.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - SimplePropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:123336.4 %
Date:2024-04-08 14:58:22Functions:2728.6 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/SimplePropagation.h"
+       2             : 
+       3             : #include <sstream>
+       4             : #include <stdexcept>
+       5             : 
+       6             : namespace crpropa {
+       7             : 
+       8          12 : SimplePropagation::SimplePropagation(double minStep, double maxStep) :
+       9          12 :                 minStep(minStep), maxStep(maxStep) {
+      10          12 :         if (minStep > maxStep)
+      11           0 :                 throw std::runtime_error("SimplePropagation: minStep > maxStep");
+      12          12 : }
+      13             : 
+      14       19294 : void SimplePropagation::process(Candidate *c) const {
+      15             :         c->previous = c->current;
+      16             : 
+      17       19294 :         double step = clip(c->getNextStep(), minStep, maxStep);
+      18       19294 :         c->setCurrentStep(step);
+      19       19294 :         Vector3d pos = c->current.getPosition();
+      20       19294 :         Vector3d dir = c->current.getDirection();
+      21       19294 :         c->current.setPosition(pos + dir * step);
+      22       19294 :         c->setNextStep(maxStep);
+      23       19294 : }
+      24             : 
+      25           0 : void SimplePropagation::setMinimumStep(double step) {
+      26           0 :         if (step > maxStep)
+      27           0 :                 throw std::runtime_error("SimplePropagation: minStep > maxStep");
+      28           0 :         minStep = step;
+      29           0 : }
+      30             : 
+      31           0 : void SimplePropagation::setMaximumStep(double step) {
+      32           0 :         if (minStep > step)
+      33           0 :                 throw std::runtime_error("SimplePropagation: minStep > maxStep");
+      34           0 :         maxStep = step;
+      35           0 : }
+      36             : 
+      37           0 : double SimplePropagation::getMinimumStep() const {
+      38           0 :         return minStep;
+      39             : }
+      40             : 
+      41           0 : double SimplePropagation::getMaximumStep() const {
+      42           0 :         return maxStep;
+      43             : }
+      44             : 
+      45           0 : std::string SimplePropagation::getDescription() const {
+      46           0 :         std::stringstream s;
+      47           0 :         s << "SimplePropagation: Step size = " << minStep / kpc
+      48           0 :                         << " - " << maxStep / kpc << " kpc";
+      49           0 :         return s.str();
+      50           0 : }
+      51             : 
+      52             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html new file mode 100644 index 000000000..d0dcbba06 --- /dev/null +++ b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html @@ -0,0 +1,156 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/SynchrotronRadiation.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - SynchrotronRadiation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8113161.8 %
Date:2024-04-08 14:58:22Functions:102147.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SynchrotronRadiation11getThinningEv0
_ZN7crpropa20SynchrotronRadiation11setThinningEd0
_ZN7crpropa20SynchrotronRadiation14getHavePhotonsEv0
_ZN7crpropa20SynchrotronRadiation17getMaximumSamplesEv0
_ZN7crpropa20SynchrotronRadiation7getBrmsEv0
_ZN7crpropa20SynchrotronRadiation8getFieldEv0
_ZN7crpropa20SynchrotronRadiation8getLimitEv0
_ZN7crpropa20SynchrotronRadiation8setFieldENS_7ref_ptrINS_13MagneticFieldEEE0
_ZN7crpropa20SynchrotronRadiationC2ENS_7ref_ptrINS_13MagneticFieldEEEbdid0
_ZNK7crpropa20SynchrotronRadiation14getDescriptionB5cxx11Ev0
_ZNK7crpropa20SynchrotronRadiation21getSecondaryThresholdEv0
_ZN7crpropa20SynchrotronRadiation12initSpectrumEv1
_ZN7crpropa20SynchrotronRadiation14setHavePhotonsEb1
_ZN7crpropa20SynchrotronRadiation17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa20SynchrotronRadiation17setMaximumSamplesEi1
_ZN7crpropa20SynchrotronRadiation21setSecondaryThresholdEd1
_ZN7crpropa20SynchrotronRadiation7setBrmsEd1
_ZN7crpropa20SynchrotronRadiation8setLimitEd1
_ZN7crpropa20SynchrotronRadiationC2Edbdid1
_ZNK7crpropa20SynchrotronRadiation7processEPNS_9CandidateE1
_ZNK7crpropa20SynchrotronRadiation17getInteractionTagB5cxx11Ev2
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html new file mode 100644 index 000000000..bc212b37e --- /dev/null +++ b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html @@ -0,0 +1,156 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/SynchrotronRadiation.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - SynchrotronRadiation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8113161.8 %
Date:2024-04-08 14:58:22Functions:102147.6 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SynchrotronRadiation11getThinningEv0
_ZN7crpropa20SynchrotronRadiation11setThinningEd0
_ZN7crpropa20SynchrotronRadiation12initSpectrumEv1
_ZN7crpropa20SynchrotronRadiation14getHavePhotonsEv0
_ZN7crpropa20SynchrotronRadiation14setHavePhotonsEb1
_ZN7crpropa20SynchrotronRadiation17getMaximumSamplesEv0
_ZN7crpropa20SynchrotronRadiation17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa20SynchrotronRadiation17setMaximumSamplesEi1
_ZN7crpropa20SynchrotronRadiation21setSecondaryThresholdEd1
_ZN7crpropa20SynchrotronRadiation7getBrmsEv0
_ZN7crpropa20SynchrotronRadiation7setBrmsEd1
_ZN7crpropa20SynchrotronRadiation8getFieldEv0
_ZN7crpropa20SynchrotronRadiation8getLimitEv0
_ZN7crpropa20SynchrotronRadiation8setFieldENS_7ref_ptrINS_13MagneticFieldEEE0
_ZN7crpropa20SynchrotronRadiation8setLimitEd1
_ZN7crpropa20SynchrotronRadiationC2ENS_7ref_ptrINS_13MagneticFieldEEEbdid0
_ZN7crpropa20SynchrotronRadiationC2Edbdid1
_ZNK7crpropa20SynchrotronRadiation14getDescriptionB5cxx11Ev0
_ZNK7crpropa20SynchrotronRadiation17getInteractionTagB5cxx11Ev2
_ZNK7crpropa20SynchrotronRadiation21getSecondaryThresholdEv0
_ZNK7crpropa20SynchrotronRadiation7processEPNS_9CandidateE1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html new file mode 100644 index 000000000..3ea130039 --- /dev/null +++ b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html @@ -0,0 +1,306 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/SynchrotronRadiation.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - SynchrotronRadiation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8113161.8 %
Date:2024-04-08 14:58:22Functions:102147.6 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/SynchrotronRadiation.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Random.h"
+       4             : 
+       5             : #include <fstream>
+       6             : #include <limits>
+       7             : #include <stdexcept>
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11           0 : SynchrotronRadiation::SynchrotronRadiation(ref_ptr<MagneticField> field, bool havePhotons, double thinning, int nSamples, double limit) {
+      12           0 :         setField(field);
+      13           0 :         setBrms(0);
+      14           0 :         initSpectrum();
+      15           0 :         setHavePhotons(havePhotons);
+      16           0 :         setLimit(limit);
+      17           0 :         setSecondaryThreshold(1e6 * eV);
+      18           0 :         setMaximumSamples(nSamples);
+      19           0 : }
+      20             : 
+      21           1 : SynchrotronRadiation::SynchrotronRadiation(double Brms, bool havePhotons, double thinning, int nSamples, double limit) {
+      22           1 :         setBrms(Brms);
+      23           1 :         initSpectrum();
+      24           1 :         setHavePhotons(havePhotons);
+      25           1 :         setLimit(limit);
+      26           1 :         setSecondaryThreshold(1e6 * eV);
+      27           1 :         setMaximumSamples(nSamples);
+      28           1 : }
+      29             : 
+      30           0 : void SynchrotronRadiation::setField(ref_ptr<MagneticField> f) {
+      31           0 :         this->field = f;
+      32           0 : }
+      33             : 
+      34           0 : ref_ptr<MagneticField> SynchrotronRadiation::getField() {
+      35           0 :         return field;
+      36             : }
+      37             : 
+      38           1 : void SynchrotronRadiation::setBrms(double Brms) {
+      39           1 :         this->Brms = Brms;
+      40           1 : }
+      41             : 
+      42           0 : double SynchrotronRadiation::getBrms() {
+      43           0 :         return Brms;
+      44             : }
+      45             : 
+      46           1 : void SynchrotronRadiation::setHavePhotons(bool havePhotons) {
+      47           1 :         this->havePhotons = havePhotons;
+      48           1 : }
+      49             : 
+      50           0 : bool SynchrotronRadiation::getHavePhotons() {
+      51           0 :         return havePhotons;
+      52             : }
+      53             : 
+      54           0 : void SynchrotronRadiation::setThinning(double thinning) {
+      55           0 :         this->thinning = thinning;
+      56           0 : }
+      57             : 
+      58           0 : double SynchrotronRadiation::getThinning() {
+      59           0 :         return thinning;
+      60             : }
+      61             : 
+      62           1 : void SynchrotronRadiation::setLimit(double limit) {
+      63           1 :         this->limit = limit;
+      64           1 : }
+      65             : 
+      66           0 : double SynchrotronRadiation::getLimit() {
+      67           0 :         return limit;
+      68             : }
+      69             : 
+      70           1 : void SynchrotronRadiation::setMaximumSamples(int nmax) {
+      71           1 :         maximumSamples = nmax;
+      72           1 : }
+      73             : 
+      74           0 : int SynchrotronRadiation::getMaximumSamples() {
+      75           0 :         return maximumSamples;
+      76             : }
+      77             : 
+      78           1 : void SynchrotronRadiation::setSecondaryThreshold(double threshold) {
+      79           1 :         secondaryThreshold = threshold;
+      80           1 : }
+      81             : 
+      82           0 : double SynchrotronRadiation::getSecondaryThreshold() const {
+      83           0 :         return secondaryThreshold;
+      84             : }
+      85             : 
+      86           1 : void SynchrotronRadiation::initSpectrum() {
+      87           2 :         std::string filename = getDataPath("Synchrotron/spectrum.txt");
+      88           1 :         std::ifstream infile(filename.c_str());
+      89             : 
+      90           1 :         if (!infile.good())
+      91           0 :                 throw std::runtime_error("SynchrotronRadiation: could not open file " + filename);
+      92             : 
+      93             :         // clear previously loaded interaction rates
+      94           1 :         tabx.clear();
+      95           1 :         tabCDF.clear();
+      96             : 
+      97        1407 :         while (infile.good()) {
+      98        1406 :                 if (infile.peek() != '#') {
+      99             :                         double a, b;
+     100             :                         infile >> a >> b;
+     101        1402 :                         if (infile) {
+     102        1401 :                                 tabx.push_back(pow(10, a));
+     103        1401 :                                 tabCDF.push_back(b);
+     104             :                         }
+     105             :                 }
+     106        1406 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
+     107             :         }
+     108           1 :         infile.close();
+     109           2 : }
+     110             : 
+     111           1 : void SynchrotronRadiation::process(Candidate *candidate) const {
+     112           1 :         double charge = fabs(candidate->current.getCharge());
+     113           1 :         if (charge == 0)
+     114           0 :                 return; // only charged particles
+     115             : 
+     116             :         // calculate gyroradius, evaluated at the current position
+     117           1 :         double z = candidate->getRedshift();
+     118             :         double B;
+     119           1 :         if (field.valid()) {
+     120           0 :                 Vector3d Bvec = field->getField(candidate->current.getPosition(), z);
+     121           0 :                 B = Bvec.cross(candidate->current.getDirection()).getR();
+     122             :         } else {
+     123           1 :                 B = sqrt(2. / 3) * Brms; // average perpendicular field component
+     124             :         }
+     125           1 :         B *= pow(1 + z, 2); // cosmological scaling
+     126           1 :         double Rg = candidate->current.getMomentum().getR() / charge / B;
+     127             : 
+     128             :         // calculate energy loss
+     129           1 :         double lf = candidate->current.getLorentzFactor();
+     130           1 :         double dEdx = 1. / 6 / M_PI / epsilon0 * pow(lf * lf - 1, 2) * pow(charge / Rg, 2); // Jackson p. 770 (14.31)
+     131           1 :         double step = candidate->getCurrentStep() / (1 + z); // step size in local frame
+     132           1 :         double dE = step * dEdx;
+     133             : 
+     134             :         // apply energy loss and limit next step
+     135           1 :         double E = candidate->current.getEnergy();
+     136           1 :         candidate->current.setEnergy(E - dE);
+     137           1 :         candidate->limitNextStep(limit * E / dEdx);
+     138             : 
+     139             :         // optionally add secondary photons
+     140           1 :         if (not(havePhotons))
+     141             :                 return;
+     142             : 
+     143             :         // check if photons with energies > 14 * Ecrit are possible
+     144           1 :         double Ecrit = 3. / 4 * h_planck / M_PI * c_light * pow(lf, 3) / Rg;
+     145           1 :         if (14 * Ecrit < secondaryThreshold)
+     146             :                 return;
+     147             : 
+     148             :         // draw photons up to the total energy loss
+     149             :         // if maximumSamples is reached before that, compensate the total energy afterwards
+     150           1 :         Random &random = Random::instance();
+     151             :         double dE0 = dE;
+     152             :         std::vector<double> energies;
+     153             :         int counter = 0;
+     154     3620603 :         while (dE > 0) {
+     155             :                 // draw random value between 0 and maximum of corresponding cdf
+     156             :                 // choose bin of s where cdf(x) = cdf_rand -> x_rand
+     157     3620602 :                 size_t i = random.randBin(tabCDF); // draw random bin (upper bin boundary returned)
+     158     3620602 :                 double binWidth = (tabx[i] - tabx[i-1]);
+     159     3620602 :                 double x = tabx[i-1] + random.rand() * binWidth; // draw random x uniformly distributed in bin
+     160     3620602 :                 double Ephoton = x * Ecrit;
+     161             : 
+     162             :                 // if the remaining energy is not sufficient check for random accepting
+     163     3620602 :                 if (Ephoton > dE) {
+     164           1 :                         if (random.rand() > (dE / Ephoton))
+     165             :                                 break; // not accepted
+     166             :                 }
+     167             : 
+     168             :                 // only activate the "per-step" sampling if maximumSamples is explicitly set.
+     169     3620602 :                 if (maximumSamples > 0) {
+     170           0 :                         if (counter >= maximumSamples) 
+     171             :                                 break;                  
+     172             :                 }
+     173             : 
+     174             :                 // store energies in array
+     175     3620602 :                 energies.push_back(Ephoton);
+     176             : 
+     177             :                 // energy loss
+     178     3620602 :                 dE -= Ephoton;
+     179             : 
+     180             :                 // counter for sampling break condition;
+     181     3620602 :                 counter++;
+     182             :         }
+     183             : 
+     184             :         // while loop before gave total energy which is just a fraction of the required
+     185             :         double w1 = 1;
+     186           1 :         if (maximumSamples > 0 && dE > 0)
+     187           0 :                 w1 = 1. / (1. - dE / dE0); 
+     188             : 
+     189             :         // loop over sampled photons and attribute weights accordingly
+     190     3620603 :         for (int i = 0; i < energies.size(); i++) {
+     191     3620602 :                 double Ephoton = energies[i];
+     192     3620602 :                 double f = Ephoton / (E - dE0);
+     193     3620602 :                 double w = w1 / pow(f, thinning);
+     194             : 
+     195             :                 // thinning procedure: accepts only a few random secondaries
+     196     3620602 :                 if (random.rand() < pow(f, thinning)) {
+     197     3620602 :                         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
+     198     3620602 :                         if (Ephoton > secondaryThreshold) // create only photons with energies above threshold
+     199     3309554 :                                 candidate->addSecondary(22, Ephoton, pos, w, interactionTag);
+     200             :                 }
+     201             :         }
+     202             : }
+     203             : 
+     204           0 : std::string SynchrotronRadiation::getDescription() const {
+     205           0 :         std::stringstream s;
+     206           0 :         s << "Synchrotron radiation";
+     207           0 :         if (field.valid())
+     208           0 :                 s << " for specified magnetic field";
+     209             :         else
+     210           0 :                 s << " for Brms = " << Brms / nG << " nG";
+     211           0 :         if (havePhotons)
+     212           0 :                 s << ", synchrotron photons E > " << secondaryThreshold / eV << " eV";
+     213             :         else
+     214           0 :                 s << ", no synchrotron photons";
+     215           0 :         if (maximumSamples > 0)
+     216           0 :                 s << "maximum number of photon samples: " << maximumSamples;
+     217           0 :         if (thinning > 0)
+     218           0 :                 s << "thinning parameter: " << thinning; 
+     219           0 :         return s.str();
+     220           0 : }
+     221             : 
+     222           1 : void SynchrotronRadiation::setInteractionTag(std::string tag) {
+     223           1 :         interactionTag = tag;
+     224           1 : }
+     225             : 
+     226           2 : std::string SynchrotronRadiation::getInteractionTag() const {
+     227           2 :         return interactionTag;
+     228             : }
+     229             : 
+     230             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html b/doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html new file mode 100644 index 000000000..97378d014 --- /dev/null +++ b/doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/TextOutput.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - TextOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21924988.0 %
Date:2024-04-08 14:58:22Functions:91464.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10TextOutput4gzipEv0
_ZN7crpropa10TextOutputC2ERSo0
_ZN7crpropa10TextOutputC2ERSoNS_6Output10OutputTypeE0
_ZN7crpropa10TextOutputC2Ev0
_ZNK7crpropa10TextOutput14getDescriptionB5cxx11Ev0
_ZN7crpropa10TextOutput4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEPNS_17ParticleCollectorE1
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE1
_ZN7crpropa10TextOutputD0Ev1
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa10TextOutputC2ENS_6Output10OutputTypeE7
_ZN7crpropa10TextOutputD2Ev9
_ZNK7crpropa10TextOutput11printHeaderEv9
_ZN7crpropa10TextOutput5closeEv10
_ZNK7crpropa10TextOutput7processEPNS_9CandidateE54
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/TextOutput.cpp.func.html b/doc/coverageReport/src/module/TextOutput.cpp.func.html new file mode 100644 index 000000000..1ca5f18f5 --- /dev/null +++ b/doc/coverageReport/src/module/TextOutput.cpp.func.html @@ -0,0 +1,128 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/TextOutput.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - TextOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21924988.0 %
Date:2024-04-08 14:58:22Functions:91464.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10TextOutput4gzipEv0
_ZN7crpropa10TextOutput4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEPNS_17ParticleCollectorE1
_ZN7crpropa10TextOutput5closeEv10
_ZN7crpropa10TextOutputC2ENS_6Output10OutputTypeE7
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE1
_ZN7crpropa10TextOutputC2ERSo0
_ZN7crpropa10TextOutputC2ERSoNS_6Output10OutputTypeE0
_ZN7crpropa10TextOutputC2Ev0
_ZN7crpropa10TextOutputD0Ev1
_ZN7crpropa10TextOutputD2Ev9
_ZNK7crpropa10TextOutput11printHeaderEv9
_ZNK7crpropa10TextOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa10TextOutput7processEPNS_9CandidateE54
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/TextOutput.cpp.gcov.html b/doc/coverageReport/src/module/TextOutput.cpp.gcov.html new file mode 100644 index 000000000..7ac87a19d --- /dev/null +++ b/doc/coverageReport/src/module/TextOutput.cpp.gcov.html @@ -0,0 +1,457 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/TextOutput.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - TextOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21924988.0 %
Date:2024-04-08 14:58:22Functions:91464.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/TextOutput.h"
+       2             : #include "crpropa/module/ParticleCollector.h"
+       3             : #include "crpropa/Units.h"
+       4             : #include "crpropa/Version.h"
+       5             : #include "crpropa/Random.h"
+       6             : #include "crpropa/base64.h"
+       7             : 
+       8             : #include "kiss/string.h"
+       9             : 
+      10             : #include <cstdio>
+      11             : #include <stdexcept>
+      12             : #include <iostream>
+      13             : 
+      14             : #ifdef CRPROPA_HAVE_ZLIB
+      15             : #include <izstream.hpp>
+      16             : #include <ozstream.hpp>
+      17             : #endif
+      18             : 
+      19             : namespace crpropa {
+      20             : 
+      21           0 : TextOutput::TextOutput() : Output(), out(&std::cout), storeRandomSeeds(false) {
+      22           0 : }
+      23             : 
+      24           7 : TextOutput::TextOutput(OutputType outputtype) : Output(outputtype), out(&std::cout), storeRandomSeeds(false) {
+      25           7 : }
+      26             : 
+      27           0 : TextOutput::TextOutput(std::ostream &out) : Output(), out(&out), storeRandomSeeds(false) {
+      28           0 : }
+      29             : 
+      30           0 : TextOutput::TextOutput(std::ostream &out,
+      31           0 :                 OutputType outputtype) : Output(outputtype), out(&out), storeRandomSeeds(false) {
+      32           0 : }
+      33             : 
+      34           4 : TextOutput::TextOutput(const std::string &filename) :  Output(), outfile(filename.c_str(),
+      35           2 :                                 std::ios::binary), out(&outfile),  filename(
+      36           4 :                                 filename), storeRandomSeeds(false) {
+      37           2 :         if (!outfile.is_open())
+      38           2 :                 throw std::runtime_error(std::string("Cannot create file: ") + filename);
+      39           3 :         if (kiss::ends_with(filename, ".gz"))
+      40           0 :                 gzip();
+      41           3 : }
+      42             : 
+      43           1 : TextOutput::TextOutput(const std::string &filename,
+      44           2 :                                 OutputType outputtype) : Output(outputtype), outfile(filename.c_str(),
+      45           1 :                                 std::ios::binary), out(&outfile), filename(
+      46           2 :                                 filename), storeRandomSeeds(false) {
+      47           1 :         if (!outfile.is_open())
+      48           0 :                 throw std::runtime_error(std::string("Cannot create file: ") + filename);
+      49           2 :         if (kiss::ends_with(filename, ".gz"))
+      50           0 :                 gzip();
+      51           1 : }
+      52             : 
+      53           9 : void TextOutput::printHeader() const {
+      54           9 :         *out << "#";
+      55           9 :         if (fields.test(TrajectoryLengthColumn))
+      56           6 :                 *out << "\tD";
+      57           9 :         if (fields.test(RedshiftColumn))
+      58           2 :                 *out << "\tz";
+      59           9 :         if (fields.test(SerialNumberColumn))
+      60           3 :                 *out << "\tSN";
+      61           9 :         if (fields.test(CurrentIdColumn))
+      62           8 :                 *out << "\tID";
+      63           9 :         if (fields.test(CurrentEnergyColumn))
+      64           8 :                 *out << "\tE";
+      65           9 :         if (fields.test(CurrentPositionColumn) && oneDimensional)
+      66           2 :                 *out << "\tX";
+      67           9 :         if (fields.test(CurrentPositionColumn) && not oneDimensional)
+      68           3 :                 *out << "\tX\tY\tZ";
+      69           9 :         if (fields.test(CurrentDirectionColumn) && not oneDimensional)
+      70           3 :                 *out << "\tPx\tPy\tPz";
+      71           9 :         if (fields.test(SerialNumberColumn))
+      72           3 :                 *out << "\tSN0";
+      73           9 :         if (fields.test(SourceIdColumn))
+      74           6 :                 *out << "\tID0";
+      75           9 :         if (fields.test(SourceEnergyColumn))
+      76           6 :                 *out << "\tE0";
+      77           9 :         if (fields.test(SourcePositionColumn) && oneDimensional) 
+      78           1 :                 *out << "\tX0";
+      79           9 :         if (fields.test(SourcePositionColumn) && not oneDimensional)
+      80           2 :                 *out << "\tX0\tY0\tZ0";
+      81           9 :         if (fields.test(SourceDirectionColumn) && not oneDimensional)
+      82           2 :                 *out << "\tP0x\tP0y\tP0z";
+      83           9 :         if (fields.test(SerialNumberColumn))
+      84           3 :                 *out << "\tSN1";
+      85           9 :         if (fields.test(CreatedIdColumn))
+      86           2 :                 *out << "\tID1";
+      87           9 :         if (fields.test(CreatedEnergyColumn))
+      88           2 :                 *out << "\tE1";
+      89           9 :         if (fields.test(CreatedPositionColumn) && oneDimensional)
+      90           1 :                 *out << "\tX1";
+      91           9 :         if (fields.test(CreatedPositionColumn) && not oneDimensional)
+      92           1 :                 *out << "\tX1\tY1\tZ1";
+      93           9 :         if (fields.test(CreatedDirectionColumn) && not oneDimensional)
+      94           1 :                 *out << "\tP1x\tP1y\tP1z";
+      95           9 :         if (fields.test(WeightColumn))
+      96           2 :                 *out << "\tW";
+      97           9 :         if (fields.test(CandidateTagColumn))
+      98           3 :                 *out << "\ttag";
+      99           9 :         for(std::vector<Property>::const_iterator iter = properties.begin();
+     100          10 :                         iter != properties.end(); ++iter)
+     101             :         {
+     102           1 :                 *out << "\t" << (*iter).name;
+     103             :         }
+     104             : 
+     105           9 :         *out << "\n#\n";
+     106           9 :         if (fields.test(TrajectoryLengthColumn))
+     107           6 :                 *out << "# D             Trajectory length [" << lengthScale / Mpc
+     108           6 :                                 << " Mpc]\n";
+     109           9 :         if (fields.test(RedshiftColumn))
+     110           2 :                 *out << "# z             Redshift\n";
+     111           9 :         if (fields.test(SerialNumberColumn))
+     112           3 :                 *out << "# SN/SN0/SN1    Serial number. Unique (within this run) id of the particle.\n";
+     113           1 :         if (fields.test(CurrentIdColumn) || fields.test(CreatedIdColumn)
+     114          10 :                         || fields.test(SourceIdColumn))
+     115           8 :                 *out << "# ID/ID0/ID1    Particle type (PDG MC numbering scheme)\n";
+     116           1 :         if (fields.test(CurrentEnergyColumn) || fields.test(CreatedEnergyColumn)
+     117          10 :                         || fields.test(SourceEnergyColumn))
+     118           8 :                 *out << "# E/E0/E1       Energy [" << energyScale / EeV << " EeV]\n";
+     119           4 :         if (fields.test(CurrentPositionColumn) || fields.test(CreatedPositionColumn)
+     120          13 :                         || fields.test(SourcePositionColumn))
+     121           5 :                 *out << "# X/X0/X1...    Position [" << lengthScale / Mpc << " Mpc]\n";
+     122             :         if (fields.test(CurrentDirectionColumn)
+     123           5 :                         || fields.test(CreatedDirectionColumn)
+     124          14 :                         || fields.test(SourceDirectionColumn))
+     125           4 :                 *out << "# Px/P0x/P1x... Heading (unit vector of momentum)\n";
+     126           9 :         if (fields.test(WeightColumn))
+     127           2 :                 *out << "# W             Weights" << " \n";
+     128           9 :         if (fields.test(CandidateTagColumn)) {
+     129           3 :                 *out << "# tag           Candidate tag can be given by the source feature (user defined tag) or by the following interaction process \n";
+     130           3 :                 *out << "#\tES  \tElasticScattering \n" << "#\tEPP \tElectronPairProduction \n" << "#\tEMPP\tEMPairProduction\n"
+     131             :                         << "#\tEMDP\tEMDoublePairProduction\n" << "#\tEMTP\tEMTripletPairProduction \n" << "#\tEMIC\tEMInverseComptonScattering\n"
+     132             :                         << "#\tND  \tNuclearDecay\n" << "#\tPD  \tPhotoDisintegration\n" << "#\tPPP  \tPhotoPionProduction\n" << "#\tSYN \tSynchrotronRadiation\n"
+     133           3 :                         << "#\tPRIM/SEC\t primary / secondary particle\n";
+     134             :         }
+     135           9 :         for(std::vector<Property>::const_iterator iter = properties.begin();
+     136          10 :                         iter != properties.end(); ++iter)
+     137             :         {
+     138           2 :                         *out << "# " << (*iter).name << " " << (*iter).comment << "\n";
+     139             :         }
+     140             : 
+     141           9 :         *out << "# no index = current, 0 = at source, 1 = at point of creation\n#\n";
+     142          18 :         *out << "# CRPropa version: " << g_GIT_DESC << "\n#\n";
+     143             : 
+     144           9 :         if (storeRandomSeeds)
+     145             :         {
+     146           0 :                 *out << "# Random seeds:\n";
+     147           0 :                 std::vector< std::vector<uint32_t> > seeds = Random::getSeedThreads();
+     148             : 
+     149           0 :                 for (size_t i =0; i < seeds.size(); i++)
+     150             :                 {
+     151           0 :                         std::string encoded_data = Base64::encode((unsigned char*) &seeds[i][0], sizeof(seeds[i][0]) * seeds[i].size() / sizeof(unsigned char));
+     152           0 :                         *out << "#   Thread " << i << ": ";
+     153           0 :                         *out << encoded_data;
+     154           0 :                         *out << "\n";
+     155             :                 }
+     156           0 :         }
+     157           9 : }
+     158             : 
+     159          54 : void TextOutput::process(Candidate *c) const {
+     160          54 :         if (fields.none() && properties.empty())
+     161           0 :                 return;
+     162             : 
+     163             :         char buffer[1024];
+     164             :         size_t p = 0;
+     165             : 
+     166          54 :         std::locale old_locale = std::locale::global(std::locale::classic());
+     167             : 
+     168          54 :         if (fields.test(TrajectoryLengthColumn))
+     169          51 :                 p += std::sprintf(buffer + p, "%8.5E\t",
+     170          51 :                                 c->getTrajectoryLength() / lengthScale);
+     171             : 
+     172          54 :         if (fields.test(RedshiftColumn))
+     173          47 :                 p += std::sprintf(buffer + p, "%1.5E\t", c->getRedshift());
+     174             : 
+     175          54 :         if (fields.test(SerialNumberColumn))
+     176          48 :                 p += std::sprintf(buffer + p, "%10lu\t",
+     177             :                                 c->getSerialNumber());
+     178          54 :         if (fields.test(CurrentIdColumn))
+     179          53 :                 p += std::sprintf(buffer + p, "%10i\t", c->current.getId());
+     180          54 :         if (fields.test(CurrentEnergyColumn))
+     181          53 :                 p += std::sprintf(buffer + p, "%8.5E\t",
+     182          53 :                                 c->current.getEnergy() / energyScale);
+     183          54 :         if (fields.test(CurrentPositionColumn)) {
+     184          50 :                 if (oneDimensional) {
+     185          37 :                         p += std::sprintf(buffer + p, "%8.5E\t",
+     186          37 :                                         c->current.getPosition().x / lengthScale);
+     187             :                 } else {
+     188          13 :                         const Vector3d pos = c->current.getPosition() / lengthScale;
+     189          13 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
+     190             :                                         pos.z);
+     191             :                 }
+     192             :         }
+     193          54 :         if (fields.test(CurrentDirectionColumn)) {
+     194          49 :                 if (not oneDimensional) {
+     195          13 :                         const Vector3d pos = c->current.getDirection();
+     196          13 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
+     197             :                                         pos.z);
+     198             :                 }
+     199             :         }
+     200             : 
+     201          54 :         if (fields.test(SerialNumberColumn))
+     202          48 :                 p += std::sprintf(buffer + p, "%10lu\t", c->getSourceSerialNumber());
+     203          54 :         if (fields.test(SourceIdColumn))
+     204          51 :                 p += std::sprintf(buffer + p, "%10i\t", c->source.getId());
+     205          54 :         if (fields.test(SourceEnergyColumn))
+     206          51 :                 p += std::sprintf(buffer + p, "%8.5E\t",
+     207          51 :                                 c->source.getEnergy() / energyScale);
+     208          54 :         if (fields.test(SourcePositionColumn)) {
+     209          48 :                 if (oneDimensional) {
+     210          36 :                         p += std::sprintf(buffer + p, "%8.5E\t",
+     211          36 :                                         c->source.getPosition().x / lengthScale);
+     212             :                 } else {
+     213          12 :                         const Vector3d pos = c->source.getPosition() / lengthScale;
+     214          12 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
+     215             :                                         pos.z);
+     216             :                 }
+     217             :         }
+     218          54 :         if (fields.test(SourceDirectionColumn)) {
+     219          48 :                 if (not oneDimensional) {
+     220          12 :                         const Vector3d pos = c->source.getDirection();
+     221          12 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
+     222             :                                         pos.z);
+     223             :                 }
+     224             : 
+     225             :         }
+     226             : 
+     227          54 :         if (fields.test(SerialNumberColumn))
+     228          48 :                 p += std::sprintf(buffer + p, "%10lu\t",
+     229             :                                 c->getCreatedSerialNumber());
+     230          54 :         if (fields.test(CreatedIdColumn))
+     231          47 :                 p += std::sprintf(buffer + p, "%10i\t", c->created.getId());
+     232          54 :         if (fields.test(CreatedEnergyColumn))
+     233          47 :                 p += std::sprintf(buffer + p, "%8.5E\t",
+     234          47 :                                 c->created.getEnergy() / energyScale);
+     235          54 :         if (fields.test(CreatedPositionColumn)) {
+     236          47 :                 if (oneDimensional) {
+     237          36 :                         p += std::sprintf(buffer + p, "%8.5E\t",
+     238          36 :                                         c->created.getPosition().x / lengthScale);
+     239             :                 } else {
+     240          11 :                         const Vector3d pos = c->created.getPosition() / lengthScale;
+     241          11 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
+     242             :                                         pos.z);
+     243             :                 }
+     244             :         }
+     245          54 :         if (fields.test(CreatedDirectionColumn)) {
+     246          47 :                 if (not oneDimensional) {
+     247          11 :                         const Vector3d pos = c->created.getDirection();
+     248          11 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
+     249             :                                         pos.z);
+     250             :                 }
+     251             :         }
+     252          54 :         if (fields.test(WeightColumn)) {
+     253          47 :                 p += std::sprintf(buffer + p, "%8.5E\t", c->getWeight());
+     254             :         }
+     255          54 :         if (fields.test(CandidateTagColumn)) {
+     256          48 :                 p += std::sprintf(buffer + p, "%s\t", c->getTagOrigin().c_str());
+     257             :         }
+     258             : 
+     259          54 :         for(std::vector<Output::Property>::const_iterator iter = properties.begin();
+     260          55 :                         iter != properties.end(); ++iter) {
+     261           1 :                   Variant v;
+     262           1 :                         if (c->hasProperty((*iter).name)) {
+     263           0 :                                 v = c->getProperty((*iter).name);
+     264             :                         } else {
+     265           1 :                                 v = (*iter).defaultValue;
+     266             :                         }
+     267           1 :                         p += std::sprintf(buffer + p, "%s", v.toString("\t").c_str());
+     268           1 :                         p += std::sprintf(buffer + p, "\t");
+     269           1 :         }
+     270          54 :         buffer[p - 1] = '\n';
+     271             : 
+     272          54 :         std::locale::global(old_locale);
+     273             : 
+     274         108 : #pragma omp critical
+     275             :         {
+     276          54 :                 if (count == 0)
+     277           9 :                         printHeader();
+     278          54 :                 Output::process(c);
+     279          54 :                 out->write(buffer, p);
+     280             :         }
+     281             : 
+     282          54 : }
+     283             : 
+     284           1 : void TextOutput::load(const std::string &filename, ParticleCollector *collector){
+     285             : 
+     286             :         std::string line;
+     287             :         std::istream *in;
+     288           1 :         std::ifstream infile(filename.c_str());
+     289             :         
+     290             :         double lengthScale = Mpc; // default Mpc
+     291             :         double energyScale = EeV; // default EeV
+     292             : 
+     293           1 :         if (!infile.good())
+     294           0 :                 throw std::runtime_error("crpropa::TextOutput: could not open file " + filename);
+     295             :         in = &infile;
+     296             :         
+     297           2 :         if (kiss::ends_with(filename, ".gz")){
+     298             : #ifdef CRPROPA_HAVE_ZLIB
+     299           0 :                 in = new zstream::igzstream(*in);
+     300             : #else
+     301             :                 throw std::runtime_error("CRPropa was built without Zlib compression!");
+     302             : #endif
+     303             :         }
+     304             : 
+     305          38 :         while (std::getline(*in, line)) {
+     306          37 :                 std::stringstream stream(line);
+     307          37 :                 if (stream.peek() == '#')
+     308             :                         continue;
+     309             : 
+     310          22 :                 ref_ptr<Candidate> c = new Candidate(); 
+     311             :                 double val_d; int val_i;
+     312             :                 double x, y, z;
+     313             :                 stream >> val_d;
+     314          11 :                 c->setTrajectoryLength(val_d*lengthScale); // D
+     315             :                 stream >> val_d;
+     316          11 :                 c->setRedshift(val_d); // z
+     317          11 :                 stream >> val_i;
+     318          11 :                 c->setSerialNumber(val_i); // SN
+     319          11 :                 stream >> val_i;
+     320          11 :                 c->current.setId(val_i); // ID
+     321             :                 stream >> val_d;
+     322          11 :                 c->current.setEnergy(val_d*energyScale); // E
+     323             :                 stream >> x >> y >> z;
+     324          11 :                 c->current.setPosition(Vector3d(x, y, z)*lengthScale); // X, Y, Z
+     325             :                 stream >> x >> y >> z;
+     326          11 :                 c->current.setDirection(Vector3d(x, y, z)*lengthScale); // Px, Py, Pz
+     327          11 :                 stream >> val_i; // SN0 (TODO: Reconstruct the parent-child relationship)
+     328          11 :                 stream >> val_i;
+     329          11 :                 c->source.setId(val_i); // ID0
+     330             :                 stream >> val_d;
+     331          11 :                 c->source.setEnergy(val_d*energyScale);      // E0
+     332             :                 stream >> x >> y >> z;
+     333          11 :                 c->source.setPosition(Vector3d(x, y, z)*lengthScale); // X0, Y0, Z0
+     334             :                 stream >> x >> y >> z;
+     335          11 :                 c->source.setDirection(Vector3d(x, y, z)*lengthScale); // P0x, P0y, P0z
+     336          11 :                 stream >> val_i; // SN1
+     337          11 :                 stream >> val_i;
+     338          11 :                 c->created.setId(val_i); // ID1
+     339             :                 stream >> val_d;
+     340          11 :                 c->created.setEnergy(val_d*energyScale); // E1
+     341             :                 stream >> x >> y >> z;
+     342          11 :                 c->created.setPosition(Vector3d(x, y, z)*lengthScale); // X1, Y1, Z1
+     343             :                 stream >> x >> y >> z;
+     344          11 :                 c->created.setDirection(Vector3d(x, y, z)*lengthScale); // P1x, P1y, P1z
+     345             :                 stream >> val_d;
+     346          11 :                 c->setWeight(val_d); // W
+     347             : 
+     348          22 :                 collector->process(c);
+     349          37 :         }
+     350           1 :         infile.close();
+     351           2 : }
+     352             : 
+     353           0 : std::string TextOutput::getDescription() const {
+     354           0 :         return "TextOutput";
+     355             : }
+     356             : 
+     357          10 : void TextOutput::close() {
+     358             : #ifdef CRPROPA_HAVE_ZLIB
+     359          10 :         zstream::ogzstream *zs = dynamic_cast<zstream::ogzstream *>(out);
+     360          10 :         if (zs) {
+     361           0 :                 zs->close();
+     362           0 :                 delete out;
+     363           0 :                 out = 0;
+     364             :         }
+     365             : #endif
+     366          10 :         outfile.flush();
+     367          10 : }
+     368             : 
+     369          10 : TextOutput::~TextOutput() {
+     370           9 :         close();
+     371          10 : }
+     372             : 
+     373           0 : void TextOutput::gzip() {
+     374             : #ifdef CRPROPA_HAVE_ZLIB
+     375           0 :         out = new zstream::ogzstream(*out);
+     376             : #else
+     377             :         throw std::runtime_error("CRPropa was built without Zlib compression!");
+     378             : #endif
+     379           0 : }
+     380             : 
+     381             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Tools.cpp.func-sort-c.html b/doc/coverageReport/src/module/Tools.cpp.func-sort-c.html new file mode 100644 index 000000000..ec6611df0 --- /dev/null +++ b/doc/coverageReport/src/module/Tools.cpp.func-sort-c.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Tools.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Tools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:77010.0 %
Date:2024-04-08 14:58:22Functions:21612.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14ParticleFilter5addIdEi0
_ZN7crpropa14ParticleFilter6getIdsEv0
_ZN7crpropa14ParticleFilter8removeIdEi0
_ZN7crpropa14ParticleFilterC2Ev0
_ZN7crpropa17EmissionMapFiller14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17EmissionMapFillerC2EPNS_11EmissionMapE0
_ZN7crpropa17PerformanceModule3addEPNS_6ModuleE0
_ZN7crpropa17PerformanceModuleD0Ev0
_ZN7crpropa17PerformanceModuleD2Ev0
_ZNK7crpropa14ParticleFilter14getDescriptionB5cxx11Ev0
_ZNK7crpropa17EmissionMapFiller14getDescriptionB5cxx11Ev0
_ZNK7crpropa17EmissionMapFiller7processEPNS_9CandidateE0
_ZNK7crpropa17PerformanceModule14getDescriptionB5cxx11Ev0
_ZNK7crpropa17PerformanceModule7processEPNS_9CandidateE0
_ZN7crpropa14ParticleFilterC2ERKSt3setIiSt4lessIiESaIiEE1
_ZNK7crpropa14ParticleFilter7processEPNS_9CandidateE7
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Tools.cpp.func.html b/doc/coverageReport/src/module/Tools.cpp.func.html new file mode 100644 index 000000000..23037d8e8 --- /dev/null +++ b/doc/coverageReport/src/module/Tools.cpp.func.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Tools.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Tools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:77010.0 %
Date:2024-04-08 14:58:22Functions:21612.5 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14ParticleFilter5addIdEi0
_ZN7crpropa14ParticleFilter6getIdsEv0
_ZN7crpropa14ParticleFilter8removeIdEi0
_ZN7crpropa14ParticleFilterC2ERKSt3setIiSt4lessIiESaIiEE1
_ZN7crpropa14ParticleFilterC2Ev0
_ZN7crpropa17EmissionMapFiller14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17EmissionMapFillerC2EPNS_11EmissionMapE0
_ZN7crpropa17PerformanceModule3addEPNS_6ModuleE0
_ZN7crpropa17PerformanceModuleD0Ev0
_ZN7crpropa17PerformanceModuleD2Ev0
_ZNK7crpropa14ParticleFilter14getDescriptionB5cxx11Ev0
_ZNK7crpropa14ParticleFilter7processEPNS_9CandidateE7
_ZNK7crpropa17EmissionMapFiller14getDescriptionB5cxx11Ev0
_ZNK7crpropa17EmissionMapFiller7processEPNS_9CandidateE0
_ZNK7crpropa17PerformanceModule14getDescriptionB5cxx11Ev0
_ZNK7crpropa17PerformanceModule7processEPNS_9CandidateE0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/Tools.cpp.gcov.html b/doc/coverageReport/src/module/Tools.cpp.gcov.html new file mode 100644 index 000000000..050d3fde4 --- /dev/null +++ b/doc/coverageReport/src/module/Tools.cpp.gcov.html @@ -0,0 +1,199 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module/Tools.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/module - Tools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:77010.0 %
Date:2024-04-08 14:58:22Functions:21612.5 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/module/Tools.h"
+       2             : #include "crpropa/Clock.h"
+       3             : 
+       4             : #include <iostream>
+       5             : #include <sstream>
+       6             : 
+       7             : using namespace std;
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11           0 : PerformanceModule::~PerformanceModule() {
+      12             :         double total = 0;
+      13           0 :         for (size_t i = 0; i < modules.size(); i++) {
+      14             :                 _module_info &m = modules[i];
+      15           0 :                 total += m.time;
+      16             :         }
+      17           0 :         cout << "Performance for " << calls << " calls:" << endl;
+      18           0 :         for (size_t i = 0; i < modules.size(); i++) {
+      19             :                 _module_info &m = modules[i];
+      20           0 :                 cout << " - " << floor((1000 * m.time / total) + 0.5) / 10 << "% -> "
+      21           0 :                                 << m.module->getDescription() << ": " << (m.time / calls)
+      22             :                                 << endl;
+      23             :         }
+      24           0 : }
+      25             : 
+      26           0 : void PerformanceModule::add(Module *module) {
+      27             :         _module_info info;
+      28           0 :         info.module = module;
+      29           0 :         info.time = 0;
+      30           0 :         modules.push_back(info);
+      31           0 : }
+      32             : 
+      33           0 : void PerformanceModule::process(Candidate *candidate) const {
+      34           0 :         vector<double> times(modules.size());
+      35           0 :         for (size_t i = 0; i < modules.size(); i++) {
+      36             :                 _module_info &m = modules[i];
+      37           0 :                 double start = Clock::getInstance().getMillisecond();
+      38           0 :                 m.module->process(candidate);
+      39           0 :                 double end = Clock::getInstance().getMillisecond();
+      40           0 :                 times[i] = end - start;
+      41             :         }
+      42             : 
+      43           0 : #pragma omp critical
+      44             :         {
+      45           0 :                 for (size_t i = 0; i < modules.size(); i++) {
+      46             :                         _module_info &m = modules[i];
+      47           0 :                         m.time += times[i];
+      48             :                 }
+      49           0 :                 calls++;
+      50             :         }
+      51           0 : }
+      52             : 
+      53           0 : string PerformanceModule::getDescription() const {
+      54           0 :         stringstream sstr;
+      55           0 :         sstr << "PerformanceModule (";
+      56           0 :         for (size_t i = 0; i < modules.size(); i++) {
+      57             :                 _module_info &m = modules[i];
+      58           0 :                 if (i > 0)
+      59           0 :                         sstr << ", ";
+      60           0 :                 sstr << m.module->getDescription();
+      61             :         }
+      62           0 :         sstr << ")";
+      63           0 :         return sstr.str();
+      64           0 : }
+      65             : 
+      66             : // ----------------------------------------------------------------------------
+      67           0 : ParticleFilter::ParticleFilter() {
+      68             : 
+      69           0 : }
+      70           1 : ParticleFilter::ParticleFilter(const std::set<int> &ids) : ids(ids) {
+      71             : 
+      72           1 : }
+      73           0 : void ParticleFilter::addId(int id) {
+      74             :         ids.insert(id);
+      75           0 : }
+      76           0 : void ParticleFilter::removeId(int id) {
+      77             :         ids.erase(id);
+      78           0 : }
+      79             : 
+      80           0 : std::set<int> &ParticleFilter::getIds() {
+      81           0 :         return ids;
+      82             : }
+      83             : 
+      84           7 : void ParticleFilter::process(Candidate* candidate) const {
+      85          14 :         if (ids.find(candidate->current.getId()) == ids.end())
+      86           5 :                 reject(candidate);
+      87             :         else
+      88           2 :                 accept(candidate);
+      89           7 : }
+      90             : 
+      91           0 : string ParticleFilter::getDescription() const {
+      92           0 :         stringstream sstr;
+      93           0 :         sstr << "ParticleFilter: ";
+      94           0 :         for (std::set<int>::const_iterator i = ids.begin(); i != ids.end(); i++) {
+      95           0 :                 sstr << *i << ", ";
+      96             :         }
+      97           0 :         sstr << ")";
+      98           0 :         return sstr.str();
+      99           0 : }
+     100             : 
+     101             : // ----------------------------------------------------------------------------
+     102           0 : EmissionMapFiller::EmissionMapFiller(EmissionMap *emissionMap) : emissionMap(emissionMap) {
+     103             : 
+     104           0 : }
+     105             : 
+     106           0 : void EmissionMapFiller::setEmissionMap(EmissionMap *emissionMap) {
+     107           0 :         this->emissionMap = emissionMap;
+     108           0 : }
+     109             : 
+     110           0 : void EmissionMapFiller::process(Candidate* candidate) const {
+     111           0 :         if (emissionMap) {
+     112           0 :                 #pragma omp critical
+     113             :                 {
+     114           0 :                         emissionMap->fillMap(candidate->source);
+     115             :                 }
+     116             :         }
+     117           0 : }
+     118             : 
+     119           0 : string EmissionMapFiller::getDescription() const {
+     120           0 :         return "EmissionMapFiller";
+     121             : }
+     122             : 
+     123             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/index-sort-f.html b/doc/coverageReport/src/module/index-sort-f.html new file mode 100644 index 000000000..cb0181bfe --- /dev/null +++ b/doc/coverageReport/src/module/index-sort-f.html @@ -0,0 +1,383 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:2250354763.4 %
Date:2024-04-08 14:58:22Functions:28648559.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
OutputShell.cpp +
0.0%
+
0.0 %0 / 270.0 %0 / 6
PhotonOutput1D.cpp +
0.0%
+
0.0 %0 / 560.0 %0 / 9
Acceleration.cpp +
0.0%
+
0.0 %0 / 890.0 %0 / 14
Tools.cpp +
10.0%10.0%
+
10.0 %7 / 7012.5 %2 / 16
Redshift.cpp +
32.1%32.1%
+
32.1 %9 / 2825.0 %1 / 4
SimplePropagation.cpp +
36.4%36.4%
+
36.4 %12 / 3328.6 %2 / 7
HDF5Output.cpp +
5.0%5.0%
+
5.0 %12 / 24128.6 %4 / 14
MomentumDiffusion.cpp +
24.4%24.4%
+
24.4 %11 / 4530.0 %3 / 10
Observer.cpp +
44.4%44.4%
+
44.4 %80 / 18036.4 %16 / 44
BreakCondition.cpp +
36.6%36.6%
+
36.6 %63 / 17239.5 %15 / 38
Boundary.cpp +
48.4%48.4%
+
48.4 %106 / 21944.4 %20 / 45
SynchrotronRadiation.cpp +
61.8%61.8%
+
61.8 %81 / 13147.6 %10 / 21
PhotoPionProduction.cpp +
63.6%63.6%
+
63.6 %246 / 38760.0 %24 / 40
TextOutput.cpp +
88.0%88.0%
+
88.0 %219 / 24964.3 %9 / 14
RestrictToRegion.cpp +
50.0%50.0%
+
50.0 %6 / 1266.7 %2 / 3
ParticleCollector.cpp +
75.0%75.0%
+
75.0 %54 / 7270.8 %17 / 24
ElasticScattering.cpp +
90.0%90.0%
+
90.0 %63 / 7071.4 %5 / 7
PhotoDisintegration.cpp +
80.0%80.0%
+
80.0 %140 / 17583.3 %10 / 12
NuclearDecay.cpp +
81.5%81.5%
+
81.5 %137 / 16884.6 %11 / 13
Output.cpp +
89.8%89.8%
+
89.8 %88 / 9887.5 %14 / 16
DiffusionSDE.cpp +
76.2%76.2%
+
76.2 %154 / 20288.0 %22 / 25
ElectronPairProduction.cpp +
92.4%92.4%
+
92.4 %85 / 9290.0 %9 / 10
CandidateSplitting.cpp +
86.9%86.9%
+
86.9 %53 / 6190.9 %10 / 11
PropagationCK.cpp +
87.6%87.6%
+
87.6 %85 / 9792.9 %13 / 14
PropagationBP.cpp +
88.5%88.5%
+
88.5 %92 / 10493.8 %15 / 16
AdiabaticCooling.cpp +
85.2%85.2%
+
85.2 %23 / 27100.0 %5 / 5
EMDoublePairProduction.cpp +
94.4%94.4%
+
94.4 %68 / 72100.0 %10 / 10
EMTripletPairProduction.cpp +
94.0%94.0%
+
94.0 %94 / 100100.0 %11 / 11
EMInverseComptonScattering.cpp +
96.2%96.2%
+
96.2 %128 / 133100.0 %13 / 13
EMPairProduction.cpp +
97.8%97.8%
+
97.8 %134 / 137100.0 %13 / 13
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/index-sort-l.html b/doc/coverageReport/src/module/index-sort-l.html new file mode 100644 index 000000000..aa76e709f --- /dev/null +++ b/doc/coverageReport/src/module/index-sort-l.html @@ -0,0 +1,383 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:2250354763.4 %
Date:2024-04-08 14:58:22Functions:28648559.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
OutputShell.cpp +
0.0%
+
0.0 %0 / 270.0 %0 / 6
PhotonOutput1D.cpp +
0.0%
+
0.0 %0 / 560.0 %0 / 9
Acceleration.cpp +
0.0%
+
0.0 %0 / 890.0 %0 / 14
HDF5Output.cpp +
5.0%5.0%
+
5.0 %12 / 24128.6 %4 / 14
Tools.cpp +
10.0%10.0%
+
10.0 %7 / 7012.5 %2 / 16
MomentumDiffusion.cpp +
24.4%24.4%
+
24.4 %11 / 4530.0 %3 / 10
Redshift.cpp +
32.1%32.1%
+
32.1 %9 / 2825.0 %1 / 4
SimplePropagation.cpp +
36.4%36.4%
+
36.4 %12 / 3328.6 %2 / 7
BreakCondition.cpp +
36.6%36.6%
+
36.6 %63 / 17239.5 %15 / 38
Observer.cpp +
44.4%44.4%
+
44.4 %80 / 18036.4 %16 / 44
Boundary.cpp +
48.4%48.4%
+
48.4 %106 / 21944.4 %20 / 45
RestrictToRegion.cpp +
50.0%50.0%
+
50.0 %6 / 1266.7 %2 / 3
SynchrotronRadiation.cpp +
61.8%61.8%
+
61.8 %81 / 13147.6 %10 / 21
PhotoPionProduction.cpp +
63.6%63.6%
+
63.6 %246 / 38760.0 %24 / 40
ParticleCollector.cpp +
75.0%75.0%
+
75.0 %54 / 7270.8 %17 / 24
DiffusionSDE.cpp +
76.2%76.2%
+
76.2 %154 / 20288.0 %22 / 25
PhotoDisintegration.cpp +
80.0%80.0%
+
80.0 %140 / 17583.3 %10 / 12
NuclearDecay.cpp +
81.5%81.5%
+
81.5 %137 / 16884.6 %11 / 13
AdiabaticCooling.cpp +
85.2%85.2%
+
85.2 %23 / 27100.0 %5 / 5
CandidateSplitting.cpp +
86.9%86.9%
+
86.9 %53 / 6190.9 %10 / 11
PropagationCK.cpp +
87.6%87.6%
+
87.6 %85 / 9792.9 %13 / 14
TextOutput.cpp +
88.0%88.0%
+
88.0 %219 / 24964.3 %9 / 14
PropagationBP.cpp +
88.5%88.5%
+
88.5 %92 / 10493.8 %15 / 16
Output.cpp +
89.8%89.8%
+
89.8 %88 / 9887.5 %14 / 16
ElasticScattering.cpp +
90.0%90.0%
+
90.0 %63 / 7071.4 %5 / 7
ElectronPairProduction.cpp +
92.4%92.4%
+
92.4 %85 / 9290.0 %9 / 10
EMTripletPairProduction.cpp +
94.0%94.0%
+
94.0 %94 / 100100.0 %11 / 11
EMDoublePairProduction.cpp +
94.4%94.4%
+
94.4 %68 / 72100.0 %10 / 10
EMInverseComptonScattering.cpp +
96.2%96.2%
+
96.2 %128 / 133100.0 %13 / 13
EMPairProduction.cpp +
97.8%97.8%
+
97.8 %134 / 137100.0 %13 / 13
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/src/module/index.html b/doc/coverageReport/src/module/index.html new file mode 100644 index 000000000..7af31a205 --- /dev/null +++ b/doc/coverageReport/src/module/index.html @@ -0,0 +1,383 @@ + + + + + + + LCOV - coverage.info.cleaned - src/module + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - src/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:2250354763.4 %
Date:2024-04-08 14:58:22Functions:28648559.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Acceleration.cpp +
0.0%
+
0.0 %0 / 890.0 %0 / 14
AdiabaticCooling.cpp +
85.2%85.2%
+
85.2 %23 / 27100.0 %5 / 5
Boundary.cpp +
48.4%48.4%
+
48.4 %106 / 21944.4 %20 / 45
BreakCondition.cpp +
36.6%36.6%
+
36.6 %63 / 17239.5 %15 / 38
CandidateSplitting.cpp +
86.9%86.9%
+
86.9 %53 / 6190.9 %10 / 11
DiffusionSDE.cpp +
76.2%76.2%
+
76.2 %154 / 20288.0 %22 / 25
EMDoublePairProduction.cpp +
94.4%94.4%
+
94.4 %68 / 72100.0 %10 / 10
EMInverseComptonScattering.cpp +
96.2%96.2%
+
96.2 %128 / 133100.0 %13 / 13
EMPairProduction.cpp +
97.8%97.8%
+
97.8 %134 / 137100.0 %13 / 13
EMTripletPairProduction.cpp +
94.0%94.0%
+
94.0 %94 / 100100.0 %11 / 11
ElasticScattering.cpp +
90.0%90.0%
+
90.0 %63 / 7071.4 %5 / 7
ElectronPairProduction.cpp +
92.4%92.4%
+
92.4 %85 / 9290.0 %9 / 10
HDF5Output.cpp +
5.0%5.0%
+
5.0 %12 / 24128.6 %4 / 14
MomentumDiffusion.cpp +
24.4%24.4%
+
24.4 %11 / 4530.0 %3 / 10
NuclearDecay.cpp +
81.5%81.5%
+
81.5 %137 / 16884.6 %11 / 13
Observer.cpp +
44.4%44.4%
+
44.4 %80 / 18036.4 %16 / 44
Output.cpp +
89.8%89.8%
+
89.8 %88 / 9887.5 %14 / 16
OutputShell.cpp +
0.0%
+
0.0 %0 / 270.0 %0 / 6
ParticleCollector.cpp +
75.0%75.0%
+
75.0 %54 / 7270.8 %17 / 24
PhotoDisintegration.cpp +
80.0%80.0%
+
80.0 %140 / 17583.3 %10 / 12
PhotoPionProduction.cpp +
63.6%63.6%
+
63.6 %246 / 38760.0 %24 / 40
PhotonOutput1D.cpp +
0.0%
+
0.0 %0 / 560.0 %0 / 9
PropagationBP.cpp +
88.5%88.5%
+
88.5 %92 / 10493.8 %15 / 16
PropagationCK.cpp +
87.6%87.6%
+
87.6 %85 / 9792.9 %13 / 14
Redshift.cpp +
32.1%32.1%
+
32.1 %9 / 2825.0 %1 / 4
RestrictToRegion.cpp +
50.0%50.0%
+
50.0 %6 / 1266.7 %2 / 3
SimplePropagation.cpp +
36.4%36.4%
+
36.4 %12 / 3328.6 %2 / 7
SynchrotronRadiation.cpp +
61.8%61.8%
+
61.8 %81 / 13147.6 %10 / 21
TextOutput.cpp +
88.0%88.0%
+
88.0 %219 / 24964.3 %9 / 14
Tools.cpp +
10.0%10.0%
+
10.0 %7 / 7012.5 %2 / 16
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/index-sort-f.html b/doc/coverageReport/test/index-sort-f.html new file mode 100644 index 000000000..d8992e401 --- /dev/null +++ b/doc/coverageReport/test/index-sort-f.html @@ -0,0 +1,243 @@ + + + + + + + LCOV - coverage.info.cleaned - test + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - testHitTotalCoverage
Test:coverage.info.cleanedLines:3320339197.9 %
Date:2024-04-08 14:58:22Functions:26427396.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
testFunctionalGroups.cpp +
87.0%87.0%
+
87.0 %20 / 2350.0 %1 / 2
testModuleList.cpp +
94.5%94.5%
+
94.5 %52 / 5585.7 %6 / 7
testVector3.cpp +
96.8%96.8%
+
96.8 %90 / 9392.3 %12 / 13
testOutput.cpp +
96.9%96.9%
+
96.9 %157 / 16294.4 %17 / 18
testPropagation.cpp +
99.1%99.1%
+
99.1 %337 / 34094.7 %18 / 19
testSource.cpp +
98.6%98.6%
+
98.6 %279 / 28395.8 %23 / 24
testBreakCondition.cpp +
99.3%99.3%
+
99.3 %398 / 40196.8 %30 / 31
testInteraction.cpp +
94.4%94.4%
+
94.4 %743 / 78798.1 %52 / 53
testCore.cpp +
99.5%99.5%
+
99.5 %654 / 65798.3 %58 / 59
testCandidateSplitting.cpp +
100.0%
+
100.0 %47 / 47100.0 %2 / 2
testAdiabaticCooling.cpp +
100.0%
+
100.0 %23 / 23100.0 %2 / 2
testAdvectionField.cpp +
100.0%
+
100.0 %83 / 83100.0 %5 / 5
testMagneticLens.cpp +
100.0%
+
100.0 %87 / 87100.0 %7 / 7
testDensity.cpp +
100.0%
+
100.0 %166 / 166100.0 %7 / 7
testTurbulentField.cpp +
100.0%
+
100.0 %46 / 46100.0 %8 / 8
testMagneticField.cpp +
100.0%
+
100.0 %138 / 138100.0 %16 / 16
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/index-sort-l.html b/doc/coverageReport/test/index-sort-l.html new file mode 100644 index 000000000..a458518a3 --- /dev/null +++ b/doc/coverageReport/test/index-sort-l.html @@ -0,0 +1,243 @@ + + + + + + + LCOV - coverage.info.cleaned - test + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - testHitTotalCoverage
Test:coverage.info.cleanedLines:3320339197.9 %
Date:2024-04-08 14:58:22Functions:26427396.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
testFunctionalGroups.cpp +
87.0%87.0%
+
87.0 %20 / 2350.0 %1 / 2
testInteraction.cpp +
94.4%94.4%
+
94.4 %743 / 78798.1 %52 / 53
testModuleList.cpp +
94.5%94.5%
+
94.5 %52 / 5585.7 %6 / 7
testVector3.cpp +
96.8%96.8%
+
96.8 %90 / 9392.3 %12 / 13
testOutput.cpp +
96.9%96.9%
+
96.9 %157 / 16294.4 %17 / 18
testSource.cpp +
98.6%98.6%
+
98.6 %279 / 28395.8 %23 / 24
testPropagation.cpp +
99.1%99.1%
+
99.1 %337 / 34094.7 %18 / 19
testBreakCondition.cpp +
99.3%99.3%
+
99.3 %398 / 40196.8 %30 / 31
testCore.cpp +
99.5%99.5%
+
99.5 %654 / 65798.3 %58 / 59
testAdiabaticCooling.cpp +
100.0%
+
100.0 %23 / 23100.0 %2 / 2
testTurbulentField.cpp +
100.0%
+
100.0 %46 / 46100.0 %8 / 8
testCandidateSplitting.cpp +
100.0%
+
100.0 %47 / 47100.0 %2 / 2
testAdvectionField.cpp +
100.0%
+
100.0 %83 / 83100.0 %5 / 5
testMagneticLens.cpp +
100.0%
+
100.0 %87 / 87100.0 %7 / 7
testMagneticField.cpp +
100.0%
+
100.0 %138 / 138100.0 %16 / 16
testDensity.cpp +
100.0%
+
100.0 %166 / 166100.0 %7 / 7
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/index.html b/doc/coverageReport/test/index.html new file mode 100644 index 000000000..8374654ca --- /dev/null +++ b/doc/coverageReport/test/index.html @@ -0,0 +1,243 @@ + + + + + + + LCOV - coverage.info.cleaned - test + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - testHitTotalCoverage
Test:coverage.info.cleanedLines:3320339197.9 %
Date:2024-04-08 14:58:22Functions:26427396.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
testAdiabaticCooling.cpp +
100.0%
+
100.0 %23 / 23100.0 %2 / 2
testAdvectionField.cpp +
100.0%
+
100.0 %83 / 83100.0 %5 / 5
testBreakCondition.cpp +
99.3%99.3%
+
99.3 %398 / 40196.8 %30 / 31
testCandidateSplitting.cpp +
100.0%
+
100.0 %47 / 47100.0 %2 / 2
testCore.cpp +
99.5%99.5%
+
99.5 %654 / 65798.3 %58 / 59
testDensity.cpp +
100.0%
+
100.0 %166 / 166100.0 %7 / 7
testFunctionalGroups.cpp +
87.0%87.0%
+
87.0 %20 / 2350.0 %1 / 2
testInteraction.cpp +
94.4%94.4%
+
94.4 %743 / 78798.1 %52 / 53
testMagneticField.cpp +
100.0%
+
100.0 %138 / 138100.0 %16 / 16
testMagneticLens.cpp +
100.0%
+
100.0 %87 / 87100.0 %7 / 7
testModuleList.cpp +
94.5%94.5%
+
94.5 %52 / 5585.7 %6 / 7
testOutput.cpp +
96.9%96.9%
+
96.9 %157 / 16294.4 %17 / 18
testPropagation.cpp +
99.1%99.1%
+
99.1 %337 / 34094.7 %18 / 19
testSource.cpp +
98.6%98.6%
+
98.6 %279 / 28395.8 %23 / 24
testTurbulentField.cpp +
100.0%
+
100.0 %46 / 46100.0 %8 / 8
testVector3.cpp +
96.8%96.8%
+
96.8 %90 / 9392.3 %12 / 13
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html b/doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html new file mode 100644 index 000000000..32530ff4f --- /dev/null +++ b/doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testAdiabaticCooling.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testAdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2323100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa34AdiabaticCooling_UniformField_Test8TestBodyEv1
_ZN7crpropa44AdiabaticCooling_ConstantSphericalField_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testAdiabaticCooling.cpp.func.html b/doc/coverageReport/test/testAdiabaticCooling.cpp.func.html new file mode 100644 index 000000000..2bf778f01 --- /dev/null +++ b/doc/coverageReport/test/testAdiabaticCooling.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testAdiabaticCooling.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testAdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2323100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa34AdiabaticCooling_UniformField_Test8TestBodyEv1
_ZN7crpropa44AdiabaticCooling_ConstantSphericalField_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html b/doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html new file mode 100644 index 000000000..6953c46a9 --- /dev/null +++ b/doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html @@ -0,0 +1,131 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testAdiabaticCooling.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testAdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2323100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Candidate.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/advectionField/AdvectionField.h"
+       5             : #include "crpropa/module/AdiabaticCooling.h"
+       6             : #include "gtest/gtest.h"
+       7             : 
+       8             : //#include <fstream>
+       9             : 
+      10             : namespace crpropa {
+      11             : 
+      12             : // AdiabaticCooling ---------------------------------------------------------------
+      13             : 
+      14           2 : TEST (AdiabaticCooling, UniformField) {
+      15             :         // Test in a uniform advection Field
+      16             : 
+      17           2 :         AdiabaticCooling AC(new UniformAdvectionField(Vector3d(1,0,0)));
+      18           1 :         Candidate c(nucleusId(1,1), 1e13*eV);
+      19           1 :         c.setCurrentStep(10*kpc);
+      20           1 :         c.setNextStep(10*kpc);
+      21           1 :         double E = c.current.getEnergy();
+      22           1 :         AC.process(&c);
+      23             : 
+      24             :         // Energy is expected to be conserved
+      25           1 :         EXPECT_DOUBLE_EQ(c.current.getEnergy(), E);
+      26           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 10*kpc);
+      27             : 
+      28             :         double limit = 0.2;
+      29           3 :         AdiabaticCooling AC2(new UniformAdvectionField(Vector3d(1,0,0)), limit);
+      30             :         
+      31           1 :         EXPECT_DOUBLE_EQ(AC2.getLimit(), limit);
+      32             : 
+      33             :         //
+      34             : 
+      35           1 : }
+      36             : 
+      37           2 : TEST (AdiabaticCooling, ConstantSphericalField) {
+      38             :         // Constant velocity vector
+      39             :         
+      40           2 :         AdiabaticCooling AC(new ConstantSphericalAdvectionField(Vector3d(0,0,0), 1));
+      41           1 :         Candidate c(nucleusId(1,1), 10);
+      42           1 :         c.current.setPosition(Vector3d(1,0,0));
+      43           1 :         c.setCurrentStep(c_light);
+      44           1 :         c.setNextStep(c_light);
+      45           1 :         double E = c.current.getEnergy();
+      46           1 :         AC.process(&c);
+      47             : 
+      48             :         // Check energy loss and step limitation
+      49           1 :         EXPECT_DOUBLE_EQ(c.current.getEnergy(), E/3.);
+      50           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 0.15*c_light);
+      51             : 
+      52           1 : }
+      53             : 
+      54             : 
+      55             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html b/doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html new file mode 100644 index 000000000..f4debdd54 --- /dev/null +++ b/doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testAdvectionField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testAdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8383100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testAdvectionFieldList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa41testUniformAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionShock_SimpleTest_Test8TestBodyEv1
_ZN7crpropa51testConstantSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testAdvectionField.cpp.func.html b/doc/coverageReport/test/testAdvectionField.cpp.func.html new file mode 100644 index 000000000..c24ce98a8 --- /dev/null +++ b/doc/coverageReport/test/testAdvectionField.cpp.func.html @@ -0,0 +1,92 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testAdvectionField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testAdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8383100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testAdvectionFieldList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa41testUniformAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionShock_SimpleTest_Test8TestBodyEv1
_ZN7crpropa51testConstantSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testAdvectionField.cpp.gcov.html b/doc/coverageReport/test/testAdvectionField.cpp.gcov.html new file mode 100644 index 000000000..e0ac90041 --- /dev/null +++ b/doc/coverageReport/test/testAdvectionField.cpp.gcov.html @@ -0,0 +1,245 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testAdvectionField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testAdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8383100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/advectionField/AdvectionField.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/Common.h"
+       4             : 
+       5             : #include "gtest/gtest.h"
+       6             : #include <stdexcept>
+       7             : #include <cmath>
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11           2 : TEST(testUniformAdvectionField, SimpleTest) {
+      12           1 :         UniformAdvectionField A(Vector3d(-1, 5, 3));
+      13           1 :         Vector3d a = A.getField(Vector3d(1, 0, 0));
+      14           1 :         double D = A.getDivergence(Vector3d(1, 0, 0));
+      15           1 :         EXPECT_DOUBLE_EQ(a.x, -1);
+      16           1 :         EXPECT_DOUBLE_EQ(a.y, 5);
+      17           1 :         EXPECT_DOUBLE_EQ(a.z, 3);
+      18           1 :         EXPECT_DOUBLE_EQ(D, 0.);
+      19           1 : }
+      20             : 
+      21           2 : TEST(testAdvectionFieldList, SimpleTest) {
+      22             :         // Test a list of three advection fields
+      23             :         AdvectionFieldList A;
+      24           2 :         A.addField(new UniformAdvectionField(Vector3d(1, 0, 0)));
+      25           2 :         A.addField(new UniformAdvectionField(Vector3d(0, 2, 0)));
+      26           2 :         A.addField(new UniformAdvectionField(Vector3d(0, 0, 3)));
+      27           1 :         Vector3d a = A.getField(Vector3d(0.));
+      28           1 :         double D = A.getDivergence(Vector3d(1, 2, 3));
+      29           1 :         EXPECT_DOUBLE_EQ(a.x, 1);
+      30           1 :         EXPECT_DOUBLE_EQ(a.y, 2);
+      31           1 :         EXPECT_DOUBLE_EQ(a.z, 3);
+      32           1 :         EXPECT_DOUBLE_EQ(D, 0.);
+      33           1 : }
+      34             : 
+      35           2 : TEST(testConstantSphericalAdvectionField, SimpleTest) {
+      36             :         
+      37             :         Vector3d origin(1, 0, 0);
+      38             :         double V_wind(10);
+      39             :         
+      40           1 :         ConstantSphericalAdvectionField A(origin, V_wind);
+      41             :         
+      42             :         // Check the properties of the advection field
+      43           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().x, origin.x);
+      44           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().y, origin.y);
+      45           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().z, origin.z);
+      46             : 
+      47           1 :         EXPECT_DOUBLE_EQ(A.getVWind(), V_wind);
+      48             : 
+      49             :         // Field should be radial with center (1,0,0)
+      50             :         Vector3d Pos(2, 1, 1);
+      51           1 :         Vector3d V = A.getField(Pos);
+      52             : 
+      53           1 :         EXPECT_DOUBLE_EQ(V.x, 10.*pow(3, -0.5));
+      54           1 :         EXPECT_DOUBLE_EQ(V.y, 10.*pow(3, -0.5));
+      55           1 :         EXPECT_DOUBLE_EQ(V.z, 10.*pow(3, -0.5));
+      56             :         
+      57             :         // Divergence should be 2*V/r
+      58             :         Vector3d Pos2(2, 0, 0);
+      59           1 :         double D = A.getDivergence(Pos2);
+      60           1 :         EXPECT_DOUBLE_EQ(D, 2*10);
+      61           1 : }
+      62             : 
+      63           2 : TEST(testSphericalAdvectionField, SimpleTest) {
+      64             : 
+      65             :         Vector3d origin(1, 0, 0);
+      66             :         double R_max(10);
+      67             :         double V_max(1000);
+      68             :         double tau(3.);
+      69             :         double alpha(2.);
+      70             : 
+      71           1 :         SphericalAdvectionField A(origin, R_max, V_max, tau, alpha);
+      72             : 
+      73             :         // Check the properties of the advection field
+      74           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().x, origin.x);
+      75           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().y, origin.y);
+      76           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().z, origin.z);
+      77             :         
+      78           1 :         EXPECT_DOUBLE_EQ(A.getRadius(), R_max);
+      79           1 :         EXPECT_DOUBLE_EQ(A.getVMax(), V_max);
+      80           1 :         EXPECT_DOUBLE_EQ(A.getTau(), tau);
+      81           1 :         EXPECT_DOUBLE_EQ(A.getAlpha(), alpha);
+      82             : 
+      83             :         // Field/divergence should be zero for R>10
+      84           1 :         EXPECT_DOUBLE_EQ(A.getField(Vector3d(12,0,0)).getR(), 0.);
+      85           1 :         EXPECT_DOUBLE_EQ(A.getDivergence(Vector3d(12,0,0)), 0.);
+      86             : 
+      87             :         // Check field and divergence
+      88             :         Vector3d Pos(2, 0, 0);
+      89           1 :         Vector3d a = A.getField(Pos);
+      90           1 :         Vector3d a0 = a.getUnitVector();
+      91           1 :         double d = A.getDivergence(Pos);
+      92             : 
+      93           1 :         EXPECT_DOUBLE_EQ(a0.x, 1.);
+      94           1 :         EXPECT_DOUBLE_EQ(a0.y, 0.);
+      95           1 :         EXPECT_DOUBLE_EQ(a0.z, 0.);
+      96           1 :         EXPECT_DOUBLE_EQ(a.getR(), V_max*(1.-exp(-1./tau)) );
+      97             : 
+      98           1 :         EXPECT_NEAR(d, 1044.624919, 1e-5);
+      99             : 
+     100             :         // Check asymptotic of the Field
+     101           1 :         EXPECT_NEAR(A.getField(Vector3d(11, 0, 0)).getR(), 1000., 1e-4);
+     102             :         
+     103             :         // Divergence should be 2*V_max/r for r>>1
+     104           1 :         EXPECT_NEAR(A.getDivergence(Vector3d(11, 0, 0)), 2*1000./10., 1e-4);
+     105           1 : }
+     106             : 
+     107             : 
+     108           2 : TEST(testSphericalAdvectionShock, SimpleTest) {
+     109             : 
+     110             :         Vector3d origin(0, 0, 0);
+     111             :         double R_0(10);
+     112             :         double V_0(1000);
+     113             :         double lambda(0.1);
+     114             :         double R_rot(1.);
+     115             :         double V_rot(100);
+     116             :         
+     117             : 
+     118           1 :         SphericalAdvectionShock A(origin, R_0, V_0, lambda);
+     119             : 
+     120             :         // Check the properties of the advection field
+     121           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().x, origin.x);
+     122           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().y, origin.y);
+     123           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().z, origin.z);
+     124             :         
+     125           1 :         EXPECT_DOUBLE_EQ(A.getR0(), R_0);
+     126           1 :         EXPECT_DOUBLE_EQ(A.getV0(), V_0);
+     127           1 :         EXPECT_DOUBLE_EQ(A.getLambda(), lambda);
+     128             : 
+     129             :         // Default values for R_Rot is R_0
+     130             :         // Default value for Azimuthal speed is 0
+     131           1 :         EXPECT_DOUBLE_EQ(A.getRRot(), R_0);
+     132           1 :         EXPECT_DOUBLE_EQ(A.getAzimuthalSpeed(), 0.);    
+     133             : 
+     134             :         // Field should drop to 0.625*V_0 at the shock 
+     135             :         // That's a difference to the analytic shock model where it should
+     136             :         // drop to v_r(R_0)=0.25*V_0.
+     137           1 :         EXPECT_DOUBLE_EQ(A.getField(Vector3d(R_0,0,0)).getR(), 0.625*V_0);
+     138             : 
+     139             :         // Field divergence should be zero for R>>R_0
+     140           1 :         EXPECT_NEAR(A.getDivergence(Vector3d(15,0,0)), 0., 1e-10);
+     141             : 
+     142             :         // Check field and divergence
+     143             :         Vector3d Pos(2, 0, 0);
+     144           1 :         Vector3d a = A.getField(Pos);
+     145           1 :         Vector3d a0 = a.getUnitVector();
+     146           1 :         double d = A.getDivergence(Pos);
+     147             : 
+     148           1 :         EXPECT_DOUBLE_EQ(a0.x, 1.);
+     149           1 :         EXPECT_DOUBLE_EQ(a0.y, 0.);
+     150           1 :         EXPECT_DOUBLE_EQ(a0.z, 0.);
+     151           1 :         EXPECT_DOUBLE_EQ(a.getR(), V_0);
+     152             :         
+     153             :         //Set explicitely the azimuthal rotation speed 
+     154           1 :         A.setRRot(R_rot);
+     155           1 :         A.setAzimuthalSpeed(V_rot);
+     156             :         
+     157           1 :         EXPECT_DOUBLE_EQ(A.getRRot(), R_rot);
+     158           1 :         EXPECT_DOUBLE_EQ(A.getAzimuthalSpeed(), V_rot); 
+     159             :         
+     160             :         Vector3d pos(1., 0., 0.);
+     161           1 :         Vector3d f = A.getField(pos);
+     162           1 :         EXPECT_DOUBLE_EQ(f.x, 1000.);
+     163           1 :         EXPECT_DOUBLE_EQ(f.y, 100.);
+     164           1 :         EXPECT_DOUBLE_EQ(f.z, 0.);      
+     165             : 
+     166             :         
+     167           1 : }
+     168             : 
+     169             : } //namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html b/doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html new file mode 100644 index 000000000..fdc048a9d --- /dev/null +++ b/doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html @@ -0,0 +1,196 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testBreakCondition.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testBreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:39840199.3 %
Date:2024-04-08 14:58:22Functions:303196.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa20PeriodicBox_low_Test8TestBodyEv1
_ZN7crpropa21PeriodicBox_high_Test8TestBodyEv1
_ZN7crpropa23MinimumEnergy_test_Test8TestBodyEv1
_ZN7crpropa23ReflectiveBox_high_Test8TestBodyEv1
_ZN7crpropa25CubicBoundary_inside_Test8TestBodyEv1
_ZN7crpropa25DetectionLength_test_Test8TestBodyEv1
_ZN7crpropa25MinimumRedshift_test_Test8TestBodyEv1
_ZN7crpropa26CubicBoundary_outside_Test8TestBodyEv1
_ZN7crpropa26ObserverFeature_Point_Test8TestBodyEv1
_ZN7crpropa29MinimumChargeNumber_test_Test8TestBodyEv1
_ZN7crpropa29SphericalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa30ObserverFeature_DetectAll_Test8TestBodyEv1
_ZN7crpropa30SphericalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa31CylindricalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa31EllipsoidalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa32CylindricalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32EllipsoidalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_LargeSphere_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_SmallSphere_Test8TestBodyEv1
_ZN7crpropa32SphericalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepLower_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepUpper_Test8TestBodyEv1
_ZN7crpropa33MaximumTrajectoryLength_test_Test8TestBodyEv1
_ZN7crpropa34CylindricalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34EllipsoidalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34ObserverFeature_TimeEvolution_Test8TestBodyEv1
_ZN7crpropa36MinimumEnergyPerParticleId_test_Test8TestBodyEv1
_ZN7crpropa37MaximumTrajectoryLength_observer_Test8TestBodyEv1
_ZN7crpropa37ObserverFeature_TimeEvolutionLog_Test8TestBodyEv1
_ZN7crpropa38RestrictToRegion_RestrictToRegion_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testBreakCondition.cpp.func.html b/doc/coverageReport/test/testBreakCondition.cpp.func.html new file mode 100644 index 000000000..13dcf1aae --- /dev/null +++ b/doc/coverageReport/test/testBreakCondition.cpp.func.html @@ -0,0 +1,196 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testBreakCondition.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testBreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:39840199.3 %
Date:2024-04-08 14:58:22Functions:303196.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20PeriodicBox_low_Test8TestBodyEv1
_ZN7crpropa21PeriodicBox_high_Test8TestBodyEv1
_ZN7crpropa23MinimumEnergy_test_Test8TestBodyEv1
_ZN7crpropa23ReflectiveBox_high_Test8TestBodyEv1
_ZN7crpropa25CubicBoundary_inside_Test8TestBodyEv1
_ZN7crpropa25DetectionLength_test_Test8TestBodyEv1
_ZN7crpropa25MinimumRedshift_test_Test8TestBodyEv1
_ZN7crpropa26CubicBoundary_outside_Test8TestBodyEv1
_ZN7crpropa26ObserverFeature_Point_Test8TestBodyEv1
_ZN7crpropa29MinimumChargeNumber_test_Test8TestBodyEv1
_ZN7crpropa29SphericalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa30ObserverFeature_DetectAll_Test8TestBodyEv1
_ZN7crpropa30SphericalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa31CylindricalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa31EllipsoidalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa32CylindricalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32EllipsoidalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_LargeSphere_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_SmallSphere_Test8TestBodyEv1
_ZN7crpropa32SphericalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepLower_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepUpper_Test8TestBodyEv1
_ZN7crpropa33MaximumTrajectoryLength_test_Test8TestBodyEv1
_ZN7crpropa34CylindricalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34EllipsoidalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34ObserverFeature_TimeEvolution_Test8TestBodyEv1
_ZN7crpropa36MinimumEnergyPerParticleId_test_Test8TestBodyEv1
_ZN7crpropa37MaximumTrajectoryLength_observer_Test8TestBodyEv1
_ZN7crpropa37ObserverFeature_TimeEvolutionLog_Test8TestBodyEv1
_ZN7crpropa38RestrictToRegion_RestrictToRegion_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testBreakCondition.cpp.gcov.html b/doc/coverageReport/test/testBreakCondition.cpp.gcov.html new file mode 100644 index 000000000..daded67ee --- /dev/null +++ b/doc/coverageReport/test/testBreakCondition.cpp.gcov.html @@ -0,0 +1,621 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testBreakCondition.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testBreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:39840199.3 %
Date:2024-04-08 14:58:22Functions:303196.8 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /** Unit tests for break condition, observer, boundary and tool modules */
+       2             : 
+       3             : #include "crpropa/module/BreakCondition.h"
+       4             : #include "crpropa/module/Observer.h"
+       5             : #include "crpropa/module/Boundary.h"
+       6             : #include "crpropa/module/Tools.h"
+       7             : #include "crpropa/module/RestrictToRegion.h"
+       8             : #include "crpropa/ParticleID.h"
+       9             : #include "crpropa/Geometry.h"
+      10             : 
+      11             : #include "gtest/gtest.h"
+      12             : 
+      13             : namespace crpropa {
+      14             : 
+      15             : //** ========================= Break conditions ============================= */
+      16           1 : TEST(MinimumEnergy, test) {
+      17           1 :         MinimumEnergy minEnergy(5);
+      18           1 :         Candidate c;
+      19             : 
+      20           1 :         c.current.setEnergy(5.1);
+      21           1 :         minEnergy.process(&c);
+      22           1 :         EXPECT_TRUE(c.isActive());
+      23             : 
+      24           1 :         c.current.setEnergy(4.9);
+      25           1 :         minEnergy.process(&c);
+      26           1 :         EXPECT_FALSE(c.isActive());
+      27           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+      28           2 : }
+      29             : 
+      30           1 : TEST(MinimumChargeNumber, test) {
+      31           1 :         MinimumChargeNumber minChargeNumber(20);
+      32           1 :         Candidate c;
+      33             : 
+      34           1 :         c.current.setId(nucleusId(56, 26));
+      35           1 :         minChargeNumber.process(&c);
+      36           1 :         EXPECT_TRUE(c.isActive());
+      37             :         
+      38           1 :         c.current.setId(-nucleusId(56, 26));
+      39           1 :         minChargeNumber.process(&c);
+      40           1 :         EXPECT_TRUE(c.isActive());
+      41             : 
+      42           1 :         c.current.setId(nucleusId(4, 2));
+      43           1 :         minChargeNumber.process(&c);
+      44           1 :         EXPECT_FALSE(c.isActive());
+      45           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+      46             :         
+      47           1 :         c.setActive(true);
+      48           1 :         c.removeProperty("Rejected");
+      49             : 
+      50           1 :         c.current.setId(-nucleusId(4, 2));
+      51           1 :         minChargeNumber.process(&c);
+      52           1 :         EXPECT_FALSE(c.isActive());
+      53           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+      54           2 : }
+      55             : 
+      56           1 : TEST(MinimumEnergyPerParticleId, test) {
+      57           1 :         MinimumEnergyPerParticleId minEnergy(1);
+      58           1 :         minEnergy.add(22, 10);
+      59           1 :         minEnergy.add(12, 2);
+      60           1 :         minEnergy.add(11, 20);
+      61             : 
+      62           1 :         Candidate c;
+      63             : 
+      64           1 :         c.current.setEnergy(20);
+      65           1 :         c.current.setId(22);
+      66           1 :         minEnergy.process(&c);
+      67           1 :         EXPECT_TRUE(c.isActive());
+      68             : 
+      69           1 :         c.current.setEnergy(5);
+      70           1 :         c.current.setId(22);
+      71           1 :         minEnergy.process(&c);
+      72           1 :         EXPECT_FALSE(c.isActive());
+      73           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+      74             : 
+      75           1 :         c.setActive(true);
+      76           1 :         c.removeProperty("Rejected");
+      77             : 
+      78           1 :         c.current.setEnergy(10);
+      79           1 :         c.current.setId(11);
+      80           1 :         minEnergy.process(&c);
+      81           1 :         EXPECT_FALSE(c.isActive());
+      82           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+      83             : 
+      84           1 :         c.setActive(true);
+      85           1 :         c.removeProperty("Rejected");
+      86             : 
+      87           1 :         c.current.setEnergy(5);
+      88           1 :         c.current.setId(12);
+      89           1 :         minEnergy.process(&c);
+      90           1 :         EXPECT_TRUE(c.isActive());      
+      91             : 
+      92           1 :         c.current.setEnergy(0.1);
+      93           1 :         c.current.setId(12);
+      94           1 :         minEnergy.process(&c);
+      95           1 :         EXPECT_FALSE(c.isActive());
+      96           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+      97           1 : }
+      98             : 
+      99           1 : TEST(MaximumTrajectoryLength, test) {
+     100           1 :         MaximumTrajectoryLength maxLength(10);
+     101           1 :         Candidate c;
+     102             : 
+     103           1 :         c.setTrajectoryLength(9.9);
+     104           1 :         maxLength.process(&c);
+     105           1 :         EXPECT_TRUE(c.isActive());
+     106             : 
+     107           1 :         c.setTrajectoryLength(10.1);
+     108           1 :         maxLength.process(&c);
+     109           1 :         EXPECT_FALSE(c.isActive());
+     110           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+     111           1 : }
+     112             : 
+     113           1 : TEST(MaximumTrajectoryLength, observer) {
+     114           1 :         MaximumTrajectoryLength maxLength(12);
+     115           1 :         maxLength.addObserverPosition(Vector3d(10, 0, 0));
+     116           1 :         Candidate c;
+     117           1 :         c.current.setPosition(Vector3d(5, 0, 0));
+     118             : 
+     119           1 :         c.setTrajectoryLength(5);
+     120           1 :         maxLength.process(&c);
+     121           1 :         EXPECT_TRUE(c.isActive());
+     122             : 
+     123           1 :         c.setTrajectoryLength(8);
+     124           1 :         maxLength.process(&c);
+     125           1 :         EXPECT_FALSE(c.isActive());
+     126           1 : }
+     127             : 
+     128           1 : TEST(MinimumRedshift, test) {
+     129           1 :         MinimumRedshift minZ; // default minimum redshift of 0
+     130           1 :         Candidate c;
+     131             : 
+     132           1 :         c.setRedshift(0.1);
+     133           1 :         minZ.process(&c);
+     134           1 :         EXPECT_TRUE(c.isActive());
+     135             : 
+     136           1 :         c.setRedshift(0);
+     137           1 :         minZ.process(&c);
+     138           1 :         EXPECT_FALSE(c.isActive());
+     139           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+     140           2 : }
+     141             : 
+     142           1 : TEST(DetectionLength, test) {
+     143           1 :         DetectionLength detL(10);
+     144           1 :         detL.setMakeRejectedInactive(false);
+     145           1 :         Candidate c;
+     146           1 :         c.current.setPosition(Vector3d(5,0,0));
+     147             : 
+     148           1 :         c.setTrajectoryLength(2);
+     149           1 :         detL.process(&c);
+     150           1 :         EXPECT_TRUE(c.isActive());
+     151             :         
+     152           1 :         c.setCurrentStep(10);
+     153           1 :         c.setTrajectoryLength(12);
+     154           1 :         detL.process(&c);
+     155           1 :         EXPECT_TRUE(c.isActive());
+     156           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+     157           2 : }
+     158             : 
+     159             : //** ============================= Observers ================================ */
+     160           1 : TEST(ObserverFeature, SmallSphere) {
+     161             :         // detect if the current position is inside and the previous outside of the sphere
+     162           1 :         Observer obs;
+     163           1 :         obs.add(new ObserverSurface(new Sphere (Vector3d(0, 0, 0), 1)));
+     164           1 :         Candidate c;
+     165           1 :         c.setNextStep(10);
+     166             : 
+     167             :         // no detection: particle was inside already
+     168           1 :         c.current.setPosition(Vector3d(0.9, 0, 0));
+     169           1 :         c.previous.setPosition(Vector3d(0.95, 0, 0));
+     170           1 :         obs.process(&c);
+     171           1 :         EXPECT_TRUE(c.isActive());
+     172             : 
+     173             :         // limit step
+     174           1 :         EXPECT_NEAR(c.getNextStep(), 0.1, 0.001);
+     175             : 
+     176             :         // detection: particle just entered
+     177           1 :         c.current.setPosition(Vector3d(0.9, 0, 0));
+     178           1 :         c.previous.setPosition(Vector3d(1.1, 0, 0));
+     179           1 :         obs.process(&c);
+     180           1 :         EXPECT_FALSE(c.isActive());
+     181           1 : }
+     182             : 
+     183           1 : TEST(ObserverFeature, LargeSphere) {
+     184             :         // detect if the current position is outside and the previous inside of the sphere
+     185           1 :         Observer obs;
+     186           1 :         obs.add(new ObserverSurface(new Sphere (Vector3d(0, 0, 0), 10)));
+     187           1 :         Candidate c;
+     188           1 :         c.setNextStep(10);
+     189             : 
+     190             :         // no detection: particle was outside already
+     191           1 :         c.current.setPosition(Vector3d(11, 0, 0));
+     192           1 :         c.previous.setPosition(Vector3d(10.5, 0, 0));
+     193           1 :         obs.process(&c);
+     194           1 :         EXPECT_TRUE(c.isActive());
+     195             : 
+     196             :         // limit step
+     197           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 1);
+     198             : 
+     199             :         // detection: particle just left
+     200           1 :         c.current.setPosition(Vector3d(11, 0, 0));
+     201           1 :         c.previous.setPosition(Vector3d(9.5, 0, 0));
+     202           1 :         obs.process(&c);
+     203           1 :         EXPECT_FALSE(c.isActive());
+     204           1 : }
+     205             : 
+     206           1 : TEST(ObserverFeature, Point) {
+     207           1 :         Observer obs;
+     208           1 :         obs.add(new Observer1D());
+     209           1 :         Candidate c;
+     210           1 :         c.setNextStep(10);
+     211             : 
+     212             :         // no detection, limit step
+     213           1 :         c.current.setPosition(Vector3d(5, 0, 0));
+     214           1 :         obs.process(&c);
+     215           1 :         EXPECT_TRUE(c.isActive());
+     216             : 
+     217             :         // limit step
+     218           1 :         EXPECT_DOUBLE_EQ(5, c.getNextStep());
+     219             : 
+     220             :         // detection
+     221           1 :         c.current.setPosition(Vector3d(0, 0, 0));
+     222           1 :         obs.process(&c);
+     223           1 :         EXPECT_FALSE(c.isActive());
+     224           1 : }
+     225             : 
+     226           1 : TEST(ObserverFeature, DetectAll) {
+     227             :         // DetectAll should detect all candidates
+     228           1 :         Observer obs;
+     229           1 :         obs.add(new ObserverDetectAll());
+     230           1 :         Candidate c;
+     231           1 :         obs.process(&c);
+     232           1 :         EXPECT_FALSE(c.isActive());
+     233           1 : }
+     234             : 
+     235           1 : TEST(ObserverFeature, TimeEvolution) {
+     236           1 :   Observer obs;
+     237           1 :   obs.setDeactivateOnDetection(false);
+     238           2 :   obs.setFlag("Detected", "Detected");
+     239           1 :   obs.add(new ObserverTimeEvolution(5, 5, 2));
+     240           1 :   Candidate c;
+     241           1 :   c.setNextStep(10);
+     242           1 :   c.setTrajectoryLength(3);
+     243             :   
+     244             :   // no detection, limit next step
+     245           1 :   obs.process(&c);
+     246           1 :   EXPECT_TRUE(c.isActive());
+     247             : 
+     248             :   // limit step
+     249           1 :   EXPECT_DOUBLE_EQ(2, c.getNextStep());
+     250             :   
+     251             :   // detection one
+     252           1 :   c.setCurrentStep(0.1);
+     253           1 :   c.setTrajectoryLength(5);
+     254           1 :   obs.process(&c);
+     255           1 :   EXPECT_TRUE(c.isActive());
+     256           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
+     257             : 
+     258             :   // delete property
+     259           1 :   c.removeProperty("Detected");
+     260           1 :   EXPECT_FALSE(c.hasProperty("Detected"));
+     261             : 
+     262             :   // detection two
+     263           1 :   c.setCurrentStep(0.1);
+     264           1 :   c.setTrajectoryLength(10.05);
+     265           1 :   obs.process(&c);
+     266           1 :   EXPECT_TRUE(c.isActive());
+     267           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
+     268           1 : }
+     269             : 
+     270           1 : TEST(ObserverFeature, TimeEvolutionLog) {
+     271           1 :   Observer obs;
+     272           1 :   obs.setDeactivateOnDetection(false);
+     273           2 :   obs.setFlag("Detected", "Detected");
+     274             :   // usage of a log scaling for the observer
+     275             :   bool log = true;
+     276           1 :   obs.add(new ObserverTimeEvolution(5, 5, 2, log));
+     277           1 :   Candidate c;
+     278           1 :   c.setNextStep(10);
+     279           1 :   c.setTrajectoryLength(3);
+     280             :   
+     281             :   // no detection, limit next step
+     282           1 :   obs.process(&c);
+     283           1 :   EXPECT_TRUE(c.isActive());
+     284             : 
+     285             :   // limit step
+     286           1 :   EXPECT_DOUBLE_EQ(2, c.getNextStep());
+     287             :   
+     288             :   // detection one
+     289           1 :   c.setCurrentStep(0.1);
+     290           1 :   c.setTrajectoryLength(5);
+     291           1 :   obs.process(&c);
+     292           1 :   EXPECT_TRUE(c.isActive());
+     293           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
+     294             : 
+     295             :   // delete property
+     296           1 :   c.removeProperty("Detected");
+     297           1 :   EXPECT_FALSE(c.hasProperty("Detected"));
+     298             : 
+     299             :   // detection two
+     300           1 :   c.setCurrentStep(0.1);
+     301           1 :   c.setTrajectoryLength(10.05);
+     302           1 :   obs.process(&c);
+     303           1 :   EXPECT_TRUE(c.isActive());
+     304           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
+     305           1 : }
+     306             : 
+     307             : //** ========================= Boundaries =================================== */
+     308           2 : TEST(PeriodicBox, high) {
+     309             :         // Tests if the periodical boundaries place the particle back inside the box and translate the initial position accordingly.
+     310             :         Vector3d origin(2, 2, 2);
+     311             :         Vector3d size(2, 2, 2);
+     312           1 :         PeriodicBox box(origin, size);
+     313             : 
+     314           1 :         Candidate c;
+     315           1 :         c.current.setPosition(Vector3d(4.5, 4.3, 4.4));
+     316           1 :         c.created.setPosition(Vector3d(3, 3, 3));
+     317             : 
+     318           1 :         box.process(&c);
+     319             : 
+     320           1 :         EXPECT_DOUBLE_EQ(2.5, c.current.getPosition().x);
+     321           1 :         EXPECT_DOUBLE_EQ(1, c.created.getPosition().x);
+     322           1 :         EXPECT_DOUBLE_EQ(2.3, c.current.getPosition().y);
+     323           1 :         EXPECT_DOUBLE_EQ(1, c.created.getPosition().y);
+     324           1 :         EXPECT_DOUBLE_EQ(2.4, c.current.getPosition().z);
+     325           1 :         EXPECT_DOUBLE_EQ(1, c.created.getPosition().z);
+     326           2 : }
+     327             : 
+     328           2 : TEST(PeriodicBox, low) {
+     329             :         // Tests if the periodical boundaries place the particle back inside the box and translate the initial position accordingly.
+     330             :         Vector3d origin(0, 0, 0);
+     331             :         Vector3d size(2, 2, 2);
+     332           1 :         PeriodicBox box(origin, size);
+     333             : 
+     334           1 :         Candidate c;
+     335           1 :         c.current.setPosition(Vector3d(-2.5, -0.3, -0.4));
+     336           1 :         c.created.setPosition(Vector3d(1, 1, 1));
+     337             : 
+     338           1 :         box.process(&c);
+     339             : 
+     340           1 :         EXPECT_DOUBLE_EQ(1.5, c.current.getPosition().x);
+     341           1 :         EXPECT_DOUBLE_EQ(5, c.created.getPosition().x);
+     342           1 :         EXPECT_DOUBLE_EQ(1.7, c.current.getPosition().y);
+     343           1 :         EXPECT_DOUBLE_EQ(3, c.created.getPosition().y);
+     344           1 :         EXPECT_DOUBLE_EQ(1.6, c.current.getPosition().z);
+     345           1 :         EXPECT_DOUBLE_EQ(3, c.created.getPosition().z);
+     346           2 : }
+     347             : 
+     348           2 : TEST(ReflectiveBox, high) {
+     349             :         // Tests if the reflective boundaries place the particle back inside the box and translate the initial position accordingly.
+     350             :         // Also the initial and final directions are to be reflected
+     351             :         Vector3d origin(10, 10, 10);
+     352             :         Vector3d size(10, 20, 20);
+     353           1 :         ReflectiveBox box(origin, size);
+     354             : 
+     355           1 :         Candidate c;
+     356           1 :         c.source.setPosition(Vector3d(16, 17, 18));
+     357           1 :         c.source.setDirection(Vector3d(1, 1.6, 1.8));
+     358           1 :         c.created.setPosition(Vector3d(15, 15, 15));
+     359           1 :         c.created.setDirection(Vector3d(0, 0.6, 0.8));
+     360           1 :         c.previous.setPosition(Vector3d(15, 15, 29.5));
+     361           1 :         c.previous.setDirection(Vector3d(0, 0.6, 0.8));
+     362           1 :         c.current.setPosition(Vector3d(15, 15, 30.5));
+     363           1 :         c.current.setDirection(Vector3d(0, 0.6, 0.8));
+     364             : 
+     365           1 :         box.process(&c);
+     366             : 
+     367           1 :         EXPECT_DOUBLE_EQ(16, c.source.getPosition().x);
+     368           1 :         EXPECT_DOUBLE_EQ(17, c.source.getPosition().y);
+     369           1 :         EXPECT_DOUBLE_EQ(42, c.source.getPosition().z);
+     370             : 
+     371           1 :         EXPECT_DOUBLE_EQ(15, c.created.getPosition().x);
+     372           1 :         EXPECT_DOUBLE_EQ(15, c.created.getPosition().y);
+     373           1 :         EXPECT_DOUBLE_EQ(45, c.created.getPosition().z);
+     374             : 
+     375           1 :         EXPECT_DOUBLE_EQ(15, c.previous.getPosition().x);
+     376           1 :         EXPECT_DOUBLE_EQ(15, c.previous.getPosition().y);
+     377           1 :         EXPECT_DOUBLE_EQ(30.5, c.previous.getPosition().z);
+     378             : 
+     379           1 :         EXPECT_DOUBLE_EQ(15, c.current.getPosition().x);
+     380           1 :         EXPECT_DOUBLE_EQ(15, c.current.getPosition().y);
+     381           1 :         EXPECT_DOUBLE_EQ(29.5, c.current.getPosition().z);
+     382             : 
+     383           1 :         EXPECT_DOUBLE_EQ(0, c.created.getDirection().x);
+     384           1 :         EXPECT_DOUBLE_EQ(0.6, c.created.getDirection().y);
+     385           1 :         EXPECT_DOUBLE_EQ(-0.8, c.created.getDirection().z);
+     386             : 
+     387           1 :         EXPECT_DOUBLE_EQ(0, c.previous.getDirection().x);
+     388           1 :         EXPECT_DOUBLE_EQ(0.6, c.previous.getDirection().y);
+     389           1 :         EXPECT_DOUBLE_EQ(-0.8, c.previous.getDirection().z);
+     390             : 
+     391           1 :         EXPECT_DOUBLE_EQ(0, c.current.getDirection().x);
+     392           1 :         EXPECT_DOUBLE_EQ(0.6, c.current.getDirection().y);
+     393           1 :         EXPECT_DOUBLE_EQ(-0.8, c.current.getDirection().z);
+     394           2 : }
+     395             : 
+     396           2 : TEST(CubicBoundary, inside) {
+     397           1 :         CubicBoundary cube(Vector3d(0, 0, 0), 10);
+     398           1 :         Candidate c;
+     399           1 :         c.current.setPosition(Vector3d(9, 5, 5));
+     400           1 :         cube.process(&c);
+     401           1 :         EXPECT_TRUE(c.isActive());
+     402           2 : }
+     403             : 
+     404           2 : TEST(CubicBoundary, outside) {
+     405           1 :         CubicBoundary cube(Vector3d(0, 0, 0), 10);
+     406           1 :         Candidate c;
+     407           1 :         c.current.setPosition(Vector3d(10.1, 5, 5));
+     408           1 :         cube.process(&c);
+     409           1 :         EXPECT_FALSE(c.isActive());
+     410           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+     411           2 : }
+     412             : 
+     413           2 : TEST(CubicBoundary, limitStepLower) {
+     414           1 :         CubicBoundary cube(Vector3d(10, 10, 10), 10);
+     415           1 :         cube.setLimitStep(true);
+     416           1 :         cube.setMargin(1);
+     417           1 :         Candidate c;
+     418           1 :         c.current.setPosition(Vector3d(15, 15, 10.5));
+     419           1 :         c.setNextStep(100);
+     420           1 :         cube.process(&c);
+     421           1 :         EXPECT_DOUBLE_EQ(1.5, c.getNextStep());
+     422           2 : }
+     423             : 
+     424           2 : TEST(CubicBoundary, limitStepUpper) {
+     425           1 :         CubicBoundary cube(Vector3d(-10, -10, -10), 10);
+     426           1 :         cube.setLimitStep(true);
+     427           1 :         cube.setMargin(1);
+     428           1 :         Candidate c;
+     429           1 :         c.current.setPosition(Vector3d(-5, -5, -0.5));
+     430           1 :         c.setNextStep(100);
+     431           1 :         cube.process(&c);
+     432           1 :         EXPECT_DOUBLE_EQ(1.5, c.getNextStep());
+     433           2 : }
+     434             : 
+     435           2 : TEST(SphericalBoundary, inside) {
+     436           1 :         SphericalBoundary sphere(Vector3d(0, 0, 0), 10);
+     437           1 :         Candidate c;
+     438           1 :         c.current.setPosition(Vector3d(9, 0, 0));
+     439           1 :         sphere.process(&c);
+     440           1 :         EXPECT_TRUE(c.isActive());
+     441           1 :         EXPECT_FALSE(c.hasProperty("Rejected"));
+     442           2 : }
+     443             : 
+     444           2 : TEST(SphericalBoundary, outside) {
+     445           1 :         SphericalBoundary sphere(Vector3d(0, 0, 0), 10);
+     446           2 :         sphere.setRejectFlag("I passed the galactic border", "Nothing happened");
+     447           1 :         Candidate c;
+     448           1 :         c.current.setPosition(Vector3d(0, -10.1, 0));
+     449           1 :         sphere.process(&c);
+     450           1 :         EXPECT_FALSE(c.isActive());
+     451           2 :         EXPECT_TRUE(c.hasProperty("I passed the galactic border"));
+     452           2 : }
+     453             : 
+     454           2 : TEST(SphericalBoundary, limitStep) {
+     455           1 :         SphericalBoundary sphere(Vector3d(0, 0, 0), 10);
+     456           1 :         sphere.setLimitStep(true);
+     457           1 :         sphere.setMargin(1);
+     458           1 :         Candidate c;
+     459           1 :         c.setNextStep(100);
+     460           1 :         c.current.setPosition(Vector3d(0, 0, 9.5));
+     461           1 :         sphere.process(&c);
+     462           1 :         EXPECT_DOUBLE_EQ(1.5, c.getNextStep());
+     463           2 : }
+     464             : 
+     465           2 : TEST(EllipsoidalBoundary, inside) {
+     466           1 :         EllipsoidalBoundary ellipsoid(Vector3d(-5, 0, 0), Vector3d(5, 0, 0), 15);
+     467           1 :         Candidate c;
+     468           1 :         c.current.setPosition(Vector3d(3, 2, 0));
+     469           1 :         ellipsoid.process(&c);
+     470           1 :         EXPECT_TRUE(c.isActive());
+     471           1 :         EXPECT_FALSE(c.hasProperty("Rejected"));
+     472           2 : }
+     473             : 
+     474           2 : TEST(EllipsoidalBoundary, outside) {
+     475           1 :         EllipsoidalBoundary ellipsoid(Vector3d(-5, 0, 0), Vector3d(5, 0, 0), 15);
+     476           1 :         Candidate c;
+     477           1 :         c.current.setPosition(Vector3d(0, 25, 0));
+     478           1 :         ellipsoid.process(&c);
+     479           1 :         EXPECT_FALSE(c.isActive());
+     480           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+     481           2 : }
+     482             : 
+     483           2 : TEST(EllipsoidalBoundary, limitStep) {
+     484           1 :         EllipsoidalBoundary ellipsoid(Vector3d(-5, 0, 0), Vector3d(5, 0, 0), 15);
+     485           1 :         ellipsoid.setLimitStep(true);
+     486           1 :         ellipsoid.setMargin(0.5);
+     487           1 :         Candidate c;
+     488           1 :         c.setNextStep(2);
+     489           1 :         c.current.setPosition(Vector3d(7, 0, 0));
+     490           1 :         ellipsoid.process(&c);
+     491           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 1.5);
+     492           2 : }
+     493             : 
+     494           2 : TEST(CylindricalBoundary, inside) {
+     495           1 :         CylindricalBoundary cylinder(Vector3d(0, 0, 0), 2, 15);
+     496           1 :         Candidate c;
+     497           1 :         c.current.setPosition(Vector3d(6, -3, 0.5));
+     498           1 :         cylinder.process(&c);
+     499           1 :         EXPECT_TRUE(c.isActive());
+     500           1 :         EXPECT_FALSE(c.hasProperty("Rejected"));
+     501           2 : }
+     502             : 
+     503           2 : TEST(CylindricalBoundary, outside) {
+     504           1 :         CylindricalBoundary cylinder(Vector3d(0, 0, 0), 2, 15);
+     505           1 :         Candidate c;
+     506           1 :         c.current.setPosition(Vector3d(6, -3, 1.5));
+     507           1 :         cylinder.process(&c);
+     508           1 :         EXPECT_FALSE(c.isActive());
+     509           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
+     510           2 : }
+     511             : 
+     512           2 : TEST(CylindricalBoundary, limitStep) {
+     513           1 :         CylindricalBoundary cylinder(Vector3d(0, 0, 0), 2, 15);
+     514           1 :         cylinder.setLimitStep(true);
+     515           1 :         cylinder.setMargin(0.5);
+     516           1 :         Candidate c;
+     517           1 :         c.setNextStep(2);
+     518           1 :         c.current.setPosition(Vector3d(7, 0, 0));
+     519           1 :         cylinder.process(&c);
+     520           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 1.5);
+     521           2 : }
+     522             : 
+     523           1 : TEST(RestrictToRegion, RestrictToRegion) {
+     524             : 
+     525           1 :         ref_ptr<Observer> obs = new Observer();
+     526           1 :         obs->add(new ObserverDetectAll());
+     527           1 :         RestrictToRegion R(obs, new Sphere(Vector3d(0, 0, 0), 10));
+     528             : 
+     529           1 :         Candidate c;
+     530           1 :         c.previous.setPosition(Vector3d(13,0,0));
+     531           1 :         c.current.setPosition(Vector3d(12,0,0));
+     532           1 :         R.process(&c);
+     533           1 :         EXPECT_TRUE(c.isActive());
+     534           1 :         c.current.setPosition(Vector3d(9,0,0));
+     535           1 :         R.process(&c);
+     536           1 :         EXPECT_FALSE(c.isActive());
+     537           2 : }
+     538             : 
+     539             : 
+     540           0 : int main(int argc, char **argv) {
+     541           0 :         ::testing::InitGoogleTest(&argc, argv);
+     542           0 :         return RUN_ALL_TESTS();
+     543             : }
+     544             : 
+     545             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html b/doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html new file mode 100644 index 000000000..fd272427c --- /dev/null +++ b/doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testCandidateSplitting.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testCandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4747100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testCandidateSplitting_SimpleTest_Test8TestBodyEv1
_ZN7crpropa39testCandidateSplitting_CheckSplits_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testCandidateSplitting.cpp.func.html b/doc/coverageReport/test/testCandidateSplitting.cpp.func.html new file mode 100644 index 000000000..5940d2ea4 --- /dev/null +++ b/doc/coverageReport/test/testCandidateSplitting.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testCandidateSplitting.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testCandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4747100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testCandidateSplitting_SimpleTest_Test8TestBodyEv1
_ZN7crpropa39testCandidateSplitting_CheckSplits_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html b/doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html new file mode 100644 index 000000000..7f7795772 --- /dev/null +++ b/doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html @@ -0,0 +1,166 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testCandidateSplitting.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testCandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4747100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Units.h"
+       2             : #include "crpropa/Common.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/module/CandidateSplitting.h"
+       5             : 
+       6             : #include "gtest/gtest.h"
+       7             : #include <stdexcept>
+       8             : #include <cmath>
+       9             : 
+      10             : namespace crpropa {
+      11             : 
+      12           1 : TEST(testCandidateSplitting, SimpleTest) {
+      13           1 :         int nSplit = 2;
+      14             :         int nBins = 4;
+      15             :         double minWeight = pow(1. / nSplit, 2);
+      16             :         double Emin = 1; // dimensionless for testing
+      17             :         double Emax = 10;       
+      18             : 
+      19           1 :         CandidateSplitting split_lin(nSplit, Emin, Emax, nBins, minWeight);
+      20             :         double dE = (Emax - Emin) / nBins;
+      21           1 :         EXPECT_DOUBLE_EQ(split_lin.getEnergyBins()[0], Emin);
+      22           1 :         EXPECT_DOUBLE_EQ(split_lin.getEnergyBins()[1], Emin + dE);
+      23             : 
+      24           1 :         EXPECT_EQ(split_lin.getNsplit(), nSplit);
+      25           1 :         EXPECT_DOUBLE_EQ(split_lin.getMinimalWeight(), minWeight);
+      26             : 
+      27           2 :         CandidateSplitting split_log(nSplit, Emin, Emax, nBins, minWeight, true);
+      28             :         double dE_log = pow(Emax / Emin, 1. / (nBins - 1.0));
+      29           1 :         EXPECT_DOUBLE_EQ(split_log.getEnergyBins()[0], Emin);
+      30           1 :         EXPECT_DOUBLE_EQ(split_log.getEnergyBins()[1], Emin * dE_log);
+      31             : 
+      32             :         double spectralIndex = -2.;
+      33           2 :         CandidateSplitting split_dsa(spectralIndex, Emin, nBins);
+      34             :         double dE_dsa = pow(1. / 2, 1. / (spectralIndex + 1));
+      35           1 :         EXPECT_DOUBLE_EQ(split_dsa.getEnergyBins()[0], Emin * dE_dsa);
+      36           1 :         EXPECT_DOUBLE_EQ(split_dsa.getEnergyBins()[nBins - 1], Emin * pow(dE_dsa, nBins));
+      37           1 : }
+      38             : 
+      39             : 
+      40           1 : TEST(testCandidateSplitting, CheckSplits) {
+      41             :         int nSplit = 2;
+      42             :         int nBins = 3;
+      43             :         double Emin = 1; // dimensionless for testing
+      44             :         double Emax = 10;
+      45             :         double minWeight = pow(1. / nSplit, 4);
+      46             : 
+      47           1 :         CandidateSplitting splitting(nSplit, Emin, Emax, nBins, minWeight);
+      48           1 :         Candidate c(nucleusId(1,1),0.5);
+      49             :         double weight = 1.0;
+      50           1 :         double serial = c.getSerialNumber();
+      51             :         
+      52           1 :         splitting.process(&c); // no split
+      53           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
+      54           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial);
+      55             : 
+      56           1 :         c.current.setEnergy(2); 
+      57           1 :         splitting.process(&c); // 1. split
+      58             :         weight = weight/nSplit;
+      59           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
+      60           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 1);
+      61           1 :         c.previous.setEnergy(2);
+      62             : 
+      63           1 :         c.current.setEnergy(6); 
+      64           1 :         splitting.process(&c); // 2. split
+      65             :         weight = weight/nSplit;
+      66           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
+      67           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 2);
+      68           1 :         c.previous.setEnergy(6);
+      69             : 
+      70           1 :         c.current.setEnergy(0.5); 
+      71           1 :         splitting.process(&c); // no split, cooling
+      72           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
+      73           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 2);
+      74           1 :         c.previous.setEnergy(0.5);
+      75             : 
+      76           1 :         c.current.setEnergy(6); 
+      77           1 :         splitting.process(&c); // 3. & 4. split, crosses two boundaries
+      78             :         weight = weight/nSplit/nSplit;
+      79           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
+      80           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 4);
+      81           1 :         c.previous.setEnergy(6);
+      82             : 
+      83           1 :         c.current.setEnergy(8); 
+      84           1 :         splitting.process(&c); // no split, minimal weight reached
+      85           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
+      86           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 4);
+      87           1 :         c.previous.setEnergy(8);
+      88           1 : }
+      89             : 
+      90             : } //namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testCore.cpp.func-sort-c.html b/doc/coverageReport/test/testCore.cpp.func-sort-c.html new file mode 100644 index 000000000..d65894f63 --- /dev/null +++ b/doc/coverageReport/test/testCore.cpp.func-sort-c.html @@ -0,0 +1,308 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testCore.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testCore.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:65465799.5 %
Date:2024-04-08 14:58:22Functions:585998.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa16Random_seed_Test8TestBodyEv1
_ZN7crpropa17Grid3f_Speed_Test8TestBodyEv1
_ZN7crpropa17common_digit_Test8TestBodyEv1
_ZN7crpropa18HepPID_charge_Test8TestBodyEv1
_ZN7crpropa19Geometry_Plane_Test8TestBodyEv1
_ZN7crpropa20Geometry_Sphere_Test8TestBodyEv1
_ZN7crpropa20Grid3f_DumpLoad_Test8TestBodyEv1
_ZN7crpropa20common_gaussInt_Test8TestBodyEv1
_ZN7crpropa21Candidate_weight_Test8TestBodyEv1
_ZN7crpropa21ParticleState_id_Test8TestBodyEv1
_ZN7crpropa22EmissionMap_merge_Test8TestBodyEv1
_ZN7crpropa22Grid1f_SimpleTest_Test8TestBodyEv1
_ZN7crpropa22Grid1f_clipVolume_Test8TestBodyEv1
_ZN7crpropa22Random_base64Seed_Test8TestBodyEv1
_ZN7crpropa22VectordGrid_Scale_Test8TestBodyEv1
_ZN7crpropa23Candidate_isActive_Test8TestBodyEv1
_ZN7crpropa23Candidate_property_Test8TestBodyEv1
_ZN7crpropa23Grid3f_DumpLoadTxt_Test8TestBodyEv1
_ZN7crpropa23Grid3f_Periodicity_Test8TestBodyEv1
_ZN7crpropa23Grid_PeriodicClamp_Test8TestBodyEv1
_ZN7crpropa23ParticleState_Mass_Test8TestBodyEv1
_ZN7crpropa23common_interpolate_Test8TestBodyEv1
_ZN7crpropa23common_pow_integer_Test8TestBodyEv1
_ZN7crpropa24Grid1f_ClosestValue_Test8TestBodyEv1
_ZN7crpropa24Grid3f_Reflectivity_Test8TestBodyEv1
_ZN7crpropa24base64_de_en_coding_Test8TestBodyEv1
_ZN7crpropa25Geometry_ParaxialBox_Test8TestBodyEv1
_ZN7crpropa25Grid3f_Interpolation_Test8TestBodyEv1
_ZN7crpropa25Grid_ReflectiveClamp_Test8TestBodyEv1
_ZN7crpropa25ParticleID_isNucleus_Test8TestBodyEv1
_ZN7crpropa25ParticleID_nucleusId_Test8TestBodyEv1
_ZN7crpropa25ParticleState_Charge_Test8TestBodyEv1
_ZN7crpropa25ParticleState_energy_Test8TestBodyEv1
_ZN7crpropa25Variant_copyToBuffer_Test8TestBodyEv1
_ZN7crpropa26Candidate_currentStep_Test8TestBodyEv1
_ZN7crpropa26EmissionMap_functions_Test8TestBodyEv1
_ZN7crpropa26Grid_PeriodicBoundary_Test8TestBodyEv1
_ZN7crpropa26ParticleID_massNumber_Test8TestBodyEv1
_ZN7crpropa26Random_bigSeedStorage_Test8TestBodyEv1
_ZN7crpropa27Candidate_addSecondary_Test8TestBodyEv1
_ZN7crpropa27Candidate_candidateTag_Test8TestBodyEv1
_ZN7crpropa27Candidate_serialNumber_Test8TestBodyEv1
_ZN7crpropa27ParticleState_Rigidity_Test8TestBodyEv1
_ZN7crpropa27ParticleState_momentum_Test8TestBodyEv1
_ZN7crpropa27ParticleState_position_Test8TestBodyEv1
_ZN7crpropa27ParticleState_velocity_Test8TestBodyEv1
_ZN7crpropa28Candidate_limitNextStep_Test8TestBodyEv1
_ZN7crpropa28Grid_ReflectiveBoundary_Test8TestBodyEv1
_ZN7crpropa28ParticleID_chargeNumber_Test8TestBodyEv1
_ZN7crpropa28ParticleState_direction_Test8TestBodyEv1
_ZN7crpropa29Grid1f_TestVectorSpacing_Test8TestBodyEv1
_ZN7crpropa29Variant_stringConversion_Test8TestBodyEv1
_ZN7crpropa30ParticleState_idException_Test8TestBodyEv1
_ZN7crpropa32ParticleState_lorentzFactor_Test8TestBodyEv1
_ZN7crpropa34common_interpolateEquidistant_Test8TestBodyEv1
_ZN7crpropa37Grid1f_GridPropertiesConstructor_Test8TestBodyEv1
_ZN7crpropa39CylindricalProjectionMap_functions_Test8TestBodyEv1
_ZN7crpropa50HepPID_consistencyWithReferenceImplementation_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testCore.cpp.func.html b/doc/coverageReport/test/testCore.cpp.func.html new file mode 100644 index 000000000..1336167ed --- /dev/null +++ b/doc/coverageReport/test/testCore.cpp.func.html @@ -0,0 +1,308 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testCore.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testCore.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:65465799.5 %
Date:2024-04-08 14:58:22Functions:585998.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16Random_seed_Test8TestBodyEv1
_ZN7crpropa17Grid3f_Speed_Test8TestBodyEv1
_ZN7crpropa17common_digit_Test8TestBodyEv1
_ZN7crpropa18HepPID_charge_Test8TestBodyEv1
_ZN7crpropa19Geometry_Plane_Test8TestBodyEv1
_ZN7crpropa20Geometry_Sphere_Test8TestBodyEv1
_ZN7crpropa20Grid3f_DumpLoad_Test8TestBodyEv1
_ZN7crpropa20common_gaussInt_Test8TestBodyEv1
_ZN7crpropa21Candidate_weight_Test8TestBodyEv1
_ZN7crpropa21ParticleState_id_Test8TestBodyEv1
_ZN7crpropa22EmissionMap_merge_Test8TestBodyEv1
_ZN7crpropa22Grid1f_SimpleTest_Test8TestBodyEv1
_ZN7crpropa22Grid1f_clipVolume_Test8TestBodyEv1
_ZN7crpropa22Random_base64Seed_Test8TestBodyEv1
_ZN7crpropa22VectordGrid_Scale_Test8TestBodyEv1
_ZN7crpropa23Candidate_isActive_Test8TestBodyEv1
_ZN7crpropa23Candidate_property_Test8TestBodyEv1
_ZN7crpropa23Grid3f_DumpLoadTxt_Test8TestBodyEv1
_ZN7crpropa23Grid3f_Periodicity_Test8TestBodyEv1
_ZN7crpropa23Grid_PeriodicClamp_Test8TestBodyEv1
_ZN7crpropa23ParticleState_Mass_Test8TestBodyEv1
_ZN7crpropa23common_interpolate_Test8TestBodyEv1
_ZN7crpropa23common_pow_integer_Test8TestBodyEv1
_ZN7crpropa24Grid1f_ClosestValue_Test8TestBodyEv1
_ZN7crpropa24Grid3f_Reflectivity_Test8TestBodyEv1
_ZN7crpropa24base64_de_en_coding_Test8TestBodyEv1
_ZN7crpropa25Geometry_ParaxialBox_Test8TestBodyEv1
_ZN7crpropa25Grid3f_Interpolation_Test8TestBodyEv1
_ZN7crpropa25Grid_ReflectiveClamp_Test8TestBodyEv1
_ZN7crpropa25ParticleID_isNucleus_Test8TestBodyEv1
_ZN7crpropa25ParticleID_nucleusId_Test8TestBodyEv1
_ZN7crpropa25ParticleState_Charge_Test8TestBodyEv1
_ZN7crpropa25ParticleState_energy_Test8TestBodyEv1
_ZN7crpropa25Variant_copyToBuffer_Test8TestBodyEv1
_ZN7crpropa26Candidate_currentStep_Test8TestBodyEv1
_ZN7crpropa26EmissionMap_functions_Test8TestBodyEv1
_ZN7crpropa26Grid_PeriodicBoundary_Test8TestBodyEv1
_ZN7crpropa26ParticleID_massNumber_Test8TestBodyEv1
_ZN7crpropa26Random_bigSeedStorage_Test8TestBodyEv1
_ZN7crpropa27Candidate_addSecondary_Test8TestBodyEv1
_ZN7crpropa27Candidate_candidateTag_Test8TestBodyEv1
_ZN7crpropa27Candidate_serialNumber_Test8TestBodyEv1
_ZN7crpropa27ParticleState_Rigidity_Test8TestBodyEv1
_ZN7crpropa27ParticleState_momentum_Test8TestBodyEv1
_ZN7crpropa27ParticleState_position_Test8TestBodyEv1
_ZN7crpropa27ParticleState_velocity_Test8TestBodyEv1
_ZN7crpropa28Candidate_limitNextStep_Test8TestBodyEv1
_ZN7crpropa28Grid_ReflectiveBoundary_Test8TestBodyEv1
_ZN7crpropa28ParticleID_chargeNumber_Test8TestBodyEv1
_ZN7crpropa28ParticleState_direction_Test8TestBodyEv1
_ZN7crpropa29Grid1f_TestVectorSpacing_Test8TestBodyEv1
_ZN7crpropa29Variant_stringConversion_Test8TestBodyEv1
_ZN7crpropa30ParticleState_idException_Test8TestBodyEv1
_ZN7crpropa32ParticleState_lorentzFactor_Test8TestBodyEv1
_ZN7crpropa34common_interpolateEquidistant_Test8TestBodyEv1
_ZN7crpropa37Grid1f_GridPropertiesConstructor_Test8TestBodyEv1
_ZN7crpropa39CylindricalProjectionMap_functions_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
_ZN7crpropa50HepPID_consistencyWithReferenceImplementation_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testCore.cpp.gcov.html b/doc/coverageReport/test/testCore.cpp.gcov.html new file mode 100644 index 000000000..3e1716747 --- /dev/null +++ b/doc/coverageReport/test/testCore.cpp.gcov.html @@ -0,0 +1,1144 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testCore.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testCore.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:65465799.5 %
Date:2024-04-08 14:58:22Functions:585998.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /** Unit tests for core features of CRPropa
+       2             :         Candidate
+       3             :         ParticleState
+       4             :         Random
+       5             :         Common functions
+       6             :  */
+       7             : 
+       8             : #include <complex>
+       9             : 
+      10             : #include "crpropa/Candidate.h"
+      11             : #include "crpropa/base64.h"
+      12             : #include "crpropa/Common.h"
+      13             : #include "crpropa/Units.h"
+      14             : #include "crpropa/ParticleID.h"
+      15             : #include "crpropa/ParticleMass.h"
+      16             : #include "crpropa/Random.h"
+      17             : #include "crpropa/Grid.h"
+      18             : #include "crpropa/GridTools.h"
+      19             : #include "crpropa/Geometry.h"
+      20             : #include "crpropa/EmissionMap.h"
+      21             : #include "crpropa/Vector3.h"
+      22             : 
+      23             : #include <HepPID/ParticleIDMethods.hh>
+      24             : #include "gtest/gtest.h"
+      25             : 
+      26             : namespace crpropa {
+      27             : 
+      28           2 : TEST(ParticleState, position) {
+      29           1 :         ParticleState particle;
+      30             :         Vector3d v(1, 3, 5);
+      31           1 :         particle.setPosition(v * Mpc);
+      32           2 :         EXPECT_TRUE(particle.getPosition() == v * Mpc);
+      33           1 : }
+      34             : 
+      35           2 : TEST(ParticleState, energy) {
+      36           1 :         ParticleState particle;
+      37           1 :         particle.setEnergy(10 * EeV);
+      38           1 :         EXPECT_EQ(particle.getEnergy(), 10 * EeV);
+      39           1 : }
+      40             : 
+      41           2 : TEST(ParticleState, direction) {
+      42           1 :         ParticleState particle;
+      43             :         Vector3d v(1, 2, 3);
+      44           1 :         particle.setDirection(v);
+      45           2 :         EXPECT_TRUE(particle.getDirection() == v.getUnitVector());
+      46           1 : }
+      47             : 
+      48           2 : TEST(ParticleState, velocity) {
+      49           1 :         ParticleState particle;
+      50             :         Vector3d v(1, 1, 0);
+      51           1 :         particle.setDirection(v);
+      52           2 :         EXPECT_TRUE(particle.getVelocity() == v.getUnitVector() * c_light);
+      53           1 : }
+      54             : 
+      55           2 : TEST(ParticleState, momentum) {
+      56           1 :         ParticleState particle;
+      57             :         Vector3d v(0, 1, 0);
+      58           1 :         particle.setDirection(v);
+      59           1 :         particle.setEnergy(100 * EeV);
+      60           2 :         EXPECT_TRUE(particle.getMomentum() == v * (particle.getEnergy() / c_light));
+      61           1 : }
+      62             : 
+      63           2 : TEST(ParticleState, id) {
+      64           1 :         ParticleState particle;
+      65           1 :         particle.setId(nucleusId(12, 6));
+      66           1 :         EXPECT_EQ(particle.getId(), 1000060120);
+      67           1 : }
+      68             : 
+      69             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
+      70           1 : TEST(ParticleState, idException) {
+      71           1 :         EXPECT_THROW(nucleusId(5, 6), std::runtime_error);
+      72           1 : }
+      73             : #endif
+      74             : 
+      75           2 : TEST(ParticleState, Charge) {
+      76           1 :         ParticleState particle;
+      77             : 
+      78           1 :         particle.setId(nucleusId(56, 26)); // iron
+      79           1 :         EXPECT_DOUBLE_EQ(26 * eplus, particle.getCharge());
+      80             : 
+      81           1 :         particle.setId(-nucleusId(56, 26)); // anti-iron
+      82           1 :         EXPECT_DOUBLE_EQ(-26 * eplus, particle.getCharge());
+      83             : 
+      84           1 :         particle.setId(11); // electron
+      85           1 :         EXPECT_DOUBLE_EQ(-1 * eplus, particle.getCharge());
+      86             : 
+      87           1 :         particle.setId(-11); // positron
+      88           1 :         EXPECT_DOUBLE_EQ(1 * eplus, particle.getCharge());
+      89             : 
+      90           1 :         particle.setId(12); // electron neutrino
+      91           1 :         EXPECT_DOUBLE_EQ(0, particle.getCharge());
+      92             : 
+      93           1 :         particle.setId(-12); // electron anti-neutrino
+      94           1 :         EXPECT_DOUBLE_EQ(0, particle.getCharge());
+      95           1 : }
+      96             : 
+      97           2 : TEST(ParticleState, Rigidity) {
+      98           1 :         ParticleState particle;
+      99             : 
+     100           1 :         particle.setId(nucleusId(1, 1)); // proton
+     101           1 :         particle.setEnergy(1 * EeV);
+     102           1 :         EXPECT_EQ(particle.getRigidity(), 1e18);
+     103           1 : }
+     104             : 
+     105           2 : TEST(ParticleState, Mass) {
+     106           1 :         ParticleState particle;
+     107             : 
+     108           1 :         particle.setId(nucleusId(1, 1)); // proton
+     109           1 :         EXPECT_DOUBLE_EQ(mass_proton, particle.getMass());
+     110             : 
+     111           1 :         particle.setId(nucleusId(1, 0)); // neutron
+     112           1 :         EXPECT_DOUBLE_EQ(mass_neutron, particle.getMass());
+     113             : 
+     114           1 :         int id = nucleusId(56, 26);
+     115           1 :         particle.setId(id); // iron
+     116           1 :         EXPECT_DOUBLE_EQ(nuclearMass(id), particle.getMass());
+     117             : 
+     118           1 :         particle.setId(-id); // anti-iron
+     119           1 :         EXPECT_DOUBLE_EQ(nuclearMass(-id), particle.getMass());
+     120             : 
+     121             :         // approximation for unkown nucleus A * amu - Z * mass_electron
+     122             :         int A = 238; int Z = 92; // Uranium92
+     123           1 :         EXPECT_DOUBLE_EQ(nuclearMass(A, Z), A*amu - Z*mass_electron);
+     124           1 : }
+     125             : 
+     126           2 : TEST(ParticleState, lorentzFactor) {
+     127           1 :         ParticleState particle;
+     128           1 :         particle.setId(nucleusId(1, 1));
+     129           1 :         particle.setEnergy(1e12 * eV);
+     130           1 :         EXPECT_DOUBLE_EQ(particle.getLorentzFactor(),
+     131             :                         1e12 * eV / mass_proton / c_squared);
+     132           1 : }
+     133             : 
+     134           1 : TEST(ParticleID, nucleusId) {
+     135           1 :         EXPECT_EQ(nucleusId(3,2), 1000020030);
+     136           1 : }
+     137             : 
+     138           1 : TEST(ParticleID, chargeNumber) {
+     139           1 :         EXPECT_EQ(chargeNumber(1000020030), 2);
+     140           1 : }
+     141             : 
+     142           1 : TEST(ParticleID, massNumber) {
+     143           1 :         EXPECT_EQ(massNumber(2112), 1);
+     144           1 :         EXPECT_EQ(massNumber(1000020030), 3);
+     145           1 : }
+     146             : 
+     147           1 : TEST(ParticleID, isNucleus) {
+     148           1 :         EXPECT_TRUE(isNucleus(1000020030));
+     149           1 :         EXPECT_FALSE(isNucleus(11));
+     150           1 : }
+     151             : 
+     152           1 : TEST(HepPID, consistencyWithReferenceImplementation) {
+     153             :         // Tests the performance improved version against the default one
+     154           1 :         unsigned long testPID = rand() % 1000000000 + 1000000000;
+     155           8 :         for(size_t i=1; i < 8; i++) {
+     156           7 :                 HepPID::location loc = (HepPID::location) i;
+     157           7 :                 unsigned short newResult = HepPID::digit(loc, testPID);
+     158             :                 //original implementation
+     159           7 :                 int numerator = (int) std::pow(10.0,(loc-1));
+     160           7 :                 EXPECT_EQ(newResult, (HepPID::abspid(testPID)/numerator)%10);
+     161             :         }
+     162           1 : }
+     163             : 
+     164           1 : TEST(HepPID, charge) {
+     165           1 :         EXPECT_DOUBLE_EQ(HepPID::charge(11), -1.);
+     166           1 : }
+     167             : 
+     168           1 : TEST(Candidate, currentStep) {
+     169           1 :         Candidate candidate;
+     170           1 :         candidate.setCurrentStep(1 * Mpc);
+     171           1 :         EXPECT_DOUBLE_EQ(candidate.getCurrentStep(), 1 * Mpc);
+     172           1 : }
+     173             : 
+     174           1 : TEST(Candidate, limitNextStep) {
+     175           1 :         Candidate candidate;
+     176           1 :         candidate.setNextStep(5 * Mpc);
+     177           1 :         EXPECT_DOUBLE_EQ(candidate.getNextStep(), 5 * Mpc);
+     178           1 :         candidate.limitNextStep(2 * Mpc);
+     179           1 :         EXPECT_DOUBLE_EQ(candidate.getNextStep(), 2 * Mpc);
+     180           1 :         candidate.limitNextStep(3 * Mpc);
+     181           1 :         EXPECT_DOUBLE_EQ(candidate.getNextStep(), 2 * Mpc);
+     182           1 : }
+     183             : 
+     184           1 : TEST(Candidate, isActive) {
+     185           1 :         Candidate candidate;
+     186           1 :         EXPECT_TRUE(candidate.isActive());
+     187           1 :         candidate.setActive(false);
+     188           1 :         EXPECT_FALSE(candidate.isActive());
+     189           1 : }
+     190             : 
+     191           1 : TEST(Candidate, property) {
+     192           1 :         Candidate candidate;
+     193           2 :         candidate.setProperty("foo", "bar");
+     194           2 :         EXPECT_TRUE(candidate.hasProperty("foo"));
+     195           2 :         std::string value = candidate.getProperty("foo");
+     196           1 :         EXPECT_EQ("bar", value);
+     197           1 : }
+     198             : 
+     199           1 : TEST(Candidate, weight) {
+     200           1 :     Candidate candidate;
+     201           1 :     EXPECT_EQ (1., candidate.getWeight());
+     202             :     
+     203           1 :     candidate.setWeight(5.);
+     204           1 :     EXPECT_EQ (5., candidate.getWeight());
+     205             :     
+     206           1 :     candidate.updateWeight(3.);
+     207           1 :     EXPECT_EQ (15., candidate.getWeight());
+     208           1 : }
+     209             : 
+     210           1 : TEST(Candidate, addSecondary) {
+     211           1 :         Candidate c;
+     212           1 :         c.setRedshift(5);
+     213           1 :         c.setTrajectoryLength(23);
+     214           1 :         c.setWeight(3.);
+     215           1 :         c.previous.setId(nucleusId(56,26));
+     216           1 :         c.previous.setEnergy(1000);
+     217           1 :         c.previous.setPosition(Vector3d(1,2,3));
+     218           1 :         c.previous.setDirection(Vector3d(0,0,1));
+     219             : 
+     220           1 :         c.addSecondary(nucleusId(1,1), 200);
+     221           2 :         c.addSecondary(nucleusId(1,1), 200, 5.);
+     222           1 :         Candidate s1 = *c.secondaries[0];
+     223           1 :         Candidate s2 = *c.secondaries[1];
+     224             : 
+     225           1 :         EXPECT_EQ(nucleusId(1,1), s1.current.getId());
+     226           1 :         EXPECT_EQ(200, s1.current.getEnergy());
+     227           1 :         EXPECT_EQ(5, s1.getRedshift());
+     228           1 :         EXPECT_EQ(23, s1.getTrajectoryLength());
+     229           1 :         EXPECT_EQ(1000, s1.created.getEnergy());
+     230           1 :         EXPECT_EQ(3., s1.getWeight());
+     231           2 :         EXPECT_TRUE(Vector3d(1,2,3) == s1.created.getPosition());
+     232           2 :         EXPECT_TRUE(Vector3d(0,0,1) == s1.created.getDirection());
+     233           2 :         EXPECT_TRUE(s1.getTagOrigin() == "SEC");
+     234             : 
+     235           1 :         EXPECT_EQ(15., s2.getWeight());
+     236           1 : }
+     237             : 
+     238           1 : TEST(Candidate, candidateTag) {
+     239           1 :         Candidate c;
+     240             : 
+     241             :         // test default tag
+     242           2 :         EXPECT_TRUE(c.getTagOrigin() == "PRIM");
+     243             : 
+     244             :         // test setting tag
+     245           1 :         c.setTagOrigin("myTag");
+     246           2 :         EXPECT_TRUE(c.getTagOrigin() == "myTag");
+     247           1 : }
+     248             : 
+     249           1 : TEST(Candidate, serialNumber) {
+     250           1 :         Candidate::setNextSerialNumber(42);
+     251           1 :         Candidate c;
+     252           1 :         EXPECT_EQ(43, c.getSourceSerialNumber());
+     253           1 : }
+     254             : 
+     255           1 : TEST(common, digit) {
+     256           1 :         EXPECT_EQ(1, digit(1234, 1000));
+     257           1 :         EXPECT_EQ(2, digit(1234, 100));
+     258           1 :         EXPECT_EQ(3, digit(1234, 10));
+     259           1 :         EXPECT_EQ(4, digit(1234, 1));
+     260           1 : }
+     261             : 
+     262           1 : TEST(common, interpolate) {
+     263             :         // create vectors x = (0, 0.02, ... 2) and y = 2x + 3 = (3, ... 7)
+     264           1 :         std::vector<double> xD(101), yD(101);
+     265         102 :         for (int i = 0; i <= 100; i++) {
+     266         101 :                 xD[i] = i * 0.02;
+     267         101 :                 yD[i] = 2 * xD[i] + 3;
+     268             :         }
+     269             : 
+     270             :         // interpolating tabulated values of a linear function should produce exact results
+     271           1 :         Random &R = Random::instance();
+     272             :         double x, ytrue, yinterp;
+     273       10001 :         for (int i = 0; i < 10000; i++) {
+     274       10000 :                 x = R.rand() * 2; // random value between 0 and 2
+     275       10000 :                 ytrue = 2 * x + 3;
+     276       10000 :                 yinterp = interpolate(x, xD, yD);
+     277       10000 :                 EXPECT_DOUBLE_EQ(ytrue, yinterp);
+     278             :         }
+     279             : 
+     280             :         // test interpolation in first bin
+     281             :         x = 0.01;
+     282             :         ytrue = 2 * x + 3;
+     283           1 :         yinterp = interpolate(x, xD, yD);
+     284           1 :         EXPECT_DOUBLE_EQ(ytrue, yinterp);
+     285             : 
+     286             :         // test interpolation in last bin
+     287             :         x = 1.99;
+     288             :         ytrue = 2 * x + 3;
+     289           1 :         yinterp = interpolate(x, xD, yD);
+     290           1 :         EXPECT_DOUBLE_EQ(ytrue, yinterp);
+     291             : 
+     292             :         // value out of range, return lower bound
+     293           1 :         EXPECT_EQ(3, interpolate(-0.001, xD, yD));
+     294             : 
+     295             :         // value out of range, return upper bound
+     296           1 :         EXPECT_EQ(7, interpolate(2.001, xD, yD));
+     297           1 : }
+     298             : 
+     299           1 : TEST(common, interpolateEquidistant) {
+     300           1 :         std::vector<double> yD(100);
+     301         101 :         for (int i = 0; i < 100; i++) {
+     302         100 :                 yD[i] = pow(1 + i * 2. / 99., 2);
+     303             :         }
+     304             : 
+     305             :         // interpolated value should be close to computed
+     306           1 :         double y = interpolateEquidistant(1.5001, 1, 3, yD);
+     307           1 :         EXPECT_NEAR(pow(1.5001, 2), y, 1e-4);
+     308             : 
+     309             :         // value out of range, return lower bound
+     310           1 :         EXPECT_EQ(1, interpolateEquidistant(0.9, 1, 3, yD));
+     311             : 
+     312             :         // value out of range, return lower bound
+     313           1 :         EXPECT_EQ(9, interpolateEquidistant(3.1, 1, 3, yD));
+     314           1 : }
+     315             : 
+     316           1 : TEST(common, pow_integer) {
+     317           1 :         EXPECT_EQ(pow_integer<0>(1.23), 1);
+     318           1 :         EXPECT_FLOAT_EQ(pow_integer<1>(1.234), 1.234);
+     319           1 :         EXPECT_FLOAT_EQ(pow_integer<2>(1.234), pow(1.234, 2));
+     320           1 :         EXPECT_FLOAT_EQ(pow_integer<3>(1.234), pow(1.234, 3));
+     321           1 : }
+     322             : 
+     323           2 : TEST(common, gaussInt) {
+     324           9 :         EXPECT_NEAR(gaussInt(([](double x){ return x*x; }), 0, 10), 1000/3., 1e-4);
+     325           9 :         EXPECT_NEAR(gaussInt(([](double x){ return sin(x)*sin(x); }), 0, M_PI), M_PI/2., 1e-4);
+     326           1 : }
+     327             : 
+     328           1 : TEST(Random, seed) {
+     329           1 :         Random &a = Random::instance();
+     330           1 :         Random &b = Random::instance();
+     331             : 
+     332           1 :         a.seed(42);
+     333           1 :         double r1 = a.rand();
+     334             : 
+     335           1 :         a.seed(42);
+     336           1 :         double r2 = a.rand();
+     337             : 
+     338           1 :         a.seed(42);
+     339           1 :         double r3 = b.rand();
+     340             : 
+     341             :         // seeding should give same random numbers
+     342           1 :         EXPECT_EQ(r1, r2);
+     343             : 
+     344             :         // seeding should work for all instances
+     345           1 :         EXPECT_EQ(r1, r3);
+     346           1 : }
+     347             : 
+     348           1 : TEST(Random, bigSeedStorage) {
+     349           1 :         Random a;
+     350             :         std::vector<uint32_t> bigSeed;
+     351             : 
+     352             :         const size_t nComp = 42;
+     353             :         double values[nComp];
+     354          43 :         for (size_t i = 0; i < nComp; i++)
+     355             :         {
+     356          42 :                 values[i] = a.rand();
+     357             :         }
+     358           1 :         bigSeed = a.getSeed();
+     359           1 :         Random b;
+     360             :         //b.load(bigSeed);
+     361           1 :         b.seed(&bigSeed[0], bigSeed.size());
+     362          43 :         for (size_t i = 0; i < nComp; i++)
+     363             :         {
+     364          42 :                 EXPECT_EQ(values[i], b.rand());
+     365             :         }
+     366             : 
+     367           1 :         a.seed(42);
+     368           1 :         bigSeed = a.getSeed();
+     369           1 :         EXPECT_EQ(bigSeed.size(), 1);
+     370           1 :         EXPECT_EQ(bigSeed[0], 42);
+     371           1 :         b.seed(bigSeed[0]);
+     372          43 :         for (size_t i = 0; i < nComp; i++)
+     373             :         {
+     374          42 :                 EXPECT_EQ(a.rand(), b.rand());
+     375             :         }
+     376             : 
+     377           1 : }
+     378             : 
+     379           1 : TEST(base64, de_en_coding) {
+     380           1 :         Random a;
+     381         100 :         for (int N=1; N < 100; N++) {
+     382             :                 std::vector<uint32_t> data;
+     383          99 :                 data.reserve(N);
+     384        5049 :                 for (int i =0; i<N; i++)
+     385        4950 :                         data.push_back(a.randInt());
+     386             : 
+     387          99 :                 std::string encoded_data = Base64::encode((unsigned char*)&data[0], sizeof(data[0]) * data.size() / sizeof(unsigned char));
+     388             : 
+     389          99 :                 std::string decoded_data = Base64::decode(encoded_data);
+     390          99 :                 size_t S = decoded_data.size() * sizeof(decoded_data[0]) / sizeof(uint32_t);
+     391        5049 :                 for (int i=0; i < S; i++) {
+     392        4950 :                         EXPECT_EQ(((uint32_t*)decoded_data.c_str())[i], data[i]);
+     393             :                 }
+     394             :         }
+     395             : 
+     396           1 : }
+     397             : 
+     398           1 : TEST(Random, base64Seed) {
+     399             : 
+     400           1 :         std::string seed =  "I1+8ANzXYwAqAAAAAwAAAA==";
+     401             :         std::vector<uint32_t> bigSeed;
+     402           1 :         bigSeed.push_back(12345123);
+     403           1 :         bigSeed.push_back(6543324);
+     404           1 :         bigSeed.push_back(42);
+     405           1 :         bigSeed.push_back(3);
+     406           1 :         Random a, b;
+     407           1 :         a.seed(seed);
+     408           1 :         b.seed(&bigSeed[0], bigSeed.size());
+     409             : 
+     410             :         const size_t nComp = 42;
+     411             :         double values[nComp];
+     412          43 :         for (size_t i = 0; i < nComp; i++)
+     413             :         {
+     414          42 :                 EXPECT_EQ(a.rand(), b.rand());
+     415             :         }
+     416           1 : }
+     417             : 
+     418           2 : TEST(Grid, PeriodicClamp) {
+     419             :         // Test correct determination of lower and upper neighbor
+     420             :         int lo, hi;
+     421             : 
+     422             :         periodicClamp(23.12, 8, lo, hi);
+     423           1 :         EXPECT_EQ(7, lo);
+     424           1 :         EXPECT_EQ(0, hi);
+     425             : 
+     426             :         periodicClamp(-23.12, 8, lo, hi);
+     427           1 :         EXPECT_EQ(0, lo);
+     428           1 :         EXPECT_EQ(1, hi);
+     429           1 : }
+     430             : 
+     431           1 : TEST(Grid, PeriodicBoundary) {
+     432             :         // Test correct determination of periodic continuated index
+     433             :         // periodic indices for n=8 should repeat like ...0123456701234567...
+     434             :         int index;
+     435             : 
+     436           1 :         index = periodicBoundary(0, 8);
+     437           1 :         EXPECT_EQ(0, index);
+     438           1 :         index = periodicBoundary(7, 8);
+     439           1 :         EXPECT_EQ(7, index);
+     440           1 :         index = periodicBoundary(8, 8);
+     441           1 :         EXPECT_EQ(0, index);
+     442           1 :         index = periodicBoundary(9, 8);
+     443           1 :         EXPECT_EQ(1, index);
+     444           1 : }
+     445             : 
+     446           1 : TEST(Grid, ReflectiveClamp) {
+     447             :         // Test correct determination of lower and upper neighbor
+     448             :         // reflective indices for n=8 should repeat like ...67765432100123456776...
+     449             :         int lo, hi; 
+     450             :         double res;
+     451             : 
+     452           1 :         reflectiveClamp(23.12, 8, lo, hi, res);
+     453           1 :         EXPECT_EQ(7, lo);
+     454           1 :         EXPECT_EQ(7, hi);
+     455           1 :         EXPECT_FLOAT_EQ(7.12, res);
+     456             : 
+     457           1 :         reflectiveClamp(-23.12, 8, lo, hi, res);
+     458           1 :         EXPECT_EQ(6, lo);
+     459           1 :         EXPECT_EQ(7, hi);
+     460           1 :         EXPECT_FLOAT_EQ(6.12, res);
+     461           1 : }
+     462             : 
+     463           2 : TEST(Grid, ReflectiveBoundary) {
+     464             :         // Test correct determination of reflected index
+     465             :         // reflective indices for n=8 should repeat like ...67765432100123456776...
+     466             :         int index; 
+     467             : 
+     468           1 :         index = reflectiveBoundary(8, 8);
+     469           1 :         EXPECT_EQ(7, index);
+     470           1 :         index = reflectiveBoundary(9, 8);
+     471           1 :         EXPECT_EQ(6, index);
+     472           1 :         index = reflectiveBoundary(0, 8);
+     473           1 :         EXPECT_EQ(0, index);
+     474           1 :         index = reflectiveBoundary(-1, 8);
+     475           1 :         EXPECT_EQ(0, index);
+     476           1 :         index = reflectiveBoundary(-8, 8);
+     477           1 :         EXPECT_EQ(7, index);
+     478           1 :         index = reflectiveBoundary(-9, 8);
+     479           1 :         EXPECT_EQ(7, index);
+     480           1 : }
+     481             : 
+     482           1 : TEST(Grid1f, SimpleTest) {
+     483             :         // Test construction and parameters
+     484           1 :         size_t Nx = 5;
+     485           1 :         size_t Ny = 8;
+     486           1 :         size_t Nz = 10;
+     487             :         double spacing = 2.0;
+     488             :         Vector3d origin(1., 2., 3.);
+     489             : 
+     490           1 :         Grid1f grid(origin, Nx, Ny, Nz, spacing);
+     491             : 
+     492           1 :         EXPECT_TRUE(origin == grid.getOrigin());
+     493           1 :         EXPECT_EQ(Nx, grid.getNx());
+     494           1 :         EXPECT_EQ(Ny, grid.getNy());
+     495           1 :         EXPECT_EQ(Nz, grid.getNz());
+     496           1 :         EXPECT_EQ(Vector3d(spacing), grid.getSpacing());
+     497           1 :         EXPECT_EQ(5 * 8 * 10, grid.getGrid().size());
+     498             : 
+     499             :         // Test index handling: get position of grid point (2, 3, 4)
+     500           1 :         size_t some_index = 2 * Ny * Nz + 3 * Nz + 4;
+     501             :         Vector3d some_grid_point = origin + Vector3d(2, 3, 4) * spacing + Vector3d(spacing / 2.);
+     502           2 :         EXPECT_EQ(some_grid_point, grid.positionFromIndex(some_index));
+     503             :         
+     504             :         //Test if value on gridpoint is correctly retrieved
+     505           1 :         grid.get(2, 3, 4) = 7;
+     506           1 :         EXPECT_FLOAT_EQ(7., grid.getGrid()[some_index]);
+     507             :         //trilinear interpolated
+     508           1 :         EXPECT_FLOAT_EQ(7., grid.interpolate(some_grid_point));
+     509             :         //tricubic interpolated
+     510             :         grid.setInterpolationType(TRICUBIC);
+     511           1 :         EXPECT_FLOAT_EQ(7., grid.interpolate(some_grid_point));
+     512             :         //nearest neighbour interpolated
+     513             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
+     514           1 :         EXPECT_FLOAT_EQ(7., grid.interpolate(some_grid_point));
+     515             : 
+     516             :         //Test if grid is set to zero outside of volume for clipVolume=true
+     517             :         grid.setClipVolume(true);
+     518           1 :         EXPECT_FLOAT_EQ(0, grid.interpolate(Vector3d(100, 0, 12)));
+     519           1 : }
+     520             : 
+     521           2 : TEST(Grid1f, GridPropertiesConstructor) {
+     522             :         // Test constructor for vector spacing
+     523             :         size_t Nx = 5;
+     524             :         size_t Ny = 8;
+     525             :         size_t Nz = 10;
+     526             :         Vector3d origin = Vector3d(1., 2., 3.);
+     527             :         Vector3d spacing = Vector3d(1., 5., 3.);
+     528             :         GridProperties properties(origin, Nx, Ny, Nz, spacing);
+     529           1 :         Grid1f grid(properties);
+     530             : 
+     531           1 :         EXPECT_EQ(spacing, grid.getSpacing());
+     532             : 
+     533             :         // Test index handling: get position of grid point (1, 7, 6)
+     534             :         size_t some_index = 1 * Ny * Nz + 7 * Nz + 6;
+     535             :         Vector3d some_grid_point = origin + Vector3d(1, 7, 6) * spacing + spacing / 2.;
+     536             : 
+     537             :         //Test if value on gridpoint is correctly retrieved
+     538           1 :         grid.get(1, 7, 6) = 12;
+     539           1 :         EXPECT_FLOAT_EQ(12., grid.getGrid()[some_index]);
+     540             :         //trilinear interpolated
+     541           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
+     542             :         //tricubic interpolated
+     543             :         grid.setInterpolationType(TRICUBIC);
+     544           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
+     545             :         //nearest neighbour interpolated
+     546             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
+     547           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
+     548           1 : }
+     549             : 
+     550           2 : TEST(Grid1f, TestVectorSpacing) {
+     551             :         // Test constructor for vector spacing
+     552             :         size_t Nx = 5;
+     553             :         size_t Ny = 8;
+     554             :         size_t Nz = 10;
+     555             :         Vector3d origin = Vector3d(1., 2., 3.);
+     556             :         Vector3d spacing = Vector3d(1., 5., 3.);
+     557             : 
+     558           1 :         Grid1f grid(origin, Nx, Ny, Nz, spacing);
+     559             : 
+     560           1 :         EXPECT_EQ(spacing, grid.getSpacing());
+     561             : 
+     562             :         // Test index handling: get position of grid point (1, 7, 6)
+     563             :         size_t some_index = 1 * Ny * Nz + 7 * Nz + 6;
+     564             :         Vector3d some_grid_point = origin + Vector3d(1, 7, 6) * spacing + spacing / 2.;
+     565             : 
+     566             :         //Test if value on gridpoint is correctly retrieved
+     567           1 :         grid.get(1, 7, 6) = 12;
+     568           1 :         EXPECT_FLOAT_EQ(12., grid.getGrid()[some_index]);
+     569             :         //trilinear interpolated
+     570           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
+     571             :         //tricubic interpolated
+     572             :         grid.setInterpolationType(TRICUBIC);
+     573           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
+     574             :         //nearest neighbour interpolated
+     575             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
+     576           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
+     577           1 : }
+     578             : 
+     579           2 : TEST(Grid1f, ClosestValue) {
+     580             :         // Check some closest values / nearest neighbour interpolation
+     581           1 :         Grid1f grid(Vector3d(0.), 2, 2, 2, 1.);
+     582           1 :         grid.get(0, 0, 0) = 1;
+     583           1 :         grid.get(0, 0, 1) = 2;
+     584           1 :         grid.get(0, 1, 0) = 3;
+     585           1 :         grid.get(0, 1, 1) = 4;
+     586           1 :         grid.get(1, 0, 0) = 5;
+     587           1 :         grid.get(1, 0, 1) = 6;
+     588           1 :         grid.get(1, 1, 0) = 7;
+     589           1 :         grid.get(1, 1, 1) = 8;
+     590             : 
+     591             :         // grid points are at 0.5 and 1.5
+     592           1 :         EXPECT_FLOAT_EQ(1, grid.closestValue(Vector3d(0.1,  0.2, 0.6)));
+     593           1 :         EXPECT_FLOAT_EQ(2, grid.closestValue(Vector3d(0.2, 0.1, 1.3)));
+     594           1 :         EXPECT_FLOAT_EQ(3, grid.closestValue(Vector3d(0.3, 1.2, 0.2)));
+     595           1 :         EXPECT_FLOAT_EQ(7, grid.closestValue(Vector3d(1.7, 1.8, 0.4)));
+     596             : 
+     597             :         //Test if grid is set to zero outside of volume for clipVolume=true
+     598           1 :         EXPECT_NE(0, grid.interpolate(Vector3d(0, 0, 12)));
+     599             :         grid.setClipVolume(true);
+     600           1 :         double b = grid.interpolate(Vector3d(0, 0, 12));
+     601           1 :         EXPECT_FLOAT_EQ(0, b);
+     602           1 : }
+     603             : 
+     604           2 : TEST(Grid1f, clipVolume) {
+     605             :         // Check volume clipping for gridproperties constructor
+     606             :         size_t N = 2;
+     607             :         Vector3d origin = Vector3d(0.);
+     608             :         double spacing = 2;
+     609             :         GridProperties properties(origin, N, spacing);
+     610           1 :         Grid1f grid(properties);
+     611           1 :         grid.get(0, 0, 0) = 1;
+     612           1 :         grid.get(0, 0, 1) = 2;
+     613           1 :         grid.get(0, 1, 0) = 3;
+     614           1 :         grid.get(0, 1, 1) = 4;
+     615           1 :         grid.get(1, 0, 0) = 5;
+     616           1 :         grid.get(1, 0, 1) = 6;
+     617           1 :         grid.get(1, 1, 0) = 7;
+     618           1 :         grid.get(1, 1, 1) = 8;
+     619             : 
+     620             :         //Test if grid is set to zero outside of volume for clipVolume=true
+     621           1 :         EXPECT_NE(0, grid.interpolate(Vector3d(0, 0, 12)));
+     622             :         grid.setClipVolume(true);
+     623           1 :         double b = grid.interpolate(Vector3d(0, 0, 10));
+     624           1 :         EXPECT_FLOAT_EQ(0, b);
+     625           1 : }
+     626             : 
+     627           2 : TEST(Grid3f, Interpolation) {
+     628             :         // Explicitly test trilinear and tricubic interpolation
+     629             :         double spacing = 2.793;
+     630             :         int n = 3;
+     631           1 :         Grid3f grid(Vector3d(0.), n, n, n, spacing);
+     632             :         grid.get(0, 0, 1) = Vector3f(1.7, 0., 0.); // set one value
+     633             : 
+     634             :         Vector3d b;
+     635             :         
+     636             :         //trilinear
+     637             : 
+     638             :         // grid points are at [0.5, 1.5, ...] * spacing
+     639           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.5) * spacing);
+     640           1 :         EXPECT_FLOAT_EQ(1.7, b.x);
+     641             : 
+     642           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.4) * spacing);
+     643           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9, b.x);
+     644             : 
+     645           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.6) * spacing);
+     646           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9, b.x);
+     647             : 
+     648           1 :         b = grid.interpolate(Vector3d(0.5, 0.35, 1.6) * spacing);
+     649           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9 * 0.85, b.x);
+     650             : 
+     651           1 :         b = grid.interpolate(Vector3d(0.5, 2.65, 1.6) * spacing); // using periodic repetition
+     652           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9 * 0.15, b.x);
+     653             :         
+     654             :         //tricubic
+     655             :         #ifdef HAVE_SIMD
+     656             :         grid.setInterpolationType(TRICUBIC);
+     657             :         
+     658           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.5) * spacing);
+     659           1 :         EXPECT_FLOAT_EQ(1.7, b.x);
+     660             : 
+     661           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.4) * spacing);
+     662           1 :         EXPECT_FLOAT_EQ(1.66005015373, b.x);
+     663             : 
+     664           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.6) * spacing);
+     665           1 :         EXPECT_FLOAT_EQ(1.66005003452, b.x);
+     666             : 
+     667           1 :         b = grid.interpolate(Vector3d(0.5, 0.35, 1.6) * spacing);
+     668           1 :         EXPECT_FLOAT_EQ(1.57507634163, b.x);
+     669             : 
+     670           1 :         b = grid.interpolate(Vector3d(0.5, 2.65, 1.6) * spacing);
+     671           1 :         EXPECT_FLOAT_EQ(0.190802007914, b.x);
+     672             :         #endif // HAVE_SIMD
+     673           1 : }
+     674             : 
+     675           2 : TEST(VectordGrid, Scale) {
+     676             :         // Test scaling a field
+     677           1 :         ref_ptr<Grid3f> grid = new Grid3f(Vector3d(0.), 3, 1);
+     678           4 :         for (int ix = 0; ix < 3; ix++)
+     679          12 :                 for (int iy = 0; iy < 3; iy++)
+     680          36 :                         for (int iz = 0; iz < 3; iz++)
+     681          27 :                                 grid->get(ix, iy, iz) = Vector3f(1, 0, 0);
+     682             : 
+     683           1 :         scaleGrid(grid, 5);
+     684           4 :         for (int ix = 0; ix < 3; ix++)
+     685          12 :                 for (int iy = 0; iy < 3; iy++)
+     686          36 :                         for (int iz = 0; iz < 3; iz++)
+     687          27 :                                 EXPECT_FLOAT_EQ(5, grid->interpolate(Vector3d(0.7, 0, 0.1)).x);
+     688           1 : }
+     689             : 
+     690           2 : TEST(Grid3f, Periodicity) {
+     691             :         // Test for periodic boundaries: grid(x+a*n) = grid(x)
+     692             :         size_t n = 3;
+     693             :         double spacing = 3;
+     694             :         double size = n * spacing;
+     695           1 :         Grid3f grid(Vector3d(0.), n, spacing);
+     696           4 :         for (int ix = 0; ix < 3; ix++)
+     697          12 :                 for (int iy = 0; iy < 3; iy++)
+     698          36 :                         for (int iz = 0; iz < 3; iz++)
+     699          27 :                                 grid.get(ix, iy, iz) = Vector3f(iz + ix, iy * iz, ix - iz * iy);
+     700             : 
+     701             :         Vector3d pos(1.2, 2.3, 0.7);
+     702             :         
+     703             :         //trilinear interpolated
+     704           1 :         Vector3f b = grid.interpolate(pos);
+     705           1 :         Vector3f b2 = grid.interpolate(pos + Vector3d(1, 0, 0) * size);
+     706           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     707           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     708           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     709             : 
+     710           1 :         b2 = grid.interpolate(pos + Vector3d(0, 5, 0) * size);
+     711           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     712           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     713           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     714             : 
+     715           1 :         b2 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
+     716           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     717           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     718           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     719             :         
+     720             :         //tricubic interpolated
+     721             :         #ifdef HAVE_SIMD
+     722             :         grid.setInterpolationType(TRICUBIC);
+     723           1 :         b = grid.interpolate(pos);
+     724           1 :         b2 = grid.interpolate(pos + Vector3d(1, 0, 0) * size);
+     725           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     726           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     727           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     728             : 
+     729           1 :         b2 = grid.interpolate(pos + Vector3d(0, 5, 0) * size);
+     730           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     731           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     732           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     733             : 
+     734           1 :         b2 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
+     735           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     736           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     737           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     738             :         #endif // HAVE_SIMD
+     739             :         
+     740             :         //nearest neighbour interpolated
+     741             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
+     742           1 :         b = grid.interpolate(pos);
+     743           1 :         b2 = grid.interpolate(pos + Vector3d(1, 0, 0) * size);
+     744           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     745           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     746           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     747             : 
+     748           1 :         b2 = grid.interpolate(pos + Vector3d(0, 5, 0) * size);
+     749           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     750           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     751           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     752             : 
+     753           1 :         b2 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
+     754           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     755           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     756           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     757             : 
+     758             :         //Test if grid is set to zero outside of volume for clipVolume=true
+     759             :         grid.setClipVolume(true);
+     760           1 :         Vector3f b3 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
+     761           1 :         EXPECT_FLOAT_EQ(0., b3.x);
+     762           1 :         EXPECT_FLOAT_EQ(0., b3.y);
+     763           1 :         EXPECT_FLOAT_EQ(0., b3.z);
+     764           1 : }
+     765             : 
+     766           2 : TEST(Grid3f, Reflectivity) {
+     767             :         // Test for reflective boundaries: grid(pos) = grid(x+a) = grid(-x-a)
+     768             :         size_t n = 3;
+     769             :         double spacing = 3;
+     770             :         double size = n * spacing;
+     771           1 :         Grid3f grid(Vector3d(0.), n, spacing);
+     772             :         grid.setReflective(true); //set reflective boundary
+     773           4 :         for (int ix = 0; ix < 3; ix++)
+     774          12 :                 for (int iy = 0; iy < 3; iy++)
+     775          36 :                         for (int iz = 0; iz < 3; iz++)
+     776          27 :                                 grid.get(ix, iy, iz) = Vector3f(iz + ix, iy * iz, ix - iz * iy);
+     777             : 
+     778             :         Vector3d pos(1.2, 2.3, 0.7);
+     779             :         
+     780             :         //trilinear interpolated
+     781           1 :         Vector3f b = grid.interpolate(pos + Vector3d(1,0,0) * spacing);
+     782           1 :         Vector3f b2 = grid.interpolate(pos *(-1) - Vector3d(1,0,0) * spacing);
+     783           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     784           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     785           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     786             :         
+     787           1 :         b = grid.interpolate(pos + Vector3d(0,5,0) * spacing);
+     788           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,5,0) * spacing);
+     789           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     790           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     791           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     792             :         
+     793           1 :         b = grid.interpolate(pos + Vector3d(0,0,-2) * spacing);
+     794           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,0,-2) * spacing);
+     795           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     796           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     797           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     798             :         
+     799             :         //tricubic interpolated
+     800             :         #ifdef HAVE_SIMD
+     801             :         grid.setInterpolationType(TRICUBIC);
+     802           1 :         b = grid.interpolate(pos + Vector3d(1,0,0) * spacing);
+     803           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(1,0,0) * spacing);
+     804           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     805           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     806           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     807             :         
+     808           1 :         b = grid.interpolate(pos + Vector3d(0,5,0) * spacing);
+     809           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,5,0) * spacing);
+     810           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     811           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     812           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     813             :         
+     814           1 :         b = grid.interpolate(pos + Vector3d(0,0,-2) * spacing);
+     815           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,0,-2) * spacing);
+     816           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     817           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     818           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     819             :         #endif //HAVE_SIMD
+     820             :         
+     821             :         //nearest neighbour interpolated
+     822             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
+     823           1 :         b = grid.interpolate(pos + Vector3d(1,0,0) * spacing);
+     824           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(1,0,0) * spacing);
+     825           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     826           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     827           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     828             :         
+     829           1 :         b = grid.interpolate(pos + Vector3d(0,5,0) * spacing);
+     830           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,5,0) * spacing);
+     831           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     832           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     833           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     834             :         
+     835           1 :         b = grid.interpolate(pos + Vector3d(0,0,-2) * spacing);
+     836           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,0,-2) * spacing);
+     837           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
+     838           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
+     839           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
+     840             : 
+     841             :         //Test if grid is set to zero outside of volume for clipVolume=true
+     842             :         grid.setClipVolume(true);
+     843           1 :         Vector3f b3 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
+     844           1 :         EXPECT_FLOAT_EQ(0., b3.x);
+     845           1 :         EXPECT_FLOAT_EQ(0., b3.y);
+     846           1 :         EXPECT_FLOAT_EQ(0., b3.z);
+     847           1 : }
+     848             : 
+     849           2 : TEST(Grid3f, DumpLoad) {
+     850             :         // Dump and load a field grid
+     851           1 :         ref_ptr<Grid3f> grid1 = new Grid3f(Vector3d(0.), 3, 1);
+     852           1 :         ref_ptr<Grid3f> grid2 = new Grid3f(Vector3d(0.), 3, 1);
+     853             : 
+     854           4 :         for (int ix = 0; ix < 3; ix++)
+     855          12 :                 for (int iy = 0; iy < 3; iy++)
+     856          36 :                         for (int iz = 0; iz < 3; iz++)
+     857          27 :                                 grid1->get(ix, iy, iz) = Vector3f(1, 2, 3);
+     858             : 
+     859           2 :         dumpGrid(grid1, "testDump.raw");
+     860           2 :         loadGrid(grid2, "testDump.raw");
+     861             : 
+     862           4 :         for (int ix = 0; ix < 3; ix++) {
+     863          12 :                 for (int iy = 0; iy < 3; iy++) {
+     864          36 :                         for (int iz = 0; iz < 3; iz++) {
+     865          27 :                                 Vector3f b1 = grid1->get(ix, iy, iz);
+     866             :                                 Vector3f b2 = grid2->get(ix, iy, iz);
+     867          27 :                                 EXPECT_FLOAT_EQ(b1.x, b2.x);
+     868          27 :                                 EXPECT_FLOAT_EQ(b1.y, b2.y);
+     869          27 :                                 EXPECT_FLOAT_EQ(b1.z, b2.z);
+     870             :                         }
+     871             :                 }
+     872             :         }
+     873           1 : }
+     874             : 
+     875           2 : TEST(Grid3f, DumpLoadTxt) {
+     876             :         // Dump and load a field grid
+     877           1 :         ref_ptr<Grid3f> grid1 = new Grid3f(Vector3d(0.), 3, 1);
+     878           1 :         ref_ptr<Grid3f> grid2 = new Grid3f(Vector3d(0.), 3, 1);
+     879             : 
+     880           4 :         for (int ix = 0; ix < 3; ix++)
+     881          12 :                 for (int iy = 0; iy < 3; iy++)
+     882          36 :                         for (int iz = 0; iz < 3; iz++)
+     883          27 :                                 grid1->get(ix, iy, iz) = Vector3f(ix, iy, iz);
+     884             : 
+     885           2 :         dumpGridToTxt(grid1, "testDump.txt", 1e4);
+     886           2 :         loadGridFromTxt(grid2, "testDump.txt", 1e-4);
+     887             : 
+     888           4 :         for (int ix = 0; ix < 3; ix++) {
+     889          12 :                 for (int iy = 0; iy < 3; iy++) {
+     890          36 :                         for (int iz = 0; iz < 3; iz++) {
+     891          27 :                                 Vector3f b1 = grid1->get(ix, iy, iz);
+     892             :                                 Vector3f b2 = grid2->get(ix, iy, iz);
+     893          27 :                                 EXPECT_FLOAT_EQ(b1.x, b2.x);
+     894          27 :                                 EXPECT_FLOAT_EQ(b1.y, b2.y);
+     895          27 :                                 EXPECT_FLOAT_EQ(b1.z, b2.z);
+     896             :                         }
+     897             :                 }
+     898             :         }
+     899           1 : }
+     900             : 
+     901           2 : TEST(Grid3f, Speed) {
+     902             :         // Dump and load a field grid
+     903           1 :         Grid3f grid(Vector3d(0.), 3, 3);
+     904           4 :         for (int ix = 0; ix < 3; ix++)
+     905          12 :                 for (int iy = 0; iy < 3; iy++)
+     906          36 :                         for (int iz = 0; iz < 3; iz++)
+     907          27 :                                 grid.get(ix, iy, iz) = Vector3f(1, 2, 3);
+     908             : 
+     909             :         Vector3d b;
+     910      100001 :         for (int i = 0; i < 100000; i++)
+     911      100000 :                 b = grid.interpolate(Vector3d(i));
+     912           1 : }
+     913             : 
+     914           2 : TEST(CylindricalProjectionMap, functions) {
+     915             :         Vector3d v;
+     916           1 :         v.setRThetaPhi(1.0, 1.2, 2.4);
+     917           1 :         EXPECT_NEAR(v.getPhi(), 2.4, .00001);
+     918           1 :         EXPECT_NEAR(v.getTheta(), 1.2, .000001);
+     919             : 
+     920             : 
+     921             : 
+     922           2 :         CylindricalProjectionMap cpm(24, 12);
+     923           1 :         size_t bin = 50;
+     924           1 :         Vector3d d = cpm.directionFromBin(bin);
+     925           1 :         size_t bin2 = cpm.binFromDirection(d);
+     926           1 :         EXPECT_EQ(bin, bin2);
+     927           1 : }
+     928             : 
+     929           1 : TEST(EmissionMap, functions) {
+     930             : 
+     931           1 :         EmissionMap em(360, 180, 100, 1 * EeV, 100 * EeV);
+     932           1 :         double e = em.energyFromBin(50);
+     933           1 :         size_t b = em.binFromEnergy(50 * EeV);
+     934             : 
+     935             :         Vector3d d(1.0, 0.0, 0.0);
+     936             : 
+     937           1 :         em.fillMap(1, 50 * EeV, d);
+     938             : 
+     939             :         Vector3d d2;
+     940             : 
+     941           1 :         bool r = em.drawDirection(1, 50 * EeV, d2);
+     942           1 :         EXPECT_TRUE(r);
+     943           1 :         EXPECT_TRUE(d.getAngleTo(d2) < (2. * M_PI / 180.));
+     944             : 
+     945           1 :         r = em.drawDirection(1, 30 * EeV, d2);
+     946           1 :         EXPECT_FALSE(r);
+     947             : 
+     948           1 :         r = em.drawDirection(2, 50 * EeV, d2);
+     949           1 :         EXPECT_FALSE(r);
+     950             : 
+     951           1 : }
+     952             : 
+     953           1 : TEST(EmissionMap, merge) {
+     954           1 :         EmissionMap em1, em2;
+     955           1 :         em1.fillMap(1, 50 * EeV, Vector3d(1.0, 0.0, 0.0));
+     956           1 :         em2.fillMap(1, 50 * EeV, Vector3d(0.0, 1.0, 0.0));
+     957           1 :         em2.fillMap(2, 50 * EeV, Vector3d(0.0, 1.0, 0.0));
+     958             : 
+     959           1 :         em1.merge(&em2);
+     960             : 
+     961           1 :         EXPECT_EQ(em1.getMaps().size(), 2);
+     962             : 
+     963           1 :         ref_ptr<CylindricalProjectionMap> cpm = em1.getMap(1, 50 * EeV);
+     964           1 :         size_t bin = cpm->binFromDirection(Vector3d(0.0, 1.0, 0.0));
+     965           1 :         EXPECT_TRUE(cpm->getPdf()[bin] > 0);
+     966           1 : }
+     967             : 
+     968           1 : TEST(Variant, copyToBuffer) {
+     969           1 :         double a = 23.42;
+     970             :         Variant v(a);
+     971             :         double b;
+     972           1 :         v.copyToBuffer(&b);
+     973           1 :         EXPECT_EQ(a, b);
+     974           1 : }
+     975             : 
+     976           1 : TEST(Variant, stringConversion) {
+     977           1 :         Variant v, w;
+     978             :         {
+     979           1 :                 int32_t a = 12;
+     980           1 :                 v = Variant::fromInt32(a);
+     981           1 :                 EXPECT_EQ(a, v.asInt32());
+     982             : 
+     983           1 :                 w = Variant::fromString(v.toString(), v.getType());
+     984           1 :                 EXPECT_EQ(a, w.asInt32());
+     985             :         }
+     986             : 
+     987             :         {
+     988           1 :                 int64_t a = 12;
+     989           1 :                 v = Variant::fromInt64(a);
+     990           1 :                 EXPECT_EQ(a, v.asInt64());
+     991             : 
+     992           1 :                 w = Variant::fromString(v.toString(), v.getType());
+     993           1 :                 EXPECT_EQ(a, w.asInt64());
+     994             :         }
+     995             : 
+     996             :         {
+     997             :                 Vector3d a(1, 2, 3);
+     998             :                 Variant v = Variant::fromVector3d(a);
+     999             :                 Vector3d u = v.asVector3d();
+    1000           1 :                 EXPECT_EQ(a.getX(), u.getX());
+    1001           1 :                 EXPECT_EQ(a.getY(), u.getY());
+    1002           1 :                 EXPECT_EQ(a.getZ(), u.getZ());
+    1003           1 :         }
+    1004             : 
+    1005             :         {
+    1006           1 :                 std::complex<double> a1(1, 1);
+    1007           1 :                 std::complex<double> a2(2, 0);
+    1008             :                 Vector3<std::complex<double>> a(a1, a1, a2);
+    1009             :                 Variant v = Variant::fromVector3c(a);
+    1010             :                 Vector3<std::complex<double>> u = v.asVector3c();
+    1011           1 :                 EXPECT_EQ(a1, u.getX());
+    1012           1 :                 EXPECT_EQ(a1, u.getY());
+    1013           1 :                 EXPECT_EQ(a2, u.getZ());
+    1014           1 :         }
+    1015             : 
+    1016             :         {
+    1017             :                 std::complex<double> a(1, 2);
+    1018             :                 Variant v = Variant::fromComplexDouble(a);
+    1019           1 :                 std::complex<double> u = v.asComplexDouble();
+    1020           1 :                 EXPECT_EQ(u.real(), 1);
+    1021           1 :                 EXPECT_EQ(u.imag(), 2);
+    1022           1 :         }
+    1023             : 
+    1024             :         {
+    1025             :                 std::vector<Variant> a;
+    1026           1 :                 a.push_back(Variant::fromDouble(1));
+    1027           1 :                 a.push_back(Variant::fromDouble(2));
+    1028           1 :                 a.push_back(Variant::fromDouble(3));
+    1029           1 :                 a.push_back(Variant::fromDouble(4));
+    1030             :                 Variant v = Variant::fromVector(a);
+    1031           1 :                 std::vector<Variant> u = v.asVector();
+    1032           1 :                 EXPECT_EQ(a[0], Variant::fromDouble(u[0]));
+    1033           1 :                 EXPECT_EQ(a[1], Variant::fromDouble(u[1]));
+    1034           1 :                 EXPECT_EQ(a[2], Variant::fromDouble(u[2]));
+    1035           1 :                 EXPECT_EQ(a[3], Variant::fromDouble(u[3]));
+    1036           1 :         }
+    1037             : 
+    1038             : 
+    1039           1 : }
+    1040             : 
+    1041           2 : TEST(Geometry, Plane) {
+    1042           1 :         Plane p(Vector3d(0,0,1), Vector3d(0,0,1));
+    1043           1 :         EXPECT_DOUBLE_EQ(-1., p.distance(Vector3d(0, 0, 0)));
+    1044           1 :         EXPECT_DOUBLE_EQ(9., p.distance(Vector3d(1, 1, 10)));
+    1045           1 : }
+    1046             : 
+    1047           2 : TEST(Geometry, Sphere) {
+    1048           1 :         Sphere s(Vector3d(0,0,0), 1.);
+    1049           1 :         EXPECT_DOUBLE_EQ(-1., s.distance(Vector3d(0, 0, 0)));
+    1050           1 :         EXPECT_DOUBLE_EQ(9., s.distance(Vector3d(10, 0, 0)));
+    1051           1 : }
+    1052             : 
+    1053           2 : TEST(Geometry, ParaxialBox) {
+    1054           1 :         ParaxialBox b(Vector3d(0,0,0), Vector3d(3,4,5));
+    1055           1 :         EXPECT_NEAR(-.1, b.distance(Vector3d(0.1, 0.1, 0.1)), 1E-10);
+    1056           1 :         EXPECT_NEAR(-.1, b.distance(Vector3d(0.1, 3.8, 0.1)), 1E-10);
+    1057           1 :         EXPECT_NEAR(-.2, b.distance(Vector3d(0.9, 3.8, 0.9)), 1E-10);
+    1058           1 :         EXPECT_NEAR(7., b.distance(Vector3d(10., 0., 0.)), 1E-10);
+    1059           1 :         EXPECT_NEAR(7., b.distance(Vector3d(10., 2., 0.)), 1E-10);
+    1060           1 :         EXPECT_NEAR(8., b.distance(Vector3d(-8., 0., 0.)), 1E-10);
+    1061           1 : }
+    1062             : 
+    1063           0 : int main(int argc, char **argv) {
+    1064           0 :         ::testing::InitGoogleTest(&argc, argv);
+    1065           0 :         return RUN_ALL_TESTS();
+    1066             : }
+    1067             : 
+    1068             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testDensity.cpp.func-sort-c.html b/doc/coverageReport/test/testDensity.cpp.func-sort-c.html new file mode 100644 index 000000000..b1eb7ef54 --- /dev/null +++ b/doc/coverageReport/test/testDensity.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testDensity.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:166166100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa31testDensityList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa31testGridDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa35testConstantDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa36testGridDensity_testRetrunValue_Test8TestBodyEv1
_ZN7crpropa41testCordes_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa43testFerriere_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa44testNakanishi_checkValueAtCertainPoints_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testDensity.cpp.func.html b/doc/coverageReport/test/testDensity.cpp.func.html new file mode 100644 index 000000000..337e954df --- /dev/null +++ b/doc/coverageReport/test/testDensity.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testDensity.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:166166100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa31testDensityList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa31testGridDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa35testConstantDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa36testGridDensity_testRetrunValue_Test8TestBodyEv1
_ZN7crpropa41testCordes_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa43testFerriere_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa44testNakanishi_checkValueAtCertainPoints_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testDensity.cpp.gcov.html b/doc/coverageReport/test/testDensity.cpp.gcov.html new file mode 100644 index 000000000..587a77d5d --- /dev/null +++ b/doc/coverageReport/test/testDensity.cpp.gcov.html @@ -0,0 +1,372 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testDensity.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:166166100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/massDistribution/Massdistribution.h"
+       2             : #include "crpropa/massDistribution/Cordes.h"
+       3             : #include "crpropa/massDistribution/Ferriere.h"
+       4             : #include "crpropa/massDistribution/Nakanishi.h"
+       5             : #include "crpropa/massDistribution/ConstantDensity.h"
+       6             : #include "crpropa/Units.h"
+       7             : #include "crpropa/Grid.h"
+       8             : 
+       9             : #include "gtest/gtest.h"
+      10             : 
+      11             : #include <stdexcept>
+      12             : #include <cmath>
+      13             : #include <string>
+      14             : 
+      15             : namespace crpropa {
+      16             : 
+      17           1 : TEST(testConstantDensity, SimpleTest) {
+      18             :         //test ConstantDensity in all types and in total density (output)
+      19           1 :         ConstantDensity n(2/ccm,3/ccm, 2/ccm);
+      20             :         Vector3d p(1*pc,2*pc,1*kpc);    // random position for testing density
+      21           1 :         EXPECT_DOUBLE_EQ(n.getHIDensity(p), 2e6);       // density output in m^-3
+      22           1 :         EXPECT_DOUBLE_EQ(n.getHIIDensity(p), 3e6);
+      23           1 :         EXPECT_DOUBLE_EQ( n.getH2Density(p), 2e6);
+      24           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p), 7e6);         // total density 2+3+2 = 7 (/ccm)
+      25           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),9e6);   // nucleon density 2+3+2*2 = 9 (/ccm) factor 2 for molecular hydrogen
+      26             : 
+      27             :         //test set/get function for used type
+      28           1 :         bool useHI = n.getIsForHI();
+      29           1 :         bool useHII= n.getIsForHII();
+      30           1 :         bool useH2 = n.getIsForH2();
+      31             :         //check if all types are activited
+      32           1 :         EXPECT_TRUE(useHI);
+      33           1 :         EXPECT_TRUE(useHII);
+      34           1 :         EXPECT_TRUE(useH2);
+      35             : 
+      36             :         //set density number to 500
+      37           1 :         n.setHI(500.);
+      38           1 :         n.setHII(500.);
+      39           1 :         n.setH2(500.);
+      40             : 
+      41             :         //check if output is changed to 500 in types and is 0 (all deactivated) for Hges
+      42           1 :         EXPECT_DOUBLE_EQ(n.getHIDensity(p), 500.);
+      43           1 :         EXPECT_DOUBLE_EQ(n.getHIIDensity(p), 500.);
+      44           1 :         EXPECT_DOUBLE_EQ(n.getH2Density(p), 500.);
+      45             : 
+      46             :         //deactivate all
+      47           1 :         n.setHI(false);
+      48           1 :         n.setHII(false);
+      49           1 :         n.setH2(false);
+      50             : 
+      51             :         //check if all isfor are set to false
+      52           1 :         useHI = n.getIsForHI();
+      53           1 :         useHII= n.getIsForHII();
+      54           1 :         useH2 = n.getIsForH2();
+      55           1 :         EXPECT_FALSE(useHI);
+      56           1 :         EXPECT_FALSE(useHII);
+      57           1 :         EXPECT_FALSE(useH2);
+      58             : 
+      59             :         //get<type>Density is independent of type activation, getDensity is not independent
+      60             :         //check if getDensity returns 0. (should give a error message in log file)
+      61           1 :         ::testing::internal::CaptureStderr();
+      62           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p), 0);
+      63           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),0);
+      64           1 :         std::string captured = testing::internal::GetCapturedStderr();
+      65           1 :         EXPECT_NE(captured.find("WARNING"), std::string::npos);
+      66           1 : }
+      67             : 
+      68             : 
+      69           2 : TEST(testDensityList, SimpleTest) {
+      70             : 
+      71             :         DensityList MS;
+      72           1 :         MS.addDensity(new ConstantDensity(1,1,2));      //sum 4
+      73           2 :         MS.addDensity(new ConstantDensity(2,3,1));      //sum 6
+      74             : 
+      75             :         Vector3d p(50*pc,10*pc,-30*pc); //random position for testing density
+      76           1 :         EXPECT_DOUBLE_EQ(MS.getHIDensity(p),3);
+      77           1 :         EXPECT_DOUBLE_EQ(MS.getHIIDensity(p),4);
+      78           1 :         EXPECT_DOUBLE_EQ(MS.getH2Density(p),3);
+      79           1 :         EXPECT_DOUBLE_EQ(MS.getDensity(p),10);  //sum of sums
+      80           1 :         EXPECT_DOUBLE_EQ(MS.getNucleonDensity(p),13);   // 3+4+2*3 factor 2 for molecular hydrogen
+      81             : 
+      82           1 : }
+      83             : 
+      84           2 : TEST(testCordes, checkValueAtCertainPoints) {
+      85             : 
+      86             :         Cordes n;
+      87             : 
+      88             :         //check type Information
+      89           1 :         EXPECT_FALSE(n.getIsForHI());
+      90           1 :         EXPECT_TRUE(n.getIsForHII());
+      91           1 :         EXPECT_FALSE(n.getIsForH2());
+      92             : 
+      93             :         Vector3d p(3.1*kpc,2.9*kpc,-30*pc);     //position for testing density
+      94             : 
+      95           1 :         EXPECT_NEAR(n.getHIIDensity(p), 184500.,1);     // output in m^-3 ; uncertainty of 1e-6 cm^-3
+      96           1 :         EXPECT_NEAR(n.getDensity(p), 184500.,1);
+      97           1 :         EXPECT_NEAR(n.getNucleonDensity(p), 184500,1);  // only HII component -> no differenz between density and nucleon density
+      98           1 :         p.z=30*pc;                      // invariant density for +/- z
+      99           1 :         EXPECT_NEAR(n.getDensity(p),184500,1);
+     100             : 
+     101           1 : }
+     102             : 
+     103           2 : TEST(testNakanishi, checkValueAtCertainPoints) {
+     104             : 
+     105             :         Nakanishi n;
+     106             : 
+     107             :         //check type Information
+     108           1 :         EXPECT_TRUE(n.getIsForHI());
+     109           1 :         EXPECT_FALSE(n.getIsForHII());
+     110           1 :         EXPECT_TRUE(n.getIsForH2());
+     111             : 
+     112             :         //first position for testing density
+     113             :         Vector3d p(4*kpc,-2.5*kpc,-0.85*kpc);
+     114             : 
+     115             :         //testing HI component
+     116           1 :         EXPECT_NEAR(n.getHIPlanedensity(p),162597,1);   //uncertaincy of 1e-6 cm^-3
+     117           1 :         EXPECT_NEAR(n.getHIScaleheight(p),0.3109*kpc,0.1*pc);
+     118           1 :         EXPECT_NEAR(n.getHIDensity(p),914,1);   //uncertainc 1e-6 cm^-3
+     119             : 
+     120             :         //testing H2 compontent
+     121           1 :         EXPECT_NEAR(n.getH2Planedensity(p),741999,1); //uncertaincy of 1e-6 cm^-3
+     122           1 :         EXPECT_NEAR(n.getH2Scaleheight(p),88.2*pc,0.1*pc);
+     123           1 :         EXPECT_NEAR(n.getH2Density(p),0,1);
+     124             : 
+     125             :         //testing total Density
+     126           1 :         EXPECT_NEAR(n.getDensity(p),914,2); //double uncertaincy for both type á 1cm^-3
+     127           1 :         EXPECT_NEAR(n.getNucleonDensity(p),914,2);      // 914 + 0*2    factor 2 for molecular hydrogen
+     128             : 
+     129             :         //second position for testing density
+     130             :         p = Vector3d(50*pc,100*pc,10*pc);
+     131             : 
+     132             :         //testing HI component
+     133           1 :         EXPECT_NEAR(n.getHIPlanedensity(p),543249,1);
+     134           1 :         EXPECT_NEAR(n.getHIScaleheight(p),125.6*pc,0.1*pc);
+     135           1 :         EXPECT_NEAR(n.getHIDensity(p),540867,1);
+     136             : 
+     137             :         //testing H2 component
+     138           1 :         EXPECT_NEAR(n.getH2Planedensity(p),10556748,1);
+     139           1 :         EXPECT_NEAR(n.getH2Scaleheight(p),57.2*pc,0.1*pc);
+     140           1 :         EXPECT_NEAR(n.getH2Density(p),10335137,1);
+     141             : 
+     142             :         //testing total Density
+     143           1 :         EXPECT_NEAR(n.getDensity(p),10876004,2);
+     144           1 :         EXPECT_NEAR(n.getNucleonDensity(p),21211141,2); // factor 2 in molecular hydrogen
+     145             : 
+     146             :         //test set type function
+     147           1 :         n.setIsForHI(false);
+     148           1 :         EXPECT_FALSE(n.getIsForHI());
+     149           1 :         EXPECT_TRUE(n.getIsForH2());
+     150             : 
+     151           1 :         n.setIsForH2(false);
+     152           1 :         EXPECT_FALSE(n.getIsForHI());
+     153           1 :         EXPECT_FALSE(n.getIsForH2());
+     154             : 
+     155             :         //check if density output is zero if all density-types are deaktivated (should give warning in log-file)
+     156           1 :         ::testing::internal::CaptureStderr();
+     157           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p),0);
+     158           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),0);
+     159           1 :         std::string captured = testing::internal::GetCapturedStderr();
+     160           1 :         EXPECT_NE(captured.find("WARNING"), std::string::npos);
+     161             : 
+     162           1 : }
+     163             : 
+     164           1 : TEST(testFerriere, checkValueAtCertainPoints) {
+     165           1 :         ::testing::internal::CaptureStderr();
+     166             :         Ferriere n;
+     167             : 
+     168             :         //check type information
+     169             : 
+     170           1 :         EXPECT_TRUE(n.getIsForHI());
+     171           1 :         EXPECT_TRUE(n.getIsForHII());
+     172           1 :         EXPECT_TRUE(n.getIsForH2());
+     173             : 
+     174             :         //testing density in inner Ring (R <= 3*kpc)
+     175             :         Vector3d p(60*pc,-60*pc,-20*pc);        //testing position in region of CMZ
+     176             : 
+     177             :         //test CMZ Trafo
+     178             :         Vector3d Trafo;
+     179           1 :         Trafo = n.CMZTransformation(p);
+     180           1 :         EXPECT_NEAR(Trafo.x,5.9767*pc,1e-4*pc);
+     181           1 :         EXPECT_NEAR(Trafo.y,12.8171*pc,1e-4*pc);
+     182           1 :         EXPECT_DOUBLE_EQ(Trafo.z,p.z);  //no transformation in z component
+     183             : 
+     184             :         //test DISK Trafo
+     185           1 :         Trafo = n.DiskTransformation(p);
+     186           1 :         EXPECT_NEAR(Trafo.x,11.0660*pc,1e-4*pc);
+     187           1 :         EXPECT_NEAR(Trafo.y,82.5860*pc,1e-4*pc);
+     188           1 :         EXPECT_NEAR(Trafo.z,-25.6338*pc,1e-4*pc);
+     189             : 
+     190             :         //testing density
+     191           1 :         EXPECT_NEAR(n.getHIDensity(p),6237723,1);       //uncertaincy 1e-6 cm^-3
+     192           1 :         EXPECT_NEAR(n.getH2Density(p),35484825,1);
+     193           1 :         EXPECT_NEAR(n.getHIIDensity(p),6243793,1);
+     194           1 :         EXPECT_NEAR(n.getDensity(p),47966341,1);
+     195           1 :         EXPECT_NEAR(n.getNucleonDensity(p),83451166,2);         //factor 2 in molecular hydrogen; double uncertaincy
+     196             : 
+     197             :         Vector3d p2(-500*pc,-900*pc,35*pc);     //testing position in region of the DISK
+     198           1 :         EXPECT_NEAR(n.getHIIDensity(p2),48190,1);
+     199           1 :         EXPECT_NEAR(n.getHIDensity(p2),5,1);
+     200           1 :         EXPECT_NEAR(n.getH2Density(p2),0,1);
+     201           1 :         EXPECT_NEAR(n.getDensity(p2),48195,1);
+     202           1 :         EXPECT_NEAR(n.getNucleonDensity(p2),48195,1);   // no H2 component -> no difference between density and nucleon-density
+     203             : 
+     204             :         //testing the outer region R>3kpc
+     205             :         Vector3d p3(5*kpc,4*kpc,-29*pc);        //testing position with 3kpc < R < R_sun
+     206           1 :         EXPECT_NEAR(n.getHIDensity(p3),540607,1);
+     207           1 :         EXPECT_NEAR(n.getHIIDensity(p3),66495 ,1);
+     208           1 :         EXPECT_NEAR(n.getH2Density(p3),2492685,1);
+     209           1 :         EXPECT_NEAR(n.getDensity(p3),3099787,1);
+     210           1 :         EXPECT_NEAR(n.getNucleonDensity(p3), 5592472,1);
+     211             : 
+     212             :         Vector3d p4(10*kpc,2*kpc,50*pc);        //testing position with R > R_sun
+     213           1 :         EXPECT_NEAR(n.getHIDensity(p4),431294,1);
+     214           1 :         EXPECT_NEAR(n.getHIIDensity(p4),22109,1);
+     215           1 :         EXPECT_NEAR(n.getH2Density(p4),54099,1);
+     216           1 :         EXPECT_NEAR(n.getDensity(p4),507502,1);
+     217           1 :         EXPECT_NEAR(n.getNucleonDensity(p4),561601,1);
+     218             : 
+     219             :         //test get/set type function
+     220           1 :         n.setIsForHI(false);
+     221           1 :         EXPECT_FALSE(n.getIsForHI());
+     222           1 :         EXPECT_TRUE(n.getIsForHII());
+     223           1 :         EXPECT_TRUE(n.getIsForH2());
+     224             : 
+     225           1 :         n.setIsForHII(false);
+     226           1 :         EXPECT_FALSE(n.getIsForHI());
+     227           1 :         EXPECT_FALSE(n.getIsForHII());
+     228           1 :         EXPECT_TRUE(n.getIsForH2());
+     229             : 
+     230           1 :         n.setIsForH2(false);
+     231           1 :         EXPECT_FALSE(n.getIsForHI());
+     232           1 :         EXPECT_FALSE(n.getIsForHII());
+     233           1 :         EXPECT_FALSE(n.getIsForH2());
+     234             : 
+     235             :         //check if density is set to zero if all types are deactivated (should give warning in log-file)
+     236           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p),0);
+     237           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),0);
+     238           1 :         std::string captured = testing::internal::GetCapturedStderr();
+     239           1 :         EXPECT_NE(captured.find("WARNING"), std::string::npos);
+     240           1 : }
+     241             : 
+     242           2 : TEST(testGridDensity, SimpleTest) {
+     243           1 :         ref_ptr<Grid1f> grid = new Grid1f(Vector3d(0.), 1, 1, 1, 1.);     
+     244           1 :         DensityGrid dens = DensityGrid(grid, true, false, false);
+     245             : 
+     246             :         // check active types
+     247           1 :         EXPECT_TRUE(dens.getIsForHI()); 
+     248           1 :         EXPECT_FALSE(dens.getIsForHII());
+     249           1 :         EXPECT_FALSE(dens.getIsForH2());
+     250             : 
+     251             :         // check set function
+     252           1 :         dens.setIsForH2(true);
+     253           1 :         EXPECT_TRUE(dens.getIsForH2());
+     254             : 
+     255           1 :         dens.setIsForHII(true);
+     256           1 :         EXPECT_TRUE(dens.getIsForHII());
+     257             : 
+     258           1 :         dens.setIsForHI(false);
+     259           1 :         EXPECT_FALSE(dens.getIsForHI());
+     260           1 : }
+     261             : 
+     262           2 : TEST(testGridDensity, testRetrunValue) {
+     263             :         size_t Nx = 5;
+     264             :         size_t Ny = 8;
+     265             :         size_t Nz = 10;
+     266             :         double spacing = 2.0;
+     267             :         Vector3d origin(1., 2., 3.);
+     268             : 
+     269           1 :         ref_ptr<Grid1f> grid = new Grid1f(origin, Nx, Ny, Nz, spacing);
+     270             : 
+     271             :         // set some values for the grid
+     272           1 :         grid->get(3, 2, 4) = 5;
+     273           1 :         grid->get(3, 2, 5) = 12;
+     274           1 :         grid->get(2, 3, 4) = 6;
+     275             : 
+     276           2 :         DensityGrid dens = DensityGrid(grid, true, false, false);
+     277             : 
+     278             :         // a point in the region where values are defined for the grid.
+     279             :         Vector3d position = origin + Vector3d(2.2, 2.8, 4.1) * spacing; 
+     280           1 :         double valueFromGrid =  grid->interpolate(position);
+     281           1 :         double nHI = dens.getHIDensity(position);
+     282           1 :         double nHII = dens.getHIIDensity(position);
+     283           1 :         double nH2 = dens.getH2Density(position);
+     284           1 :         double nNucleon = dens.getNucleonDensity(position);
+     285           1 :         double nTotal = dens.getDensity(position);
+     286             : 
+     287             :         // Check for values
+     288           1 :         EXPECT_DOUBLE_EQ(valueFromGrid, nHI);
+     289           1 :         EXPECT_DOUBLE_EQ(nHII, 0);      // HII is set to false and should be 0
+     290           1 :         EXPECT_DOUBLE_EQ(nH2, 0);       // H2 is set to false and should be 0
+     291           1 :         EXPECT_DOUBLE_EQ(nNucleon, valueFromGrid);
+     292           1 :         EXPECT_DOUBLE_EQ(nTotal, valueFromGrid);
+     293           1 : }
+     294             : 
+     295             : 
+     296             : } //namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html b/doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html new file mode 100644 index 000000000..1eaa671c2 --- /dev/null +++ b/doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testFunctionalGroups.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testFunctionalGroups.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:202387.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa36testFunctionalGroups_gyroradius_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testFunctionalGroups.cpp.func.html b/doc/coverageReport/test/testFunctionalGroups.cpp.func.html new file mode 100644 index 000000000..24b5d5269 --- /dev/null +++ b/doc/coverageReport/test/testFunctionalGroups.cpp.func.html @@ -0,0 +1,80 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testFunctionalGroups.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testFunctionalGroups.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:202387.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ +
+ + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa36testFunctionalGroups_gyroradius_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html b/doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html new file mode 100644 index 000000000..e6bdc1708 --- /dev/null +++ b/doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html @@ -0,0 +1,126 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testFunctionalGroups.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testFunctionalGroups.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:202387.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "CRPropa.h"
+       2             : #include "gtest/gtest.h"
+       3             : 
+       4             : namespace crpropa {
+       5             : 
+       6             : /*
+       7             :  * Functional test which calculates the particle's gyroradius in a uniform field
+       8             :  * r_g = R / (B*c) = 1 EV / (1 nG * c) \approx 1.08*Mpc
+       9             :  */
+      10           2 : TEST(testFunctionalGroups, gyroradius) {
+      11             :         double energy = 1*EeV;
+      12             :         double field = 1*nG;
+      13             : 
+      14           1 :         ParticleState p;
+      15           1 :         p.setId(nucleusId(1, 1));
+      16           1 :         p.setEnergy(energy);
+      17           1 :         p.setPosition(Vector3d(0, 0, 0));
+      18           1 :         p.setDirection(Vector3d(0, 0, 1));
+      19             : 
+      20           1 :         ref_ptr<Candidate> c = new Candidate(p);
+      21           1 :         ref_ptr<PropagationCK> propa = new PropagationCK(new UniformMagneticField(Vector3d(field, 0, 0)));
+      22           1 :         ref_ptr<ParticleCollector> collector = new ParticleCollector();
+      23           1 :         collector->setClone(true);
+      24           1 :         ref_ptr<ModuleList> sim = new ModuleList();
+      25             : 
+      26             :         Vector3d pos;
+      27             :         double max_y = 0;
+      28             : 
+      29           1 :         sim->add(propa);
+      30           1 :         sim->add(new MaximumTrajectoryLength(10*Mpc));
+      31           1 :         sim->add(collector);
+      32             : 
+      33           1 :         sim->run(c);
+      34             : 
+      35          16 :         for (ParticleCollector::iterator itr = collector->begin(); itr != collector->end(); ++itr){
+      36          15 :                 pos = (*(itr->get())).current.getPosition();
+      37          15 :                 if (max_y < pos.getY())
+      38             :                         max_y = pos.getY();
+      39             :         }
+      40             : 
+      41           1 :         EXPECT_NEAR(max_y/2.0, energy/(field * c_light * eplus), 0.01*Mpc);
+      42             : 
+      43           1 : }
+      44             : 
+      45           0 : int main(int argc, char **argv) {
+      46           0 :         ::testing::InitGoogleTest(&argc, argv);
+      47           0 :         return RUN_ALL_TESTS();
+      48             : }
+      49             : 
+      50             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testInteraction.cpp.func-sort-c.html b/doc/coverageReport/test/testInteraction.cpp.func-sort-c.html new file mode 100644 index 000000000..e28ec63a0 --- /dev/null +++ b/doc/coverageReport/test/testInteraction.cpp.func-sort-c.html @@ -0,0 +1,284 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testInteraction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testInteraction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:74378794.4 %
Date:2024-04-08 14:58:22Functions:525398.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa24Redshift_simpleTest_Test8TestBodyEv1
_ZN7crpropa25NuclearDecay_helium5_Test8TestBodyEv1
_ZN7crpropa26NuclearDecay_lithium4_Test8TestBodyEv1
_ZN7crpropa28NuclearDecay_scandium44_Test8TestBodyEv1
_ZN7crpropa29NuclearDecay_secondaries_Test8TestBodyEv1
_ZN7crpropa29PhotoDisintegration_iron_Test8TestBodyEv1
_ZN7crpropa31NuclearDecay_limitNextStep_Test8TestBodyEv1
_ZN7crpropa31PhotoDisintegration_carbon_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_helium_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_proton_Test8TestBodyEv1
_ZN7crpropa32NuclearDecay_interactionTag_Test8TestBodyEv1
_ZN7crpropa33EMPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa33PhotoPionProduction_sampling_Test8TestBodyEv1
_ZN7crpropa34ElasticScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa35EMPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa35Redshift_limitRedshiftDecrease_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_allChannelsWorking_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa36PhotoDisintegration_allIsotopes_Test8TestBodyEv1
_ZN7crpropa36PhotoPionProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa37ElasticScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesCMB_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesIRB_Test8TestBodyEv1
_ZN7crpropa38PhotoDisintegration_limitNextStep_Test8TestBodyEv1
_ZN7crpropa38PhotoPionProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa39EMDoublePairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_interactionTag_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa40EMTripletPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa40SynchrotronRadiation_interactionTag_Test8TestBodyEv1
_ZN7crpropa41EMDoublePairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa42EMTripletPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43EMInverseComptonScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43PhotoDisintegration_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa43PhotoPionProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa44ElectronPairProduction_energyDecreasing_Test8TestBodyEv1
_ZN7crpropa45EMInverseComptonScattering_limitNextStep_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_interactionTag_Test8TestBodyEv1
_ZN7crpropa46ElectronPairProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa47ElectronPairProduction_belowEnergyTreshold_Test8TestBodyEv1
_ZN7crpropa55Photodisintegration_updateParticleParentProperties_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testInteraction.cpp.func.html b/doc/coverageReport/test/testInteraction.cpp.func.html new file mode 100644 index 000000000..ded452dfc --- /dev/null +++ b/doc/coverageReport/test/testInteraction.cpp.func.html @@ -0,0 +1,284 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testInteraction.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testInteraction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:74378794.4 %
Date:2024-04-08 14:58:22Functions:525398.1 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa24Redshift_simpleTest_Test8TestBodyEv1
_ZN7crpropa25NuclearDecay_helium5_Test8TestBodyEv1
_ZN7crpropa26NuclearDecay_lithium4_Test8TestBodyEv1
_ZN7crpropa28NuclearDecay_scandium44_Test8TestBodyEv1
_ZN7crpropa29NuclearDecay_secondaries_Test8TestBodyEv1
_ZN7crpropa29PhotoDisintegration_iron_Test8TestBodyEv1
_ZN7crpropa31NuclearDecay_limitNextStep_Test8TestBodyEv1
_ZN7crpropa31PhotoDisintegration_carbon_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_helium_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_proton_Test8TestBodyEv1
_ZN7crpropa32NuclearDecay_interactionTag_Test8TestBodyEv1
_ZN7crpropa33EMPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa33PhotoPionProduction_sampling_Test8TestBodyEv1
_ZN7crpropa34ElasticScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa35EMPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa35Redshift_limitRedshiftDecrease_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_allChannelsWorking_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa36PhotoDisintegration_allIsotopes_Test8TestBodyEv1
_ZN7crpropa36PhotoPionProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa37ElasticScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesCMB_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesIRB_Test8TestBodyEv1
_ZN7crpropa38PhotoDisintegration_limitNextStep_Test8TestBodyEv1
_ZN7crpropa38PhotoPionProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa39EMDoublePairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_interactionTag_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa40EMTripletPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa40SynchrotronRadiation_interactionTag_Test8TestBodyEv1
_ZN7crpropa41EMDoublePairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa42EMTripletPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43EMInverseComptonScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43PhotoDisintegration_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa43PhotoPionProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa44ElectronPairProduction_energyDecreasing_Test8TestBodyEv1
_ZN7crpropa45EMInverseComptonScattering_limitNextStep_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_interactionTag_Test8TestBodyEv1
_ZN7crpropa46ElectronPairProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa47ElectronPairProduction_belowEnergyTreshold_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
_ZN7crpropa55Photodisintegration_updateParticleParentProperties_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testInteraction.cpp.gcov.html b/doc/coverageReport/test/testInteraction.cpp.gcov.html new file mode 100644 index 000000000..a903e964c --- /dev/null +++ b/doc/coverageReport/test/testInteraction.cpp.gcov.html @@ -0,0 +1,1229 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testInteraction.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testInteraction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:74378794.4 %
Date:2024-04-08 14:58:22Functions:525398.1 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Candidate.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/PhotonBackground.h"
+       5             : #include "crpropa/module/ElectronPairProduction.h"
+       6             : #include "crpropa/module/NuclearDecay.h"
+       7             : #include "crpropa/module/PhotoDisintegration.h"
+       8             : #include "crpropa/module/ElasticScattering.h"
+       9             : #include "crpropa/module/PhotoPionProduction.h"
+      10             : #include "crpropa/module/Redshift.h"
+      11             : #include "crpropa/module/EMPairProduction.h"
+      12             : #include "crpropa/module/EMDoublePairProduction.h"
+      13             : #include "crpropa/module/EMTripletPairProduction.h"
+      14             : #include "crpropa/module/EMInverseComptonScattering.h"
+      15             : #include "crpropa/module/SynchrotronRadiation.h"
+      16             : #include "gtest/gtest.h"
+      17             : 
+      18             : #include <fstream>
+      19             : 
+      20             : namespace crpropa {
+      21             : 
+      22             : // ElectronPairProduction -----------------------------------------------------
+      23           1 : TEST(ElectronPairProduction, allBackgrounds) {
+      24             :         // Test if interaction data files are loaded.
+      25           1 :         ref_ptr<PhotonField> cmb = new CMB();
+      26           1 :         ElectronPairProduction epp(cmb);
+      27           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+      28           1 :         epp.setPhotonField(irb);
+      29           2 :         irb = new IRB_Stecker05();
+      30           1 :         epp.setPhotonField(irb);
+      31           2 :         irb = new IRB_Franceschini08();
+      32           1 :         epp.setPhotonField(irb);
+      33           2 :         irb = new IRB_Finke10();
+      34           1 :         epp.setPhotonField(irb);
+      35           2 :         irb = new IRB_Dominguez11();
+      36           1 :         epp.setPhotonField(irb);
+      37           2 :         irb = new IRB_Gilmore12();
+      38           1 :         epp.setPhotonField(irb);
+      39           2 :         irb = new IRB_Stecker16_upper();
+      40           1 :         epp.setPhotonField(irb);
+      41           2 :         irb = new IRB_Stecker16_lower();
+      42           1 :         epp.setPhotonField(irb);
+      43           2 :     irb = new IRB_Finke22();
+      44           2 :         epp.setPhotonField(irb);
+      45           2 : }
+      46             : 
+      47           1 : TEST(ElectronPairProduction, energyDecreasing) {
+      48             :         // Test if energy loss occurs for protons with energies from 1e15 - 1e23 eV.
+      49           1 :         Candidate c;
+      50           1 :         c.setCurrentStep(2 * Mpc);
+      51           1 :         c.current.setId(nucleusId(1, 1)); // proton
+      52             : 
+      53           1 :         ref_ptr<PhotonField> cmb = new CMB();
+      54           1 :         ElectronPairProduction epp1(cmb);
+      55          81 :         for (int i = 0; i < 80; i++) {
+      56          80 :                 double E = pow(10, 15 + i * 0.1) * eV;
+      57          80 :                 c.current.setEnergy(E);
+      58          80 :                 epp1.process(&c);
+      59          80 :                 EXPECT_LE(c.current.getEnergy(), E);
+      60             :         }
+      61             : 
+      62           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+      63           2 :         ElectronPairProduction epp2(irb);
+      64          81 :         for (int i = 0; i < 80; i++) {
+      65          80 :                 double E = pow(10, 15 + i * 0.1) * eV;
+      66          80 :                 c.current.setEnergy(E);
+      67          80 :                 epp2.process(&c);
+      68          80 :                 EXPECT_LE(c.current.getEnergy(), E);
+      69             :         }
+      70           2 : }
+      71             : 
+      72           1 : TEST(ElectronPairProduction, belowEnergyTreshold) {
+      73             :         // Test if nothing happens below 1e15 eV.
+      74           1 :         ref_ptr<PhotonField> cmb = new CMB();
+      75           1 :         ElectronPairProduction epp(cmb);
+      76           1 :         Candidate c(nucleusId(1, 1), 1E14 * eV);
+      77           1 :         epp.process(&c);
+      78           1 :         EXPECT_DOUBLE_EQ(1E14 * eV, c.current.getEnergy());
+      79           2 : }
+      80             : 
+      81           1 : TEST(ElectronPairProduction, thisIsNotNucleonic) {
+      82             :         // Test if non-nuclei are skipped.
+      83           1 :         ref_ptr<PhotonField> cmb = new CMB();
+      84           1 :         ElectronPairProduction epp(cmb);
+      85           1 :         Candidate c(11, 1E20 * eV);  // electron
+      86           1 :         epp.process(&c);
+      87           1 :         EXPECT_DOUBLE_EQ(1E20 * eV, c.current.getEnergy());
+      88           2 : }
+      89             : 
+      90           2 : TEST(ElectronPairProduction, valuesCMB) {
+      91             :         // Test if energy loss corresponds to the data table.
+      92             :         std::vector<double> x;
+      93             :         std::vector<double> y;
+      94           2 :         std::ifstream infile(getDataPath("pair_CMB.txt").c_str());
+      95           1 :         while (infile.good()) {
+      96           0 :                 if (infile.peek() != '#') {
+      97             :                         double a, b;
+      98             :                         infile >> a >> b;
+      99           0 :                         if (infile) {
+     100           0 :                                 x.push_back(a * eV);
+     101           0 :                                 y.push_back(b * eV / Mpc);
+     102             :                         }
+     103             :                 }
+     104           0 :                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+     105             :         }
+     106           1 :         infile.close();
+     107             : 
+     108           1 :         Candidate c;
+     109           1 :         c.setCurrentStep(1 * Mpc);
+     110           1 :         c.current.setId(nucleusId(1, 1)); // proton
+     111           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     112             : 
+     113           1 :         ElectronPairProduction epp(cmb);
+     114           1 :         for (int i = 0; i < x.size(); i++) {
+     115           0 :                 c.current.setEnergy(x[i]);
+     116           0 :                 epp.process(&c);
+     117           0 :                 double dE = x[i] - c.current.getEnergy();
+     118           0 :                 double dE_table = y[i] * 1 * Mpc;
+     119           0 :                 EXPECT_NEAR(dE_table, dE, 1e-12);
+     120             :         }
+     121           3 : }
+     122             : 
+     123           1 : TEST(ElectronPairProduction, interactionTag) {
+     124             :         
+     125           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     126           0 :         ElectronPairProduction epp(cmb);
+     127             :         
+     128             :         // test the default interaction tag
+     129           2 :         EXPECT_TRUE(epp.getInteractionTag() == "EPP");
+     130             : 
+     131             :         // test changing the interaction tag
+     132           1 :         epp.setInteractionTag("myTag");
+     133           2 :         EXPECT_TRUE(epp.getInteractionTag() == "myTag");
+     134             : 
+     135             :         // test the tag of produced secondaries
+     136           2 :         Candidate c;
+     137           1 :         c.setCurrentStep(1 * Gpc);
+     138           1 :         c.current.setId(nucleusId(1,1));
+     139           1 :         c.current.setEnergy(100 * EeV);
+     140           1 :         epp.setHaveElectrons(true);
+     141           1 :         epp.process(&c);
+     142             :         
+     143           1 :         std::string secondaryTag = c.secondaries[0] -> getTagOrigin();
+     144           1 :         EXPECT_TRUE(secondaryTag == "myTag");
+     145           2 : }
+     146             : 
+     147           2 : TEST(ElectronPairProduction, valuesIRB) {
+     148             :         // Test if energy loss corresponds to the data table.
+     149             :         std::vector<double> x;
+     150             :         std::vector<double> y;
+     151           2 :         std::ifstream infile(getDataPath("pairIRB.txt").c_str());
+     152           1 :         while (infile.good()) {
+     153           0 :                 if (infile.peek() != '#') {
+     154             :                         double a, b;
+     155             :                         infile >> a >> b;
+     156           0 :                         if (infile) {
+     157           0 :                                 x.push_back(a * eV);
+     158           0 :                                 y.push_back(b * eV / Mpc);
+     159             :                         }
+     160             :                 }
+     161           0 :                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+     162             :         }
+     163           1 :         infile.close();
+     164             : 
+     165           1 :         Candidate c;
+     166           1 :         c.setCurrentStep(1 * Mpc);
+     167           1 :         c.current.setId(nucleusId(1, 1)); // proton
+     168           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+     169             : 
+     170           1 :         ElectronPairProduction epp(irb);
+     171           1 :         for (int i = 0; i < x.size(); i++) {
+     172           0 :                 c.current.setEnergy(x[i]);
+     173           0 :                 epp.process(&c);
+     174           0 :                 double dE = x[i] - c.current.getEnergy();
+     175           0 :                 double dE_table = y[i] * 1 * Mpc;
+     176           0 :                 EXPECT_NEAR(dE, dE_table, 1e-12);
+     177             :         }
+     178           3 : }
+     179             : 
+     180             : // NuclearDecay ---------------------------------------------------------------
+     181           1 : TEST(NuclearDecay, scandium44) {
+     182             :         // Test beta+ decay of 44Sc to 44Ca.
+     183             :         // This test can stochastically fail.
+     184           1 :         NuclearDecay d(true, true);
+     185           1 :         Candidate c(nucleusId(44, 21), 1E18 * eV);
+     186           1 :         c.setCurrentStep(100 * Mpc);
+     187           1 :         double gamma = c.current.getLorentzFactor();
+     188           1 :         d.process(&c);
+     189             :         
+     190             :         // expected decay product: 44Ca
+     191           1 :         EXPECT_EQ(nucleusId(44, 20), c.current.getId());
+     192             : 
+     193             :         // expect Lorentz factor to be conserved
+     194           1 :         EXPECT_DOUBLE_EQ(gamma, c.current.getLorentzFactor());
+     195             :         
+     196             :         // expect at least two secondaries: positron + electron neutrino
+     197           1 :         EXPECT_GE(c.secondaries.size(), 2);
+     198           1 : }
+     199             : 
+     200           1 : TEST(NuclearDecay, lithium4) {
+     201             :         // Test proton dripping of Li-4 to He-3
+     202             :         // This test can stochastically fail
+     203           1 :         NuclearDecay d;
+     204           1 :         Candidate c(nucleusId(4, 3), 4 * EeV);
+     205           1 :         c.setCurrentStep(100 * Mpc);
+     206           1 :         d.process(&c);
+     207             :         
+     208             :         // expected decay product: He-3
+     209           1 :         EXPECT_EQ(nucleusId(3, 2), c.current.getId());
+     210             : 
+     211             :         // expected secondary: proton
+     212           1 :         EXPECT_EQ(1, c.secondaries.size());
+     213           2 :         Candidate c1 = *c.secondaries[0];
+     214           1 :         EXPECT_EQ(nucleusId(1, 1), c1.current.getId());
+     215           1 :         EXPECT_EQ(1 * EeV, c1.current.getEnergy());
+     216           1 : }
+     217             : 
+     218           1 : TEST(NuclearDecay, helium5) {
+     219             :         // Test neutron dripping of He-5 to He-4.
+     220             :         // This test can stochastically fail.
+     221           1 :         NuclearDecay d;
+     222           1 :         Candidate c(nucleusId(5, 2), 5 * EeV);
+     223           1 :         c.setCurrentStep(100 * Mpc);
+     224           1 :         d.process(&c);
+     225             : 
+     226             :         // expected primary: He-4
+     227           1 :         EXPECT_EQ(nucleusId(4, 2), c.current.getId());
+     228           1 :         EXPECT_EQ(4, c.current.getEnergy() / EeV);
+     229             :         
+     230             :         // expected secondary: neutron
+     231           2 :         Candidate c2 = *c.secondaries[0];
+     232           1 :         EXPECT_EQ(nucleusId(1, 0), c2.current.getId());
+     233           1 :         EXPECT_EQ(1, c2.current.getEnergy() / EeV);
+     234           1 : }
+     235             : 
+     236           1 : TEST(NuclearDecay, limitNextStep) {
+     237             :         // Test if next step is limited in case of a neutron.
+     238           1 :         NuclearDecay decay;
+     239           1 :         Candidate c(nucleusId(1, 0), 10 * EeV);
+     240           1 :         c.setNextStep(std::numeric_limits<double>::max());
+     241           1 :         decay.process(&c);
+     242           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
+     243           1 : }
+     244             : 
+     245           1 : TEST(NuclearDecay, allChannelsWorking) {
+     246             :         // Test if all nuclear decays are working.
+     247           1 :         NuclearDecay d;
+     248           1 :         Candidate c;
+     249             : 
+     250           2 :         std::ifstream infile(getDataPath("nuclear_decay.txt").c_str());
+     251         951 :         while (infile.good()) {
+     252         950 :                 if (infile.peek() != '#') {
+     253             :                         int Z, N, channel, foo;
+     254         948 :                         infile >> Z >> N >> channel >> foo;
+     255         948 :                         c.current.setId(nucleusId(Z + N, Z));
+     256         948 :                         c.current.setEnergy(80 * EeV);
+     257         948 :                         d.performInteraction(&c, channel);
+     258             :                 }
+     259         950 :                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
+     260             :         }
+     261           1 :         infile.close();
+     262           1 : }
+     263             : 
+     264           1 : TEST(NuclearDecay, secondaries) {
+     265             :         // Test if all types of secondaries are produced.
+     266           1 :         NuclearDecay d;
+     267           1 :         d.setHaveElectrons(true);
+     268           1 :         d.setHaveNeutrinos(true);
+     269           1 :         d.setHavePhotons(true);
+     270           1 :         Candidate c;
+     271             : 
+     272             :         // He-8 --> Li-8 + e- + neutrino
+     273             :         // additional photon emitted with 84% probability
+     274             :         // --> expect at least 1 photon out of 10 decays
+     275          11 :         for (int i = 0; i < 10; ++i) {
+     276          10 :                 c.current.setId(nucleusId(8, 2));
+     277          10 :                 c.current.setEnergy(5 * EeV);
+     278          10 :                 d.performInteraction(&c, 10000);
+     279             :         }
+     280             : 
+     281             :         // count number of secondaries
+     282           1 :         size_t nElectrons = 0;
+     283           1 :         size_t nNeutrinos = 0;
+     284           1 :         size_t nPhotons = 0;
+     285             : 
+     286          30 :         for(size_t i = 0; i < c.secondaries.size(); ++i) {
+     287          29 :                 int id = (*c.secondaries[i]).current.getId();
+     288          29 :                 if (id == 22) nPhotons++;
+     289          29 :                 if (id == 11) nElectrons++;
+     290          29 :                 if (id == -12) nNeutrinos++;
+     291             :         }
+     292             : 
+     293           1 :         EXPECT_EQ(nElectrons, 10);
+     294           1 :         EXPECT_EQ(nNeutrinos, 10);
+     295           1 :         EXPECT_GE(nPhotons, 1);
+     296           1 : }
+     297             : 
+     298           1 : TEST(NuclearDecay, thisIsNotNucleonic) {
+     299             :         // Test if nothing happens to an electron
+     300           1 :         NuclearDecay decay;
+     301           1 :         Candidate c(11, 10 * EeV);
+     302           1 :         c.setNextStep(std::numeric_limits<double>::max());
+     303           1 :         decay.process(&c);
+     304           1 :         EXPECT_EQ(11, c.current.getId());
+     305           1 :         EXPECT_EQ(10 * EeV, c.current.getEnergy());
+     306           1 : }
+     307             : 
+     308           1 : TEST(NuclearDecay, interactionTag) {
+     309             :         // test default interaction tag
+     310           1 :         NuclearDecay decay;
+     311           2 :         EXPECT_TRUE(decay.getInteractionTag() == "ND");
+     312             : 
+     313             :         // test secondary tag
+     314           1 :         decay.setHaveElectrons(true);
+     315           2 :         Candidate c(nucleusId(8,2), 5 * EeV);
+     316           1 :         decay.performInteraction(&c, 10000);
+     317           3 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "ND");
+     318             : 
+     319             :         // test custom tags
+     320           1 :         decay.setInteractionTag("myTag");
+     321           2 :         EXPECT_TRUE(decay.getInteractionTag() == "myTag");
+     322           1 : }
+     323             : 
+     324             : // PhotoDisintegration --------------------------------------------------------
+     325           1 : TEST(PhotoDisintegration, allBackgrounds) {
+     326             :         // Test if interaction data files are loaded.
+     327           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     328           1 :         PhotoDisintegration pd(cmb);
+     329           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+     330           1 :         pd.setPhotonField(irb);
+     331           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
+     332           1 :         pd.setPhotonField(urb);
+     333           2 :         irb = new IRB_Stecker05();
+     334           1 :         pd.setPhotonField(irb);
+     335           2 :         irb = new IRB_Franceschini08();
+     336           1 :         pd.setPhotonField(irb);
+     337           2 :         irb = new IRB_Finke10();
+     338           1 :         pd.setPhotonField(irb);
+     339           2 :         irb = new IRB_Dominguez11();
+     340           1 :         pd.setPhotonField(irb);
+     341           2 :         irb = new IRB_Gilmore12();
+     342           1 :         pd.setPhotonField(irb);
+     343           2 :         irb = new IRB_Stecker16_upper();
+     344           1 :         pd.setPhotonField(irb);
+     345           2 :         irb = new IRB_Stecker16_lower();
+     346           1 :         pd.setPhotonField(irb);
+     347           2 :     irb = new IRB_Finke22();
+     348           1 :         pd.setPhotonField(irb);
+     349           2 :         urb = new URB_Nitu21();
+     350           2 :         pd.setPhotonField(urb);
+     351           2 : }
+     352             : 
+     353           1 : TEST(PhotoDisintegration, carbon) {
+     354             :         // Test if a 100 EeV C-12 nucleus photo-disintegrates (at least once) over a distance of 1 Gpc.
+     355             :         // This test can stochastically fail.
+     356           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     357           1 :         PhotoDisintegration pd(cmb);
+     358           1 :         Candidate c;
+     359           1 :         int id = nucleusId(12, 6);
+     360           1 :         c.current.setId(id);
+     361           1 :         c.current.setEnergy(100 * EeV);
+     362           1 :         c.setCurrentStep(1000 * Mpc);
+     363           1 :         pd.process(&c);
+     364             : 
+     365           1 :         EXPECT_TRUE(c.current.getEnergy() < 100 * EeV);
+     366             :         // energy loss
+     367           1 :         EXPECT_TRUE(c.secondaries.size() > 0);
+     368             :         // secondaries produced
+     369             : 
+     370           1 :         double E = c.current.getEnergy();
+     371           1 :         id = c.current.getId();
+     372           1 :         int A = massNumber(id);
+     373           1 :         int Z = chargeNumber(id);
+     374             : 
+     375           2 :         for (int i = 0; i < c.secondaries.size(); i++) {
+     376           1 :                 E += (*c.secondaries[i]).current.getEnergy();
+     377           1 :                 id = (*c.secondaries[i]).current.getId();
+     378           1 :                 A += massNumber(id);
+     379           1 :                 Z += chargeNumber(id);
+     380             :         }
+     381           1 :         EXPECT_EQ(12, A);
+     382             :         // nucleon number conserved
+     383           1 :         EXPECT_EQ(6, Z);
+     384             :         // proton number conserved
+     385           1 :         EXPECT_DOUBLE_EQ(100 * EeV, E);
+     386             :         // energy conserved
+     387           2 : }
+     388             : 
+     389           1 : TEST(PhotoDisintegration, iron) {
+     390             :         // Test if a 200 EeV Fe-56 nucleus photo-disintegrates (at least once) over a distance of 1 Gpc.
+     391             :         // This test can stochastically fail.
+     392           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+     393           1 :         PhotoDisintegration pd(irb);
+     394           1 :         Candidate c;
+     395           1 :         int id = nucleusId(56, 26);
+     396           1 :         c.current.setId(id);
+     397           1 :         c.current.setEnergy(200 * EeV);
+     398           1 :         c.setCurrentStep(1000 * Mpc);
+     399           1 :         pd.process(&c);
+     400             : 
+     401             :         // expect energy loss
+     402           1 :         EXPECT_TRUE(c.current.getEnergy() < 200 * EeV);
+     403             :         
+     404             :         // expect secondaries produced
+     405           1 :         EXPECT_TRUE(c.secondaries.size() > 0);
+     406             : 
+     407           1 :         double E = c.current.getEnergy();
+     408           1 :         id = c.current.getId();
+     409           1 :         int A = massNumber(id);
+     410           1 :         int Z = chargeNumber(id);
+     411             : 
+     412          31 :         for (int i = 0; i < c.secondaries.size(); i++) {
+     413          30 :                 E += (*c.secondaries[i]).current.getEnergy();
+     414          30 :                 id = (*c.secondaries[i]).current.getId();
+     415          30 :                 A += massNumber(id);
+     416          30 :                 Z += chargeNumber(id);
+     417             :         }
+     418             : 
+     419             :         // nucleon number conserved
+     420           1 :         EXPECT_EQ(56, A);
+     421             :         
+     422             :         // proton number conserved (no decay active)
+     423           1 :         EXPECT_EQ(26, Z);
+     424             :         
+     425             :         // energy conserved
+     426           1 :         EXPECT_DOUBLE_EQ(200 * EeV, E);
+     427           2 : }
+     428             : 
+     429           1 : TEST(PhotoDisintegration, thisIsNotNucleonic) {
+     430             :         // Test that nothing happens to an electron.
+     431           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     432           1 :         PhotoDisintegration pd(cmb);
+     433           1 :         Candidate c;
+     434           1 :         c.setCurrentStep(1 * Mpc);
+     435           1 :         c.current.setId(11); // electron
+     436           1 :         c.current.setEnergy(10 * EeV);
+     437           1 :         pd.process(&c);
+     438           1 :         EXPECT_EQ(11, c.current.getId());
+     439           1 :         EXPECT_EQ(10 * EeV, c.current.getEnergy());
+     440           2 : }
+     441             : 
+     442           1 : TEST(PhotoDisintegration, limitNextStep) {
+     443             :         // Test if the interaction limits the next propagation step.
+     444           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     445           1 :         PhotoDisintegration pd(cmb);
+     446           1 :         Candidate c;
+     447           1 :         c.setNextStep(std::numeric_limits<double>::max());
+     448           1 :         c.current.setId(nucleusId(4, 2));
+     449           1 :         c.current.setEnergy(200 * EeV);
+     450           1 :         pd.process(&c);
+     451           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
+     452           2 : }
+     453             : 
+     454           1 : TEST(PhotoDisintegration, allIsotopes) {
+     455             :         // Test if all isotopes are handled.
+     456           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     457           1 :         PhotoDisintegration pd1(cmb);
+     458           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+     459           1 :         PhotoDisintegration pd2(irb);
+     460           1 :         Candidate c;
+     461           1 :         c.setCurrentStep(10 * Mpc);
+     462             : 
+     463          27 :         for (int Z = 1; Z <= 26; Z++) {
+     464         806 :                 for (int N = 1; N <= 30; N++) {
+     465             : 
+     466         780 :                         c.current.setId(nucleusId(Z + N, Z));
+     467         780 :                         c.current.setEnergy(80 * EeV);
+     468         780 :                         pd1.process(&c);
+     469             : 
+     470         780 :                         c.current.setId(nucleusId(Z + N, Z));
+     471         780 :                         c.current.setEnergy(80 * EeV);
+     472         780 :                         pd2.process(&c);
+     473             :                 }
+     474             :         }
+     475           3 : }
+     476             : 
+     477           1 : TEST(Photodisintegration, updateParticleParentProperties) { // Issue: #204
+     478           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     479           1 :         PhotoDisintegration pd(cmb);
+     480             : 
+     481           1 :         Candidate c(nucleusId(56,26), 500 * EeV, Vector3d(1 * Mpc, 0, 0));
+     482             : 
+     483           1 :         pd.performInteraction(&c, 1);
+     484             :         // the candidates parent is the original particle
+     485           1 :         EXPECT_EQ(c.created.getId(), nucleusId(56,26));
+     486             : 
+     487           1 :         pd.performInteraction(&c, 1);
+     488             :         // now it has to be changed
+     489           1 :         EXPECT_NE(c.created.getId(), nucleusId(56,26));
+     490           2 : }
+     491             : 
+     492           1 : TEST(PhotoDisintegration, interactionTag) {
+     493           2 :         PhotoDisintegration pd(new CMB());
+     494             : 
+     495             :         // test default interactionTag
+     496           2 :         EXPECT_TRUE(pd.getInteractionTag() == "PD");
+     497             : 
+     498             :         // test secondary tag
+     499           1 :         pd.setHavePhotons(true);
+     500           2 :         Candidate c(nucleusId(56,26), 500 * EeV);
+     501           1 :         c.setCurrentStep(1 * Gpc);
+     502           1 :         pd.process(&c);
+     503           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "PD");
+     504             : 
+     505             :         // test custom tag
+     506           1 :         pd.setInteractionTag("myTag");
+     507           2 :         EXPECT_TRUE(pd.getInteractionTag() == "myTag");
+     508           1 : }
+     509             : 
+     510             : // ElasticScattering ----------------------------------------------------------
+     511           1 : TEST(ElasticScattering, allBackgrounds) {
+     512             :         // Test if interaction data files are loaded.
+     513           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     514           1 :         ElasticScattering scattering(cmb);
+     515           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+     516           1 :         scattering.setPhotonField(irb);
+     517           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
+     518           2 :         scattering.setPhotonField(urb);
+     519           2 : }
+     520             : 
+     521           1 : TEST(ElasticScattering, secondaries) {
+     522             :         // Test the creation of cosmic ray photons.
+     523             :         // This test can stochastically fail.
+     524           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     525           1 :         ElasticScattering scattering(cmb);
+     526           1 :         Candidate c;
+     527           1 :         int id = nucleusId(12, 6);
+     528           1 :         c.current.setId(id);
+     529           1 :         c.current.setEnergy(200 * EeV);
+     530           1 :         c.setCurrentStep(400 * Mpc);
+     531           1 :         scattering.process(&c);
+     532             : 
+     533           1 :         EXPECT_GT(c.secondaries.size(), 0);
+     534             : 
+     535           8 :         for (int i = 0; i < c.secondaries.size(); i++) {
+     536           7 :                 int id = (*c.secondaries[i]).current.getId();
+     537           7 :                 EXPECT_EQ(id, 22);
+     538           7 :                 double energy = (*c.secondaries[i]).current.getEnergy();
+     539           7 :                 EXPECT_GT(energy, 0);
+     540           7 :                 EXPECT_LT(energy, 200 * EeV);
+     541             :         }
+     542           2 : }
+     543             : 
+     544             : // PhotoPionProduction --------------------------------------------------------
+     545           1 : TEST(PhotoPionProduction, allBackgrounds) {
+     546             :         // Test if all interaction data files can be loaded.
+     547           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     548           1 :         PhotoPionProduction ppp(cmb);
+     549           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
+     550           1 :         ppp.setPhotonField(irb);
+     551           2 :         irb = new IRB_Stecker05();
+     552           1 :         ppp.setPhotonField(irb);
+     553           2 :         irb = new IRB_Franceschini08();
+     554           1 :         ppp.setPhotonField(irb);
+     555           2 :         irb = new IRB_Finke10();
+     556           1 :         ppp.setPhotonField(irb);
+     557           2 :         irb = new IRB_Dominguez11();
+     558           1 :         ppp.setPhotonField(irb);
+     559           2 :         irb = new IRB_Gilmore12();
+     560           1 :         ppp.setPhotonField(irb);
+     561           2 :         irb = new IRB_Stecker16_upper();
+     562           1 :         ppp.setPhotonField(irb);
+     563           2 :         irb = new IRB_Stecker16_lower();
+     564           1 :         ppp.setPhotonField(irb);
+     565           2 :     irb = new IRB_Finke22();
+     566           1 :         ppp.setPhotonField(irb);
+     567           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
+     568           1 :         ppp.setPhotonField(urb);
+     569           2 :         urb = new URB_Nitu21();
+     570           2 :         ppp.setPhotonField(urb);
+     571           2 : }
+     572             : 
+     573           1 : TEST(PhotoPionProduction, proton) {
+     574             :         // Test photopion interaction for 100 EeV proton.
+     575             :         // This test can stochastically fail.
+     576           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     577           1 :         PhotoPionProduction ppp(cmb);
+     578           1 :         Candidate c(nucleusId(1, 1), 100 * EeV);
+     579           1 :         c.setCurrentStep(1000 * Mpc);
+     580           1 :         ppp.process(&c);
+     581             : 
+     582             :         // expect energy loss
+     583           1 :         EXPECT_LT(c.current.getEnergy(), 100. * EeV);
+     584             : 
+     585             :         // expect nucleon number conservation
+     586           1 :         EXPECT_EQ(1, massNumber(c.current.getId()));
+     587             : 
+     588             :         // expect no (nucleonic) secondaries
+     589           1 :         EXPECT_EQ(0, c.secondaries.size());
+     590           2 : }
+     591             : 
+     592           1 : TEST(PhotoPionProduction, helium) {
+     593             :         // Test photo-pion interaction for 400 EeV He nucleus.
+     594             :         // This test can stochastically fail.
+     595           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     596           1 :         PhotoPionProduction ppp(cmb);
+     597           1 :         Candidate c;
+     598           1 :         c.current.setId(nucleusId(4, 2));
+     599           1 :         c.current.setEnergy(400. * EeV);
+     600           1 :         c.setCurrentStep(1000 * Mpc);
+     601           1 :         ppp.process(&c);
+     602           1 :         EXPECT_LT(c.current.getEnergy(), 400. * EeV);
+     603           1 :         int id = c.current.getId();
+     604           1 :         EXPECT_TRUE(massNumber(id) < 4);
+     605           1 :         EXPECT_TRUE(c.secondaries.size() > 0);
+     606           2 : }
+     607             : 
+     608           1 : TEST(PhotoPionProduction, thisIsNotNucleonic) {
+     609             :         // Test if nothing happens to an electron.
+     610           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     611           1 :         PhotoPionProduction ppp(cmb);
+     612           1 :         Candidate c;
+     613           1 :         c.current.setId(11); // electron
+     614           1 :         c.current.setEnergy(10 * EeV);
+     615           1 :         c.setCurrentStep(100 * Mpc);
+     616           1 :         ppp.process(&c);
+     617           1 :         EXPECT_EQ(11, c.current.getId());
+     618           1 :         EXPECT_EQ(10 * EeV, c.current.getEnergy());
+     619           2 : }
+     620             : 
+     621           1 : TEST(PhotoPionProduction, limitNextStep) {
+     622             :         // Test if the interaction limits the next propagation step.
+     623           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     624           1 :         PhotoPionProduction ppp(cmb);
+     625           1 :         Candidate c(nucleusId(1, 1), 200 * EeV);
+     626           1 :         c.setNextStep(std::numeric_limits<double>::max());
+     627           1 :         ppp.process(&c);
+     628           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
+     629           2 : }
+     630             : 
+     631           1 : TEST(PhotoPionProduction, secondaries) {
+     632             :         // Test photo-pion interaction for 100 EeV proton.
+     633             :         // This test can stochastically fail.
+     634           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     635           1 :         PhotoPionProduction ppp(cmb, true, true, true);
+     636           1 :         Candidate c(nucleusId(1, 1), 100 * EeV);
+     637           1 :         c.setCurrentStep(1000 * Mpc);
+     638           1 :         ppp.process(&c);
+     639             :         // there should be secondaries
+     640           1 :         EXPECT_GT(c.secondaries.size(), 1);
+     641           2 : }
+     642             : 
+     643           1 : TEST(PhotoPionProduction, sampling) {
+     644             :         // Specific test of photon sampling of photo-pion production
+     645             :         // by testing the calculated pEpsMax for CMB(), also indirectly
+     646             :         // testing epsMinInteraction and logSampling (default).
+     647           1 :         ref_ptr<PhotonField> cmb = new CMB(); //create CMB instance
+     648             :         double energy = 1.e10; //1e10 GeV
+     649             :         bool onProton = true; //proton
+     650             :         double z = 0; //no redshift
+     651           1 :         PhotoPionProduction ppp(cmb, true, true, true);
+     652           1 :         double correctionFactor = ppp.getCorrectionFactor(); //get current correctionFactor
+     653           1 :         double epsMin = std::max(cmb -> getMinimumPhotonEnergy(z) / eV, 0.00710614); // 0.00710614 = epsMinInteraction(onProton,energy)
+     654           1 :         double epsMax = cmb -> getMaximumPhotonEnergy(z) / eV;
+     655           1 :         double pEpsMax = ppp.probEpsMax(onProton, energy, z, epsMin, epsMax) / correctionFactor;
+     656           1 :         EXPECT_DOUBLE_EQ(pEpsMax,132673934934.922);
+     657           2 : }
+     658             : 
+     659           1 : TEST(PhotoPionProduction, interactionTag) {
+     660           2 :         PhotoPionProduction ppp(new CMB());
+     661             : 
+     662             :         // test default interactionTag
+     663           2 :         EXPECT_TRUE(ppp.getInteractionTag() == "PPP");
+     664             : 
+     665             :         // test secondary tag
+     666           1 :         ppp.setHavePhotons(true);
+     667           2 :         Candidate c(nucleusId(1,1), 100 * EeV);
+     668          11 :         for(int i = 0; i <10; i++) 
+     669          10 :                 ppp.performInteraction(&c, true);
+     670           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "PPP");
+     671             : 
+     672             :         // test custom interactionTag
+     673           1 :         ppp.setInteractionTag("myTag");
+     674           2 :         EXPECT_TRUE(ppp.getInteractionTag() == "myTag");
+     675           1 : }
+     676             : 
+     677             : // Redshift -------------------------------------------------------------------
+     678           2 : TEST(Redshift, simpleTest) {
+     679             :         // Test if redshift is decreased and adiabatic energy loss is applied.
+     680             :         Redshift redshift;
+     681             : 
+     682           1 :         Candidate c;
+     683           1 :         c.setRedshift(0.024);
+     684           1 :         c.current.setEnergy(100 * EeV);
+     685           1 :         c.setCurrentStep(1 * Mpc);
+     686             : 
+     687           1 :         redshift.process(&c);
+     688           1 :         EXPECT_GT(0.024, c.getRedshift()); // expect redshift decrease
+     689           1 :         EXPECT_GT(100, c.current.getEnergy() / EeV); // expect energy loss
+     690           2 : }
+     691             : 
+     692           2 : TEST(Redshift, limitRedshiftDecrease) {
+     693             :         // Test if the redshift decrease is limited to z_updated >= 0.
+     694             :         Redshift redshift;
+     695             : 
+     696           1 :         Candidate c;
+     697           1 :         c.setRedshift(0.024); // roughly corresponds to 100 Mpc
+     698           1 :         c.setCurrentStep(150 * Mpc);
+     699             : 
+     700           1 :         redshift.process(&c);
+     701           1 :         EXPECT_DOUBLE_EQ(0, c.getRedshift());
+     702           2 : }
+     703             : 
+     704             : // EMPairProduction -----------------------------------------------------------
+     705           1 : TEST(EMPairProduction, allBackgrounds) {
+     706             :         // Test if interaction data files are loaded.
+     707           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     708           1 :         EMPairProduction em(cmb);
+     709           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
+     710           1 :         em.setPhotonField(ebl);
+     711           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
+     712           1 :         em.setPhotonField(urb);
+     713           2 :         ebl = new IRB_Stecker05();
+     714           1 :         em.setPhotonField(ebl);
+     715           2 :         ebl = new IRB_Franceschini08();
+     716           1 :         em.setPhotonField(ebl);
+     717           2 :         ebl = new IRB_Finke10();
+     718           1 :         em.setPhotonField(ebl);
+     719           2 :         ebl = new IRB_Dominguez11();
+     720           1 :         em.setPhotonField(ebl);
+     721           2 :         ebl = new IRB_Gilmore12();
+     722           1 :         em.setPhotonField(ebl);
+     723           2 :         ebl = new IRB_Stecker16_upper();
+     724           1 :         em.setPhotonField(ebl);
+     725           2 :         ebl = new IRB_Stecker16_lower();
+     726           1 :         em.setPhotonField(ebl);
+     727           2 :         ebl = new IRB_Finke22();
+     728           1 :         em.setPhotonField(ebl);
+     729           2 :         urb = new URB_Fixsen11();
+     730           1 :         em.setPhotonField(urb);
+     731           2 :         urb = new URB_Nitu21();
+     732           2 :         em.setPhotonField(urb);
+     733           2 : }
+     734             : 
+     735           1 : TEST(EMPairProduction, limitNextStep) {
+     736             :         // Test if the interaction limits the next propagation step.
+     737           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     738           1 :         EMPairProduction m(cmb);
+     739           1 :         Candidate c(22, 1E17 * eV);
+     740           1 :         c.setNextStep(std::numeric_limits<double>::max());
+     741           1 :         m.process(&c);
+     742           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
+     743           2 : }
+     744             : 
+     745           1 : TEST(EMPairProduction, secondaries) {
+     746             :         // Test if secondaries are correctly produced.
+     747           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     748           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
+     749           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
+     750           1 :         EMPairProduction m(cmb);
+     751           1 :         m.setHaveElectrons(true);
+     752           1 :         m.setThinning(0.);
+     753             : 
+     754             :         std::vector<ref_ptr<PhotonField>> fields;
+     755           1 :         fields.push_back(cmb);
+     756           1 :         fields.push_back(irb);
+     757           1 :         fields.push_back(urb);
+     758             : 
+     759             :         // loop over photon backgrounds
+     760           4 :         for (int f = 0; f < fields.size(); f++) {
+     761           3 :                 m.setPhotonField(fields[f]);
+     762         423 :                 for (int i = 0; i < 140; i++) { // loop over energies Ep = (1e10 - 1e23) eV
+     763         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
+     764         420 :                         Candidate c(22, Ep);
+     765         420 :                         c.setCurrentStep(1e10 * Mpc);
+     766             : 
+     767         420 :                         m.process(&c);
+     768             : 
+     769             :                         // pass if no interaction has ocurred (no tabulated rates)
+     770         420 :                         if (c.isActive())
+     771             :                                 continue;
+     772             :                         
+     773             :                         // expect 2 secondaries
+     774         311 :                         EXPECT_EQ(c.secondaries.size(), 2);
+     775             : 
+     776             :                         // expect electron / positron with energies 0 < E < Ephoton
+     777             :                         double Etot = 0;
+     778         933 :                         for (int j = 0; j < c.secondaries.size(); j++) {
+     779         622 :                                 Candidate s = *c.secondaries[j];
+     780         622 :                                 EXPECT_EQ(abs(s.current.getId()), 11);
+     781         622 :                                 EXPECT_GT(s.current.getEnergy(), 0);
+     782         622 :                                 EXPECT_LT(s.current.getEnergy(), Ep);
+     783         622 :                                 Etot += s.current.getEnergy();
+     784         622 :                         }
+     785             : 
+     786             :                         // test energy conservation
+     787         311 :                         EXPECT_DOUBLE_EQ(Ep, Etot);
+     788         420 :                 }
+     789             :         }
+     790           2 : }
+     791             : 
+     792           1 : TEST(EMPairProduction, interactionTag) {
+     793           2 :         EMPairProduction m(new CMB());
+     794             : 
+     795             :         // test default interactionTag
+     796           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMPP");
+     797             : 
+     798             :         // test secondary tag
+     799           1 :         m.setHaveElectrons(true);
+     800           2 :         Candidate c(22, 1 * EeV);
+     801           1 :         m.performInteraction(&c);
+     802           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMPP");
+     803             : 
+     804             :         // test custom tag
+     805           1 :         m.setInteractionTag("myTag");
+     806           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
+     807           1 : }
+     808             : 
+     809             : // EMDoublePairProduction -----------------------------------------------------
+     810           1 : TEST(EMDoublePairProduction, allBackgrounds) {
+     811             :         // Test if interaction data files are loaded.
+     812           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     813           1 :         EMDoublePairProduction em(cmb);
+     814           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
+     815           1 :         em.setPhotonField(ebl);
+     816           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
+     817           1 :         em.setPhotonField(urb);
+     818           2 :         ebl = new IRB_Stecker05();
+     819           1 :         em.setPhotonField(ebl);
+     820           2 :         ebl = new IRB_Franceschini08();
+     821           1 :         em.setPhotonField(ebl);
+     822           2 :         ebl = new IRB_Finke10();
+     823           1 :         em.setPhotonField(ebl);
+     824           2 :         ebl = new IRB_Dominguez11();
+     825           1 :         em.setPhotonField(ebl);
+     826           2 :         ebl = new IRB_Gilmore12();
+     827           1 :         em.setPhotonField(ebl);
+     828           2 :         ebl = new IRB_Stecker16_upper();
+     829           1 :         em.setPhotonField(ebl);
+     830           2 :         ebl = new IRB_Stecker16_lower();
+     831           1 :         em.setPhotonField(ebl);
+     832           2 :         ebl = new IRB_Finke22();
+     833           1 :         em.setPhotonField(ebl);
+     834           2 :         urb = new URB_Fixsen11();
+     835           1 :         em.setPhotonField(urb);
+     836           2 :         urb = new URB_Nitu21();
+     837           2 :         em.setPhotonField(urb);
+     838           2 : }
+     839             : 
+     840           1 : TEST(EMDoublePairProduction, limitNextStep) {
+     841             :         // Test if the interaction limits the next propagation step.
+     842           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     843           1 :         EMDoublePairProduction m(cmb);
+     844           1 :         Candidate c(22, 1E17 * eV);
+     845           1 :         c.setNextStep(std::numeric_limits<double>::max());
+     846           1 :         m.process(&c);
+     847           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
+     848           2 : }
+     849             : 
+     850           1 : TEST(EMDoublePairProduction, secondaries) {
+     851             :         // Test if secondaries are correctly produced.
+     852           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     853           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
+     854           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
+     855           1 :         EMPairProduction m(cmb);
+     856           1 :         m.setHaveElectrons(true);
+     857           1 :         m.setThinning(0.);
+     858             : 
+     859             :         std::vector<ref_ptr<PhotonField>> fields;
+     860           1 :         fields.push_back(cmb);
+     861           1 :         fields.push_back(irb);
+     862           1 :         fields.push_back(urb);
+     863             : 
+     864             :         // loop over photon backgrounds
+     865           4 :         for (int f = 0; f < fields.size(); f++) {
+     866           3 :                 m.setPhotonField(fields[f]);
+     867             :                 
+     868             :                 // loop over energies Ep = (1e9 - 1e23) eV
+     869         423 :                 for (int i = 0; i < 140; i++) {
+     870         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
+     871         420 :                         Candidate c(22, Ep);
+     872         420 :                         c.setCurrentStep(1e4 * Mpc); // use lower value so that the test can run faster
+     873         420 :                         m.process(&c);
+     874             : 
+     875             :                         // pass if no interaction has occured (no tabulated rates)
+     876         420 :                         if (c.isActive())
+     877             :                                 continue;
+     878             :                         
+     879             :                         // expect 2 secondaries (only one pair is considered)
+     880         251 :                         EXPECT_EQ(c.secondaries.size(), 2);
+     881             : 
+     882             :                         // expect electron / positron with energies 0 < E < Ephoton
+     883             :                         double Etot = 0;
+     884         753 :                         for (int j = 0; j < c.secondaries.size(); j++) {
+     885         502 :                                 Candidate s = *c.secondaries[j];
+     886         502 :                                 EXPECT_EQ(abs(s.current.getId()), 11);
+     887         502 :                                 EXPECT_GT(s.current.getEnergy(), 0);
+     888         502 :                                 EXPECT_LT(s.current.getEnergy(), Ep);
+     889         502 :                                 Etot += s.current.getEnergy();
+     890         502 :                         }
+     891             : 
+     892             :                         // test energy conservation
+     893         251 :                         EXPECT_NEAR(Ep, Etot, 1E-9);
+     894         420 :                 }
+     895             :         }
+     896           2 : }
+     897             : 
+     898           1 : TEST(EMDoublePairProduction, interactionTag) {
+     899           2 :         EMDoublePairProduction m(new CMB());
+     900             : 
+     901             :         // test default interactionTag
+     902           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMDP");
+     903             : 
+     904             :         // test secondary tag
+     905           1 :         m.setHaveElectrons(true);
+     906           2 :         Candidate c(22, 1 * EeV);
+     907           1 :         m.performInteraction(&c);
+     908           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMDP");
+     909             : 
+     910             :         // test custom tag
+     911           1 :         m.setInteractionTag("myTag");
+     912           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
+     913           1 : }
+     914             : 
+     915             : // EMTripletPairProduction ----------------------------------------------------
+     916           1 : TEST(EMTripletPairProduction, allBackgrounds) {
+     917             :         // Test if interaction data files are loaded.
+     918           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     919           1 :         EMTripletPairProduction em(cmb);
+     920           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
+     921           1 :         em.setPhotonField(ebl);
+     922           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
+     923           1 :         em.setPhotonField(urb);
+     924           2 :         ebl = new IRB_Stecker05();
+     925           1 :         em.setPhotonField(ebl);
+     926           2 :         ebl = new IRB_Franceschini08();
+     927           1 :         em.setPhotonField(ebl);
+     928           2 :         ebl = new IRB_Finke10();
+     929           1 :         em.setPhotonField(ebl);
+     930           2 :         ebl = new IRB_Dominguez11();
+     931           1 :         em.setPhotonField(ebl);
+     932           2 :         ebl = new IRB_Gilmore12();
+     933           1 :         em.setPhotonField(ebl);
+     934           2 :         ebl = new IRB_Stecker16_upper();
+     935           1 :         em.setPhotonField(ebl);
+     936           2 :         ebl = new IRB_Stecker16_lower();
+     937           1 :         em.setPhotonField(ebl);
+     938           2 :         ebl = new IRB_Finke22();
+     939           1 :         em.setPhotonField(ebl);
+     940           2 :         urb = new URB_Fixsen11();
+     941           1 :         em.setPhotonField(urb);
+     942           2 :         urb = new URB_Nitu21();
+     943           2 :         em.setPhotonField(urb);
+     944           2 : }
+     945             : 
+     946           1 : TEST(EMTripletPairProduction, limitNextStep) {
+     947             :         // Test if the interaction limits the next propagation step.
+     948           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     949           1 :         EMTripletPairProduction m(cmb);
+     950           1 :         Candidate c(11, 1E17 * eV);
+     951           1 :         c.setNextStep(std::numeric_limits<double>::max());
+     952           1 :         m.process(&c);
+     953           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
+     954           2 : }
+     955             : 
+     956           1 : TEST(EMTripletPairProduction, secondaries) {
+     957             :         // Test if secondaries are correctly produced.
+     958           1 :         ref_ptr<PhotonField> cmb = new CMB();
+     959           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
+     960           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
+     961           1 :         EMPairProduction m(cmb);
+     962           1 :         m.setHaveElectrons(true);
+     963           1 :         m.setThinning(0.);
+     964             : 
+     965             :         std::vector<ref_ptr<PhotonField>> fields;
+     966           1 :         fields.push_back(cmb);
+     967           1 :         fields.push_back(irb);
+     968           1 :         fields.push_back(urb);
+     969             : 
+     970             :         // loop over photon backgrounds
+     971           4 :         for (int f = 0; f < fields.size(); f++) {
+     972           3 :                 m.setPhotonField(fields[f]);
+     973             :                 
+     974             :                 // loop over energies Ep = (1e9 - 1e23) eV
+     975         423 :                 for (int i = 0; i < 140; i++) {
+     976             : 
+     977         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
+     978         420 :                         Candidate c(11, Ep);
+     979         420 :                         c.setCurrentStep(1e4 * Mpc); // use lower value so that the test can run faster
+     980         420 :                         m.process(&c);
+     981             : 
+     982             :                         // pass if no interaction has occured (no tabulated rates)
+     983         420 :                         if (c.current.getEnergy() == Ep)
+     984             :                                 continue;
+     985             : 
+     986             :                         // expect positive energy of primary electron
+     987           0 :                         EXPECT_GT(c.current.getEnergy(), 0);
+     988           0 :                         double Etot = c.current.getEnergy();
+     989             : 
+     990             :                         // expect electron / positron with energies 0 < E < Ephoton
+     991           0 :                         for (int j = 0; j < c.secondaries.size(); j++) {
+     992           0 :                                 Candidate s = *c.secondaries[j];
+     993           0 :                                 EXPECT_EQ(abs(s.current.getId()), 11);
+     994           0 :                                 EXPECT_GT(s.current.getEnergy(), 0);
+     995           0 :                                 EXPECT_LT(s.current.getEnergy(), Ep);
+     996           0 :                                 Etot += s.current.getEnergy();
+     997           0 :                         }
+     998             : 
+     999             :                         // test energy conservation
+    1000           0 :                         EXPECT_NEAR(Ep, Etot, 1e-9);
+    1001         420 :                 }
+    1002             :         }
+    1003           2 : }
+    1004             : 
+    1005           1 : TEST(EMTripletPairProduction, interactionTag) {
+    1006           2 :         EMTripletPairProduction m(new CMB());
+    1007             : 
+    1008             :         // test default interactionTag
+    1009           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMTP");
+    1010             : 
+    1011             :         // test secondary tag
+    1012           1 :         m.setHaveElectrons(true);
+    1013           2 :         Candidate c(11, 1 * EeV);
+    1014           1 :         m.performInteraction(&c);
+    1015           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMTP");
+    1016             : 
+    1017             :         // test custom tag
+    1018           1 :         m.setInteractionTag("myTag");
+    1019           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
+    1020           1 : }
+    1021             : 
+    1022             : // EMInverseComptonScattering -------------------------------------------------
+    1023           1 : TEST(EMInverseComptonScattering, allBackgrounds) {
+    1024             :         // Test if interaction data files are loaded.
+    1025           1 :         ref_ptr<PhotonField> cmb = new CMB();
+    1026           1 :         EMInverseComptonScattering em(cmb);
+    1027           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
+    1028           1 :         em.setPhotonField(ebl);
+    1029           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
+    1030           1 :         em.setPhotonField(urb);
+    1031           2 :         ebl = new IRB_Stecker05();
+    1032           1 :         em.setPhotonField(ebl);
+    1033           2 :         ebl = new IRB_Franceschini08();
+    1034           1 :         em.setPhotonField(ebl);
+    1035           2 :         ebl = new IRB_Finke10();
+    1036           1 :         em.setPhotonField(ebl);
+    1037           2 :         ebl = new IRB_Dominguez11();
+    1038           1 :         em.setPhotonField(ebl);
+    1039           2 :         ebl = new IRB_Gilmore12();
+    1040           1 :         em.setPhotonField(ebl);
+    1041           2 :         ebl = new IRB_Stecker16_upper();
+    1042           1 :         em.setPhotonField(ebl);
+    1043           2 :         ebl = new IRB_Stecker16_lower();
+    1044           1 :         em.setPhotonField(ebl);
+    1045           2 :         ebl = new IRB_Finke22();
+    1046           1 :         em.setPhotonField(ebl);
+    1047           2 :         urb = new URB_Fixsen11();
+    1048           1 :         em.setPhotonField(urb);
+    1049           2 :         urb = new URB_Nitu21();
+    1050           2 :         em.setPhotonField(urb);
+    1051           2 : }
+    1052             : 
+    1053           1 : TEST(EMInverseComptonScattering, limitNextStep) {
+    1054             :         // Test if the interaction limits the next propagation step.
+    1055           1 :         ref_ptr<PhotonField> cmb = new CMB();
+    1056           1 :         EMInverseComptonScattering m(cmb);
+    1057           1 :         Candidate c(11, 1E17 * eV);
+    1058           1 :         c.setNextStep(std::numeric_limits<double>::max());
+    1059           1 :         m.process(&c);
+    1060           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
+    1061           2 : }
+    1062             : 
+    1063           1 : TEST(EMInverseComptonScattering, secondaries) {
+    1064             :         // Test if secondaries are correctly produced.
+    1065           1 :         ref_ptr<PhotonField> cmb = new CMB();
+    1066           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
+    1067           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
+    1068           1 :         EMPairProduction m(cmb);
+    1069           1 :         m.setHaveElectrons(true);
+    1070           1 :         m.setThinning(0.);
+    1071             : 
+    1072             :         std::vector<ref_ptr<PhotonField>> fields;
+    1073           1 :         fields.push_back(cmb);
+    1074           1 :         fields.push_back(irb);
+    1075           1 :         fields.push_back(urb);
+    1076             : 
+    1077             :         // loop over photon backgrounds
+    1078           4 :         for (int f = 0; f < fields.size(); f++) {
+    1079           3 :                 m.setPhotonField(fields[f]);
+    1080             :                 
+    1081             :                 // loop over energies Ep = (1e9 - 1e23) eV
+    1082         423 :                 for (int i = 0; i < 140; i++) {
+    1083         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
+    1084         420 :                         Candidate c(11, Ep);
+    1085         420 :                         c.setCurrentStep(1e3 * Mpc); // use lower value so that the test can run faster
+    1086         420 :                         m.process(&c);
+    1087             : 
+    1088             :                         // pass if no interaction has occured (no tabulated rates)
+    1089         420 :                         if (c.current.getEnergy() == Ep)
+    1090             :                                 continue;
+    1091             :                         
+    1092             :                         // expect positive energy of primary electron
+    1093           0 :                         EXPECT_GT(c.current.getEnergy(), 0);
+    1094             : 
+    1095             :                         // expect photon with energy 0 < E < Ephoton
+    1096           0 :                         Candidate s = *c.secondaries[0];
+    1097           0 :                         EXPECT_EQ(abs(s.current.getId()), 22);
+    1098           0 :                         EXPECT_TRUE(s.current.getEnergy() >= 0.);
+    1099           0 :                         EXPECT_TRUE(s.current.getEnergy() < Ep);
+    1100             : 
+    1101             : 
+    1102           0 :                         double Etot = c.current.getEnergy();
+    1103           0 :                         for (int j = 0; j < c.secondaries.size(); j++) {
+    1104           0 :                                 s = *c.secondaries[j];
+    1105           0 :                                 Etot += s.current.getEnergy();
+    1106             :                         }
+    1107           0 :                         EXPECT_NEAR(Ep, Etot, 1e-9); 
+    1108         420 :                 }
+    1109             :         }
+    1110           2 : }
+    1111             : 
+    1112           1 : TEST(EMInverseComptonScattering, interactionTag) {
+    1113           2 :         EMInverseComptonScattering m(new CMB());
+    1114             : 
+    1115             :         // test default interactionTag
+    1116           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMIC");
+    1117             : 
+    1118             :         // test secondary tag
+    1119           1 :         m.setHavePhotons(true);
+    1120           2 :         Candidate c(11, 1 * PeV);
+    1121           1 :         m.performInteraction(&c);
+    1122           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMIC");
+    1123             : 
+    1124             :         // test custom tag
+    1125           1 :         m.setInteractionTag("myTag");
+    1126           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
+    1127           1 : }
+    1128             : 
+    1129             : // SynchrotronRadiation -------------------------------------------------
+    1130           1 : TEST(SynchrotronRadiation, interactionTag) {
+    1131           1 :         SynchrotronRadiation s(1 * muG, true);
+    1132             : 
+    1133             :         // test default interactionTag
+    1134           2 :         EXPECT_TRUE(s.getInteractionTag() == "SYN");
+    1135             : 
+    1136             :         // test secondary tag
+    1137           2 :         Candidate c(11, 10 * PeV);
+    1138           1 :         c.setCurrentStep(1 * pc);
+    1139           1 :         s.process(&c);
+    1140           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "SYN");
+    1141             : 
+    1142             :         // test custom tag
+    1143           1 :         s.setInteractionTag("myTag");
+    1144           2 :         EXPECT_TRUE(s.getInteractionTag() == "myTag");
+    1145           1 : }
+    1146             : 
+    1147             : 
+    1148           0 : int main(int argc, char **argv) {
+    1149           0 :         ::testing::InitGoogleTest(&argc, argv);
+    1150           0 :         return RUN_ALL_TESTS();
+    1151             : }
+    1152             : 
+    1153             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html b/doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html new file mode 100644 index 000000000..aaf4ebc36 --- /dev/null +++ b/doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testMagneticField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:138138100.0 %
Date:2024-04-08 14:58:22Functions:1616100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN36testCMZMagneticField_SimpleTest_Test8TestBodyEv1
_ZN37testMagneticFieldList_SimpleTest_Test8TestBodyEv1
_ZN37testToroidalHaloField_SimpleTest_Test8TestBodyEv1
_ZN38testCMZMagneticField_TestNTFField_Test8TestBodyEv1
_ZN39testMagneticDipoleField_SimpleTest_Test8TestBodyEv1
_ZN40testUniformMagneticField_SimpleTest_Test8TestBodyEv1
_ZN41testCMZMagneticField_TestICComponent_Test8TestBodyEv1
_ZN41testPeriodicMagneticField_Exceptions_Test8TestBodyEv1
_ZN42testLogarithmicSpiralField_SimpleTest_Test8TestBodyEv1
_ZN42testMagneticFieldEvolution_SimpleTest_Test8TestBodyEv1
_ZN43testCMZMagneticField_TestRaidoArcField_Test8TestBodyEv1
_ZN44testRenormalizeMagneticField_simpleTest_Test8TestBodyEv1
_ZN47testCMZMagneticField_TestAzimutalComponent_Test8TestBodyEv1
_ZN52testPolarizedSingleModeMagneticField_SimpleTest_Test8TestBodyEv1
main1
_ZNK17EchoMagneticField8getFieldERKN7crpropa7Vector3IdEE3
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testMagneticField.cpp.func.html b/doc/coverageReport/test/testMagneticField.cpp.func.html new file mode 100644 index 000000000..4842756d7 --- /dev/null +++ b/doc/coverageReport/test/testMagneticField.cpp.func.html @@ -0,0 +1,136 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testMagneticField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:138138100.0 %
Date:2024-04-08 14:58:22Functions:1616100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN36testCMZMagneticField_SimpleTest_Test8TestBodyEv1
_ZN37testMagneticFieldList_SimpleTest_Test8TestBodyEv1
_ZN37testToroidalHaloField_SimpleTest_Test8TestBodyEv1
_ZN38testCMZMagneticField_TestNTFField_Test8TestBodyEv1
_ZN39testMagneticDipoleField_SimpleTest_Test8TestBodyEv1
_ZN40testUniformMagneticField_SimpleTest_Test8TestBodyEv1
_ZN41testCMZMagneticField_TestICComponent_Test8TestBodyEv1
_ZN41testPeriodicMagneticField_Exceptions_Test8TestBodyEv1
_ZN42testLogarithmicSpiralField_SimpleTest_Test8TestBodyEv1
_ZN42testMagneticFieldEvolution_SimpleTest_Test8TestBodyEv1
_ZN43testCMZMagneticField_TestRaidoArcField_Test8TestBodyEv1
_ZN44testRenormalizeMagneticField_simpleTest_Test8TestBodyEv1
_ZN47testCMZMagneticField_TestAzimutalComponent_Test8TestBodyEv1
_ZN52testPolarizedSingleModeMagneticField_SimpleTest_Test8TestBodyEv1
_ZNK17EchoMagneticField8getFieldERKN7crpropa7Vector3IdEE3
main1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testMagneticField.cpp.gcov.html b/doc/coverageReport/test/testMagneticField.cpp.gcov.html new file mode 100644 index 000000000..1da471524 --- /dev/null +++ b/doc/coverageReport/test/testMagneticField.cpp.gcov.html @@ -0,0 +1,292 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testMagneticField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:138138100.0 %
Date:2024-04-08 14:58:22Functions:1616100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include <stdexcept>
+       2             : 
+       3             : #include "crpropa/magneticField/MagneticFieldGrid.h"
+       4             : #include "crpropa/magneticField/CMZField.h"
+       5             : #include "crpropa/magneticField/PolarizedSingleModeMagneticField.h"
+       6             : #include "crpropa/magneticField/GalacticMagneticField.h"
+       7             : #include "crpropa/Grid.h"
+       8             : #include "crpropa/Units.h"
+       9             : #include "crpropa/Common.h"
+      10             : 
+      11             : #include "gtest/gtest.h"
+      12             : 
+      13             : using namespace crpropa;
+      14             : 
+      15           1 : TEST(testUniformMagneticField, SimpleTest) {
+      16             :         UniformMagneticField B(Vector3d(-1, 5, 3));
+      17             :         Vector3d b = B.getField(Vector3d(1, 0, 0));
+      18           1 :         EXPECT_DOUBLE_EQ(b.getX(), -1);
+      19           1 :         EXPECT_DOUBLE_EQ(b.getY(), 5);
+      20           1 :         EXPECT_DOUBLE_EQ(b.getZ(), 3);
+      21           1 : }
+      22             : 
+      23           2 : TEST(testMagneticDipoleField, SimpleTest) {
+      24             :         // Test magnetic dipole
+      25             :         // mu0 / (4*M_PI) * m / r^3 (2*cos(theta)*e_r + sin(theta)*e_theta)
+      26             :         MagneticDipoleField B(Vector3d(0,0,0), Vector3d(0,0,1), 1);
+      27           1 :         Vector3d b1 = B.getField(Vector3d(0, 0, 1)); // theta = 0
+      28           1 :         Vector3d b2 = B.getField(Vector3d(1, 0, 0)); // theta = 0
+      29           1 :         EXPECT_NEAR(b1.getX(), 0, 1E-8);
+      30           1 :         EXPECT_NEAR(b1.getY(), 0, 1E-8);
+      31           1 :         EXPECT_NEAR(b1.getZ(), mu0 / (4*M_PI) * 2, 1E-8);
+      32           1 :         EXPECT_NEAR(b2.getX(), 0, 1E-8);
+      33           1 :         EXPECT_NEAR(b2.getY(), 0, 1E-8);
+      34           1 :         EXPECT_NEAR(b2.getZ(), -1 * mu0 / (4*M_PI), 1E-8);
+      35           1 : }
+      36             : 
+      37             : #ifdef CRPROPA_HAVE_MUPARSER
+      38           1 : TEST(testRenormalizeMagneticField, simpleTest) {
+      39           1 :         ref_ptr<UniformMagneticField> field = new UniformMagneticField(Vector3d(2*nG, 0, 0));
+      40           2 :         RenormalizeMagneticField modField(field, "B^2-1*nG");
+      41           1 :         Vector3d b = modField.getField(Vector3d(5, 5, 5));
+      42           1 :         EXPECT_NEAR(b.getR(), 3*nG, 0.001);
+      43           2 : }
+      44             : #endif
+      45             : 
+      46           2 : TEST(testMagneticFieldList, SimpleTest) {
+      47             :         // Test a list of three magnetic fields
+      48             :         MagneticFieldList B;
+      49           1 :         B.addField(new UniformMagneticField(Vector3d(1, 0, 0)));
+      50           1 :         B.addField(new UniformMagneticField(Vector3d(0, 2, 0)));
+      51           2 :         B.addField(new UniformMagneticField(Vector3d(0, 0, 3)));
+      52           1 :         Vector3d b = B.getField(Vector3d(0.));
+      53           1 :         EXPECT_DOUBLE_EQ(b.x, 1);
+      54           1 :         EXPECT_DOUBLE_EQ(b.y, 2);
+      55           1 :         EXPECT_DOUBLE_EQ(b.z, 3);
+      56           1 : }
+      57             : 
+      58           1 : TEST(testMagneticFieldEvolution, SimpleTest) {
+      59             :         // Test if this decorator scales the underlying field as (1+z)^m
+      60           1 :         ref_ptr<UniformMagneticField> B = new UniformMagneticField(Vector3d(1,0,0));
+      61             :         double z = 1.2;
+      62             :         double m = 3;
+      63           2 :         MagneticFieldEvolution Bz(B, m);
+      64             : 
+      65             :         // scaled field
+      66           1 :         Vector3d b = Bz.getField(Vector3d(0,0,0), z);
+      67           1 :         EXPECT_DOUBLE_EQ(b.x, pow(1+z, m));
+      68             : 
+      69             :         // unscaled field
+      70           1 :         b = Bz.getField(Vector3d(0,0,0));
+      71           1 :         EXPECT_DOUBLE_EQ(b.x, 1);
+      72           1 : }
+      73             : 
+      74           1 : class EchoMagneticField: public MagneticField {
+      75             : public:
+      76           3 :         Vector3d getField(const Vector3d &position) const {
+      77           3 :                 return position;
+      78             :         }
+      79             : };
+      80             : 
+      81           1 : TEST(testPeriodicMagneticField, Exceptions) {
+      82           1 :         ref_ptr<EchoMagneticField> f = new EchoMagneticField();
+      83             :         ref_ptr<PeriodicMagneticField> p = new PeriodicMagneticField(f,
+      84           1 :                         Vector3d(10000, 10000, 10000), Vector3d(1000, 1000, 1000), true);
+      85             : 
+      86             :         // box 0, 0, 0
+      87           1 :         Vector3d v = p->getField(Vector3d(1000, 2000, 3000));
+      88           1 :         EXPECT_DOUBLE_EQ(0, v.x);
+      89           1 :         EXPECT_DOUBLE_EQ(1000, v.y);
+      90           1 :         EXPECT_DOUBLE_EQ(2000, v.z);
+      91             : 
+      92             :         // box 1, 2, 3
+      93           1 :         v = p->getField(Vector3d(12000, 23000, 34000));
+      94           1 :         EXPECT_DOUBLE_EQ(9000, v.x);
+      95           1 :         EXPECT_DOUBLE_EQ(2000, v.y);
+      96           1 :         EXPECT_DOUBLE_EQ(7000, v.z);
+      97             : 
+      98             :         // box -1, -2, -3
+      99           1 :         v = p->getField(Vector3d(0, -10000, -20000));
+     100           1 :         EXPECT_DOUBLE_EQ(1000, v.x);
+     101           1 :         EXPECT_DOUBLE_EQ(9000, v.y);
+     102           1 :         EXPECT_DOUBLE_EQ(1000, v.z);
+     103             : 
+     104           1 : }
+     105             : 
+     106           1 : TEST(testCMZMagneticField, SimpleTest) {
+     107           1 :         ref_ptr<CMZField> field = new CMZField();
+     108             :         
+     109             :         // check use-Values
+     110           1 :         EXPECT_FALSE(field->getUseMCField());
+     111           1 :         EXPECT_TRUE(field->getUseICField());
+     112           1 :         EXPECT_FALSE(field->getUseNTFField());
+     113           1 :         EXPECT_FALSE(field->getUseRadioArc());
+     114             : 
+     115             :         // check set function
+     116           1 :         field->setUseMCField(true);
+     117           1 :         EXPECT_TRUE(field->getUseMCField());
+     118           1 :         field->setUseICField(false);
+     119           1 :         EXPECT_FALSE(field->getUseICField());
+     120           1 :         field->setUseNTFField(true);
+     121           1 :         EXPECT_TRUE(field->getUseNTFField());
+     122           1 :         field->setUseRadioArc(true);
+     123           1 :         EXPECT_TRUE(field->getUseRadioArc());
+     124           1 : }
+     125             : 
+     126           1 : TEST(testCMZMagneticField, TestICComponent) {
+     127           1 :         ref_ptr<CMZField> field = new CMZField();
+     128             :         Vector3d pos(10*pc,15*pc,-5*pc);        
+     129             : 
+     130             :         // check IC field at given position
+     131           1 :         Vector3d bVec = field->getField(pos);
+     132           1 :         EXPECT_NEAR(bVec.getR(), 10.501*muG, 1E-3*muG);
+     133           1 :         EXPECT_NEAR(bVec.x, 0.225*muG, 1E-3*muG);
+     134           1 :         EXPECT_NEAR(bVec.y, 0.524*muG, 1E-3*muG);
+     135           1 :         EXPECT_NEAR(bVec.z, 10.486*muG, 1E-3*muG);
+     136           1 : }
+     137           1 : TEST(testCMZMagneticField, TestNTFField){
+     138           1 :         ref_ptr<CMZField> field = new CMZField();
+     139             :         Vector3d pos(10*pc,15*pc,-5*pc);        
+     140             :         
+     141             :         // check NFTField at given position
+     142           1 :         Vector3d bVec = field->getNTFField(pos);
+     143           1 :         EXPECT_NEAR(bVec.getR(),1.692*muG, 1e-3*muG);
+     144           1 :         EXPECT_NEAR(bVec.x, -0.584*muG, 1e-3*muG);
+     145           1 :         EXPECT_NEAR(bVec.y, -1.185*muG, 1e-3*muG);
+     146           1 :         EXPECT_NEAR(bVec.z, 1.057*muG, 1e-3*muG);
+     147           1 : }
+     148           1 : TEST(testCMZMagneticField, TestRaidoArcField){
+     149           1 :         ref_ptr<CMZField> field = new CMZField();
+     150             :         Vector3d pos(10*pc,15*pc,-5*pc);        
+     151             : 
+     152             :         // check RadioArcField at given position
+     153           1 :         Vector3d bVec = field->getRadioArcField(pos);
+     154           1 :         EXPECT_NEAR(bVec.getR(), 31.616*muG, 1e-3*muG);
+     155           1 :         EXPECT_NEAR(bVec.x, -4.671*muG, 1e-3*muG);
+     156           1 :         EXPECT_NEAR(bVec.y, 5.465*muG, 1e-3*muG);
+     157           1 :         EXPECT_NEAR(bVec.z, 30.788*muG, 1e-3*muG);
+     158           1 : }
+     159             : 
+     160           1 : TEST(testCMZMagneticField, TestAzimutalComponent){
+     161           1 :         ref_ptr<CMZField> field = new CMZField();
+     162             :         Vector3d mid(12*pc, 9*pc, 20*pc);
+     163             :         Vector3d pos(9*pc, 10*pc, 25*pc);       
+     164             : 
+     165             :         // simple Test for inner part
+     166           1 :         Vector3d bVec = field->BAz(pos, mid, 100, 0.2, 60*pc);
+     167           1 :         EXPECT_NEAR(bVec.x, 3939.782, 1e-3);
+     168           1 :         EXPECT_NEAR(bVec.y, 14347.304, 1e-3);
+     169           1 :         EXPECT_DOUBLE_EQ(bVec.z, 0);
+     170             : 
+     171             :         // simple Test for outer part
+     172           1 :         bVec = field->BAz(pos, mid, 100, 0.2, 10*pc);
+     173           1 :         EXPECT_NEAR(bVec.x, -164.659, 1e-3);
+     174           1 :         EXPECT_NEAR(bVec.y, -1317.270, 1e-3);
+     175           1 :         EXPECT_DOUBLE_EQ(bVec.z, 0);
+     176             : 
+     177             :         // test for molecular Clouds
+     178           1 :         bVec = field->getMCField(pos);
+     179           1 :         EXPECT_NEAR(bVec.x, -8.339*muG, 1e-3*muG);
+     180           1 :         EXPECT_NEAR(bVec.y, -0.850*muG, 1e-3*muG);
+     181           1 :         EXPECT_DOUBLE_EQ(bVec.z, 0);
+     182           1 : }
+     183             : 
+     184           1 : TEST(testToroidalHaloField, SimpleTest) {
+     185           1 :         ref_ptr<ToroidalHaloField> field = new ToroidalHaloField();
+     186           1 :         Vector3d b = field->getField(Vector3d(0.));
+     187           1 :         EXPECT_DOUBLE_EQ(b.x, 0);
+     188           1 :         EXPECT_DOUBLE_EQ(b.y, 0);
+     189           1 :         EXPECT_DOUBLE_EQ(b.z, 0);
+     190             : 
+     191           1 :         b = field->getField(Vector3d(1,0,0));
+     192           1 :         EXPECT_DOUBLE_EQ(b.x, 0.5);
+     193           1 :         EXPECT_DOUBLE_EQ(b.y, 0);
+     194           1 :         EXPECT_DOUBLE_EQ(b.z, 0);
+     195           1 : }
+     196             : 
+     197           1 : TEST(testLogarithmicSpiralField, SimpleTest) {
+     198           1 :         ref_ptr<LogarithmicSpiralField> field = new LogarithmicSpiralField();
+     199           1 :         Vector3d b = field->getField(Vector3d(8.5, 0, 0)*kpc);
+     200           1 :         EXPECT_NEAR(b.x, -1., 1E-2);
+     201           1 :         EXPECT_NEAR(b.y, 0, 1E-10);
+     202           1 :         EXPECT_NEAR(b.z, 0, 1E-10);
+     203           1 : }
+     204             : 
+     205           1 : TEST(testPolarizedSingleModeMagneticField, SimpleTest) {
+     206           1 :         PolarizedSingleModeMagneticField B(2, 4, 0.5, Vector3d(1,1,1), Vector3d(0,1,0), Vector3d(1,0,0), "amplitude", "polarization", "elliptical");
+     207           1 :         Vector3d b = B.getField(Vector3d(1,1,2));
+     208           1 :         EXPECT_DOUBLE_EQ(b.x, 1);
+     209           1 :         EXPECT_NEAR(b.y, 0, 1E-10);
+     210           1 :         EXPECT_NEAR(b.z, 0, 1E-10);
+     211           1 : }
+     212             : 
+     213           1 : int main(int argc, char **argv) {
+     214           1 :         ::testing::InitGoogleTest(&argc, argv);
+     215             :         return RUN_ALL_TESTS();
+     216             : }
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html b/doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html new file mode 100644 index 000000000..d114bd5b9 --- /dev/null +++ b/doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testMagneticLens.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testMagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8787100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN28MagneticLens_Deflection_Test8TestBodyEv1
_ZN33Pixelization_angularDistance_Test8TestBodyEv1
_ZN35MagneticLens_OutOfBoundsEnergy_Test8TestBodyEv1
_ZN35MagneticLens_Vector3Deflection_Test8TestBodyEv1
_ZN38ParticleMapsContainer_addParticle_Test8TestBodyEv1
_ZN40Pixelization_randomDirectionInPixel_Test8TestBodyEv1
_ZN45ParticleMapsContainer_getRandomParticles_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testMagneticLens.cpp.func.html b/doc/coverageReport/test/testMagneticLens.cpp.func.html new file mode 100644 index 000000000..8fc41a1d4 --- /dev/null +++ b/doc/coverageReport/test/testMagneticLens.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testMagneticLens.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testMagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8787100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN28MagneticLens_Deflection_Test8TestBodyEv1
_ZN33Pixelization_angularDistance_Test8TestBodyEv1
_ZN35MagneticLens_OutOfBoundsEnergy_Test8TestBodyEv1
_ZN35MagneticLens_Vector3Deflection_Test8TestBodyEv1
_ZN38ParticleMapsContainer_addParticle_Test8TestBodyEv1
_ZN40Pixelization_randomDirectionInPixel_Test8TestBodyEv1
_ZN45ParticleMapsContainer_getRandomParticles_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testMagneticLens.cpp.gcov.html b/doc/coverageReport/test/testMagneticLens.cpp.gcov.html new file mode 100644 index 000000000..e293783f6 --- /dev/null +++ b/doc/coverageReport/test/testMagneticLens.cpp.gcov.html @@ -0,0 +1,248 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testMagneticLens.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testMagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8787100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /// Tests gamale with a test lense from file and demonstrating basic
+       2             : /// usage
+       3             : 
+       4             : //--------------------------------------------
+       5             : // Project: Galactic magnetic Lense (GaMaLe) -
+       6             : // Copyright (C) 2009 Tobias Winchen         -
+       7             : //               RWTH Aachen, Germany        -
+       8             : // Contact: winchen@physik.rwth-achen.de     -
+       9             : // Licensed under the GNU GPL v2             - 
+      10             : //--------------------------------------------
+      11             : 
+      12             : #include <string>
+      13             : #include "gtest/gtest.h"
+      14             : 
+      15             : #include "crpropa/magneticLens/MagneticLens.h"
+      16             : #include "crpropa/magneticLens/ModelMatrix.h"
+      17             : #include "crpropa/magneticLens/Pixelization.h"
+      18             : #include "crpropa/magneticLens/ParticleMapsContainer.h"
+      19             : #include "crpropa/Common.h"
+      20             : 
+      21             : using namespace std;
+      22             : using namespace crpropa;
+      23             : 
+      24           1 : TEST(MagneticLens, Deflection)
+      25             : {
+      26           1 :         MagneticLens magneticLens(5);
+      27           1 :         Pixelization P(5);
+      28           1 :         ModelMatrixType M;
+      29           1 :         M.resize(P.nPix(), P.nPix());
+      30           1 :         M.reserve(P.nPix());
+      31             : 
+      32             :         // Map any direction (p,t) to (p, -t)
+      33       12289 :         for (int i=0;i<P.nPix();i++)
+      34             :         {
+      35             :                 double theta, phi;
+      36       12288 :                 P.pix2Direction(i, phi, theta);
+      37       12288 :                 theta*= -1;
+      38       12288 :                 int j = P.direction2Pix(phi, theta);
+      39       12288 :                 M.insert(i,j) =1;
+      40             :         }
+      41             : 
+      42           1 :         magneticLens.setLensPart(M, 10 * EeV, 100 * EeV);
+      43             : 
+      44       12289 :         for (int i=0; i < P.nPix(); i++)
+      45             :         {
+      46             :                 double theta, phi;
+      47       12288 :                 P.pix2Direction(i, phi, theta);
+      48       12288 :                 double theta0 = theta;
+      49             : 
+      50             :                 // No CR is allowed to be lost in this lens
+      51       12288 :                 EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, phi, theta));
+      52       12288 :                 EXPECT_NEAR(theta+theta0,0., 0.05);
+      53             :         }
+      54           2 : }
+      55             : 
+      56           1 : TEST(MagneticLens, Vector3Deflection)
+      57             : {
+      58           1 :         MagneticLens magneticLens(5);
+      59           1 :         Pixelization P(5);
+      60           1 :         ModelMatrixType M;
+      61           1 :         M.resize(P.nPix(), P.nPix());
+      62           1 :         M.reserve(P.nPix());
+      63             : 
+      64             :         // No deflection 
+      65       12289 :         for (int i=0;i<P.nPix();i++)
+      66             :         {
+      67       12288 :                 M.insert(i,i) = 1;
+      68             :         }
+      69             : 
+      70           1 :         magneticLens.setLensPart(M, 10 * EeV, 100 * EeV);
+      71             : 
+      72             :         Vector3d u(1,0,0);
+      73             :         Vector3d v(u);
+      74           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
+      75           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
+      76             : 
+      77           1 :         u.x = 0; u.y = 1; u.z = 0; v = u;
+      78           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
+      79           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
+      80             : 
+      81           1 :         u.x = 0; u.y = 0; u.z = 1; v = u;
+      82           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
+      83           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
+      84             : 
+      85           1 :         u.x = 1; u.y = -2; u.z = 3; v = u;
+      86           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
+      87           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
+      88           2 : }
+      89             : 
+      90           1 : TEST(MagneticLens, OutOfBoundsEnergy)
+      91             : {
+      92           1 :         MagneticLens magneticLens(5);
+      93           1 :         Pixelization P(5);
+      94           1 :         ModelMatrixType M;
+      95           1 :         M.resize(P.nPix(), P.nPix());
+      96           1 :         M.reserve(P.nPix());
+      97           1 :         magneticLens.setLensPart(M,10. * EeV, 100. * EeV);
+      98           1 :         double theta = 0, phi = 0;
+      99           1 :         EXPECT_FALSE(magneticLens.transformCosmicRay(1. * EeV, phi, theta));
+     100           2 : }
+     101             : 
+     102             : 
+     103           1 : TEST(Pixelization, angularDistance)
+     104             : {
+     105             :         // test for correct angular distance in case of same vectors 
+     106           1 :         Pixelization P(6);
+     107       49153 :         for (int idx =0; idx < P.nPix(); idx++)
+     108             :         {
+     109       49152 :                 double ang = P.angularDistance(idx,idx);
+     110       49152 :                 EXPECT_TRUE(ang == ang);
+     111             :         }
+     112           1 : }
+     113             : 
+     114             : 
+     115           1 : TEST(ParticleMapsContainer, addParticle)
+     116             : {
+     117           1 :   ParticleMapsContainer maps;
+     118           1 :   maps.addParticle(1000010010, 1 * EeV, 0 , 0 );
+     119           1 :   std::vector<int> pids = maps.getParticleIds();
+     120           1 :   EXPECT_EQ(pids.size(), 1);
+     121           1 :   EXPECT_EQ(pids[0], 1000010010);
+     122             : 
+     123           1 :   std::vector<double> energies = maps.getEnergies(1000010010);
+     124           1 :   EXPECT_EQ(energies.size(), 1);
+     125           1 : }
+     126             : 
+     127           1 : TEST(ParticleMapsContainer, getRandomParticles)
+     128             : {
+     129           1 :   ParticleMapsContainer maps(0.002);
+     130           1 :   maps.addParticle(1000010010, 1 * EeV, 0 , 0 );
+     131             :   std::vector<double> energies;
+     132             :   std::vector<double> lons;
+     133             :   std::vector<double> lats;
+     134             :   std::vector<int> particleIds;
+     135             : 
+     136           1 :   size_t N = 420;
+     137           1 :         maps.getRandomParticles(N, particleIds, energies, lons, lats);
+     138             :                         
+     139           1 :   EXPECT_EQ(energies.size(), N);
+     140           1 :   EXPECT_EQ(lons.size(), N);
+     141           1 :   EXPECT_EQ(lats.size(), N);
+     142           1 :   EXPECT_EQ(particleIds.size(), N);
+     143             : 
+     144         421 :   for(size_t i = 0; i < N; i++)
+     145             :   {
+     146         420 :     EXPECT_NEAR(log10(energies[i]), 18, 0.002);
+     147         420 :     EXPECT_EQ(particleIds[i], 1000010010);
+     148         420 :     EXPECT_NEAR(lons[i], 0, 2./180*M_PI);
+     149         420 :     EXPECT_NEAR(lats[i], 0, 2./180*M_PI);
+     150             :   }
+     151             : 
+     152           1 : }
+     153             : 
+     154           1 : TEST(Pixelization, randomDirectionInPixel)
+     155             : {
+     156           1 :   Pixelization p(6);
+     157             :   const double long0 = -35./180 * M_PI;
+     158             :   const double lat0 =  12.08/180 * M_PI;
+     159             : 
+     160           1 :   int pix = p.direction2Pix(long0, lat0);
+     161             : 
+     162             :   double rlon, rlat;
+     163           1 :   p.getRandomDirectionInPixel(pix, rlon, rlat);
+     164             : 
+     165             :   // new direction should be inside the pixel
+     166           1 :   EXPECT_EQ(pix, p.direction2Pix(rlon, rlat));
+     167             : 
+     168             :   // new direction should be different from input 
+     169           1 :   EXPECT_FALSE(long0 == rlon);
+     170           1 :   EXPECT_FALSE(lat0 == rlat);
+     171             : 
+     172           1 : }
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testModuleList.cpp.func-sort-c.html b/doc/coverageReport/test/testModuleList.cpp.func-sort-c.html new file mode 100644 index 000000000..923a232e2 --- /dev/null +++ b/doc/coverageReport/test/testModuleList.cpp.func-sort-c.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testModuleList.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testModuleList.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:525594.5 %
Date:2024-04-08 14:58:22Functions:6785.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa23ModuleList_process_Test8TestBodyEv1
_ZN7crpropa25ModuleList_getModule_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runOpenMP_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runSource_Test8TestBodyEv1
_ZN7crpropa28ModuleList_removeModule_Test8TestBodyEv1
_ZN7crpropa32ModuleList_runCandidateList_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testModuleList.cpp.func.html b/doc/coverageReport/test/testModuleList.cpp.func.html new file mode 100644 index 000000000..1ac5ff9e1 --- /dev/null +++ b/doc/coverageReport/test/testModuleList.cpp.func.html @@ -0,0 +1,100 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testModuleList.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testModuleList.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:525594.5 %
Date:2024-04-08 14:58:22Functions:6785.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa23ModuleList_process_Test8TestBodyEv1
_ZN7crpropa25ModuleList_getModule_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runOpenMP_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runSource_Test8TestBodyEv1
_ZN7crpropa28ModuleList_removeModule_Test8TestBodyEv1
_ZN7crpropa32ModuleList_runCandidateList_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testModuleList.cpp.gcov.html b/doc/coverageReport/test/testModuleList.cpp.gcov.html new file mode 100644 index 000000000..63abd27da --- /dev/null +++ b/doc/coverageReport/test/testModuleList.cpp.gcov.html @@ -0,0 +1,155 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testModuleList.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testModuleList.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:525594.5 %
Date:2024-04-08 14:58:22Functions:6785.7 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/ModuleList.h"
+       2             : #include "crpropa/Source.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : #include "crpropa/module/SimplePropagation.h"
+       5             : #include "crpropa/module/BreakCondition.h"
+       6             : 
+       7             : #include "gtest/gtest.h"
+       8             : 
+       9             : namespace crpropa {
+      10             : 
+      11           1 : TEST(ModuleList, process) {
+      12           1 :         ModuleList modules;
+      13           2 :         modules.add(new SimplePropagation());
+      14           1 :         ParticleState initial;
+      15           1 :         ref_ptr<Candidate> candidate = new Candidate(initial);
+      16           2 :         modules.process(candidate);
+      17           1 : }
+      18             : 
+      19           1 : TEST(ModuleList, getModule) {
+      20           1 :         ModuleList modules;
+      21           1 :         ref_ptr<SimplePropagation> prop = new SimplePropagation();
+      22           1 :         modules.add(prop);
+      23           2 :         EXPECT_TRUE(modules[0] == prop);
+      24           1 : }
+      25             : 
+      26           1 : TEST(ModuleList, removeModule) {
+      27           1 :         ModuleList modules;
+      28           1 :         ref_ptr<SimplePropagation> prop = new SimplePropagation();
+      29           1 :         modules.add(prop);
+      30           1 :         modules.remove(0);
+      31           1 :         EXPECT_EQ(modules.size(), 0);
+      32           1 : }
+      33             : 
+      34           1 : TEST(ModuleList, runCandidateList) {
+      35           1 :         ModuleList modules;
+      36           2 :         modules.add(new SimplePropagation());
+      37           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
+      38           1 :         ParticleState initial;
+      39           1 :         ref_ptr<Candidate> candidate = new Candidate(initial);
+      40           1 :         modules.run(candidate);
+      41           1 :         EXPECT_DOUBLE_EQ(1 * Mpc, candidate->getTrajectoryLength());
+      42           1 :         EXPECT_TRUE(candidate->isActive() == false);
+      43           1 : }
+      44             : 
+      45           1 : TEST(ModuleList, runSource) {
+      46           1 :         ModuleList modules;
+      47           2 :         modules.add(new SimplePropagation());
+      48           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
+      49             :         Source source;
+      50           1 :         source.add(new SourcePosition(Vector3d(10, 0, 0) * Mpc));
+      51           2 :         source.add(new SourceIsotropicEmission());
+      52           1 :         source.add(new SourcePowerLawSpectrum(5 * EeV, 100 * EeV, -2));
+      53           1 :         source.add(new SourceParticleType(nucleusId(1, 1)));
+      54           1 :         modules.setShowProgress(true);
+      55           1 :         modules.run(&source, 100, false);
+      56           1 : }
+      57             : 
+      58             : #if _OPENMP
+      59             : #include <omp.h>
+      60           1 : TEST(ModuleList, runOpenMP) {
+      61           1 :         ModuleList modules;
+      62           2 :         modules.add(new SimplePropagation());
+      63           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
+      64             :         Source source;
+      65           1 :         source.add(new SourcePosition(Vector3d(10, 0, 0) * Mpc));
+      66           2 :         source.add(new SourceIsotropicEmission());
+      67           1 :         source.add(new SourcePowerLawSpectrum(5 * EeV, 100 * EeV, -2));
+      68           1 :         source.add(new SourceParticleType(nucleusId(1, 1)));
+      69           1 :         omp_set_num_threads(2);
+      70           1 :         modules.run(&source, 1000, false);
+      71           1 : }
+      72             : #endif
+      73             : 
+      74           0 : int main(int argc, char **argv) {
+      75           0 :         ::testing::InitGoogleTest(&argc, argv);
+      76           0 :         return RUN_ALL_TESTS();
+      77             : }
+      78             : 
+      79             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testOutput.cpp.func-sort-c.html b/doc/coverageReport/test/testOutput.cpp.func-sort-c.html new file mode 100644 index 000000000..f1f61fe38 --- /dev/null +++ b/doc/coverageReport/test/testOutput.cpp.func-sort-c.html @@ -0,0 +1,144 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testOutput.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15716296.9 %
Date:2024-04-08 14:58:22Functions:171894.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_Z11ArraysMatchIiLm10EEN7testing15AssertionResultERAT0__KT_S5_1
_ZN7crpropa16Output_size_Test8TestBodyEv1
_ZN7crpropa27ParticleCollector_size_Test8TestBodyEv1
_ZN7crpropa29TextOutput_printProperty_Test8TestBodyEv1
_ZN7crpropa31ParticleCollector_dumpload_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_fetchItem_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_reprocess_Test8TestBodyEv1
_ZN7crpropa34TextOutput_printHeader_Custom_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event1D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event3D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Version_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_getTrajectory_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_runModuleList_Test8TestBodyEv1
_ZN7crpropa39HDF5Output_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa39TextOutput_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory1D_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory3D_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testOutput.cpp.func.html b/doc/coverageReport/test/testOutput.cpp.func.html new file mode 100644 index 000000000..9920b9d67 --- /dev/null +++ b/doc/coverageReport/test/testOutput.cpp.func.html @@ -0,0 +1,144 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testOutput.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15716296.9 %
Date:2024-04-08 14:58:22Functions:171894.4 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_Z11ArraysMatchIiLm10EEN7testing15AssertionResultERAT0__KT_S5_1
_ZN7crpropa16Output_size_Test8TestBodyEv1
_ZN7crpropa27ParticleCollector_size_Test8TestBodyEv1
_ZN7crpropa29TextOutput_printProperty_Test8TestBodyEv1
_ZN7crpropa31ParticleCollector_dumpload_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_fetchItem_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_reprocess_Test8TestBodyEv1
_ZN7crpropa34TextOutput_printHeader_Custom_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event1D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event3D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Version_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_getTrajectory_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_runModuleList_Test8TestBodyEv1
_ZN7crpropa39HDF5Output_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa39TextOutput_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory1D_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory3D_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testOutput.cpp.gcov.html b/doc/coverageReport/test/testOutput.cpp.gcov.html new file mode 100644 index 000000000..3a91eb777 --- /dev/null +++ b/doc/coverageReport/test/testOutput.cpp.gcov.html @@ -0,0 +1,355 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testOutput.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15716296.9 %
Date:2024-04-08 14:58:22Functions:171894.4 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : /** Unit tests for Output modules of CRPropa
+       2             :     Output
+       3             :     TextOutput
+       4             :     ParticleCollector
+       5             :  */
+       6             : 
+       7             : #include "CRPropa.h"
+       8             : 
+       9             : #include "gtest/gtest.h"
+      10             : #include <iostream>
+      11             : #include <string>
+      12             : 
+      13             : 
+      14             : #ifdef CRPROPA_HAVE_HDF5
+      15             : #include <hdf5.h>
+      16             : #endif
+      17             : 
+      18             : // compare two arrays (intead of using Google Mock)
+      19             : // https://stackoverflow.com/a/10062016/6819103
+      20             : template <typename T, size_t size>
+      21           1 : ::testing::AssertionResult ArraysMatch(const T (&expected)[size],
+      22             :                                        const T (&actual)[size]) {
+      23          11 :         for (size_t i(0); i < size; ++i) {
+      24          10 :                 if (expected[i] != actual[i]) {
+      25             :                         return ::testing::AssertionFailure()
+      26           0 :                                << "array[" << i << "] (" << actual[i] << ") != expected["
+      27           0 :                                << i << "] (" << expected[i] << ")";
+      28             :                 }
+      29             :         }
+      30             : 
+      31           1 :         return ::testing::AssertionSuccess();
+      32             : }
+      33             : 
+      34             : namespace crpropa {
+      35             : 
+      36             : //-- Output
+      37           1 : TEST(Output, size) {
+      38           1 :         Candidate c;
+      39           1 :         Output output;
+      40           6 :         for (int it = 0; it < 5; ++it, output.process(&c));
+      41             : 
+      42           1 :         EXPECT_EQ(output.size(), 5);
+      43           1 : }
+      44             : 
+      45             : //-- TextOutput
+      46           1 : TEST(TextOutput, printHeader_Trajectory1D) {
+      47           1 :         Candidate c;
+      48           1 :         TextOutput output(Output::Trajectory1D);
+      49             : 
+      50           1 :         ::testing::internal::CaptureStdout();
+      51           1 :         output.process(&c);
+      52           1 :         std::string captured = testing::internal::GetCapturedStdout();
+      53             : 
+      54           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")), "#\tID\tE\tX");
+      55           1 : }
+      56             : 
+      57           1 : TEST(TextOutput, printHeader_Event1D) {
+      58           1 :         Candidate c;
+      59           1 :         TextOutput output(Output::Event1D);
+      60             : 
+      61           1 :         ::testing::internal::CaptureStdout();
+      62           1 :         output.process(&c);
+      63           1 :         std::string captured = testing::internal::GetCapturedStdout();
+      64             : 
+      65           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")), "#\tD\tID\tE\tID0\tE0");
+      66           1 : }
+      67             : 
+      68           1 : TEST(TextOutput, printHeader_Trajectory3D) {
+      69           1 :         Candidate c;
+      70           1 :         TextOutput output(Output::Trajectory3D);
+      71             : 
+      72           1 :         ::testing::internal::CaptureStdout();
+      73           1 :         output.process(&c);
+      74           1 :         std::string captured = testing::internal::GetCapturedStdout();
+      75             : 
+      76           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")),
+      77             :                   "#\tD\tID\tE\tX\tY\tZ\tPx\tPy\tPz");
+      78           1 : }
+      79             : 
+      80           1 : TEST(TextOutput, printHeader_Event3D) {
+      81           1 :         Candidate c;
+      82           1 :         TextOutput output(Output::Event3D);
+      83             : 
+      84           1 :         ::testing::internal::CaptureStdout();
+      85           1 :         output.process(&c);
+      86           1 :         std::string captured = testing::internal::GetCapturedStdout();
+      87             : 
+      88           2 :         EXPECT_EQ(
+      89             :             captured.substr(0, captured.find("\n")),
+      90             :             "#\tD\tID\tE\tX\tY\tZ\tPx\tPy\tPz\tID0\tE0\tX0\tY0\tZ0\tP0x\tP0y\tP0z");
+      91           1 : }
+      92             : 
+      93           1 : TEST(TextOutput, printHeader_Custom) {
+      94           1 :         Candidate c;
+      95           1 :         TextOutput output(Output::Event1D);
+      96             : 
+      97           1 :         output.enable(Output::SerialNumberColumn);
+      98           1 :         output.disable(Output::TrajectoryLengthColumn);
+      99           1 :         output.set(Output::RedshiftColumn, false);
+     100           1 :         output.enable(Output::CandidateTagColumn);
+     101             : 
+     102           1 :         ::testing::internal::CaptureStdout();
+     103           1 :         output.process(&c);
+     104           1 :         std::string captured = testing::internal::GetCapturedStdout();
+     105             : 
+     106           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")),
+     107             :                   "#\tSN\tID\tE\tSN0\tID0\tE0\tSN1\ttag");
+     108           1 : }
+     109             : 
+     110           1 : TEST(TextOutput, printProperty) {
+     111           1 :         Candidate c;
+     112           1 :         TextOutput output(Output::Event1D);
+     113           1 :         output.disableAll();
+     114           2 :         output.enableProperty("foo", 2.0, "Bar");
+     115             : 
+     116           1 :         ::testing::internal::CaptureStdout();
+     117           1 :         output.process(&c);
+     118           1 :         std::string captured = testing::internal::GetCapturedStdout();
+     119             : 
+     120             :         // name in first line of header
+     121           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")), "#\tfoo");
+     122           1 : }
+     123             : 
+     124           1 : TEST(TextOutput, printHeader_Version) {
+     125           1 :         Candidate c;
+     126           1 :         TextOutput output(Output::Event1D);
+     127             : 
+     128           1 :         ::testing::internal::CaptureStdout();
+     129           1 :         output.process(&c);
+     130           1 :         std::string captured = testing::internal::GetCapturedStdout();
+     131             : 
+     132             :         // length of the prefix is 19 chars
+     133           1 :         size_t version_pos = captured.find("# CRPropa version: ") + 19;
+     134             : 
+     135           2 :         EXPECT_EQ(captured.substr(version_pos,
+     136             :                                   captured.find("\n", version_pos) - version_pos),
+     137             :                   g_GIT_DESC);
+     138           1 : }
+     139             : 
+     140             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
+     141           1 : TEST(TextOutput, failOnIllegalOutputFile) {
+     142           2 :         EXPECT_THROW(
+     143             :             TextOutput output("THIS_FOLDER_MUST_NOT_EXISTS_12345+/FILE.txt"),
+     144             :             std::runtime_error);
+     145           1 : }
+     146             : #endif
+     147             : 
+     148             : #ifdef CRPROPA_HAVE_HDF5
+     149             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
+     150           1 : TEST(HDF5Output, failOnIllegalOutputFile) {
+     151           1 :         HDF5Output out;
+     152             :         // disable default error output of HDF5
+     153           1 :         H5Eset_auto2(H5E_DEFAULT, NULL, NULL);
+     154           2 :         EXPECT_THROW(out.open("THIS_FOLDER_MUST_NOT_EXISTS_12345+/FILE.h5"),
+     155             :                      std::runtime_error);
+     156           1 : }
+     157             : #endif
+     158             : #endif
+     159             : 
+     160             : //-- ParticleCollector
+     161           2 : TEST(ParticleCollector, size) {
+     162           2 :         ref_ptr<Candidate> c = new Candidate();
+     163           1 :         ParticleCollector output;
+     164             : 
+     165           6 :         for (int it = 0; it < 5; ++it, output.process(c))
+     166             :                 ;
+     167             : 
+     168           1 :         EXPECT_EQ(output.size(), 5);
+     169           2 : }
+     170             : 
+     171           1 : TEST(ParticleCollector, fetchItem) {
+     172           2 :         ref_ptr<Candidate> c = new Candidate(nucleusId(1, 1), 1 * EeV);
+     173           1 :         ParticleCollector output;
+     174             : 
+     175           1 :         output.process(c);
+     176             : 
+     177           2 :         EXPECT_EQ(output[0], c);
+     178           2 : }
+     179             : 
+     180           1 : TEST(ParticleCollector, reprocess) {
+     181           2 :         ref_ptr<Candidate> c = new Candidate(nucleusId(1, 1), 1 * EeV);
+     182           1 :         ParticleCollector collector;
+     183           1 :         ParticleCollector output;
+     184             : 
+     185           1 :         collector.process(c);
+     186           1 :         collector.reprocess(&output);
+     187             : 
+     188           2 :         EXPECT_EQ(output[0], c);
+     189           2 : }
+     190             : 
+     191           1 : TEST(ParticleCollector, dumpload) {
+     192           2 :         ref_ptr<Candidate> c = new Candidate(nucleusId(1, 1), 1.234 * EeV);
+     193           1 :         c->current.setPosition(Vector3d(1, 2, 3));
+     194           1 :         c->current.setDirection(Vector3d(-1, -1, -1));
+     195           1 :         c->setTrajectoryLength(1 * Mpc);
+     196           1 :         c->setRedshift(2);
+     197             : 
+     198           1 :         ParticleCollector input;
+     199           1 :         ParticleCollector output;
+     200             : 
+     201          12 :         for (int i = 0; i <= 10; ++i) {
+     202          22 :                 input.process(c);
+     203             :         }
+     204             : 
+     205             :         // Well, it would be nicer if we don't need to receate any file
+     206           1 :         input.dump("ParticleCollector_DumpTest.txt");
+     207           1 :         output.load("ParticleCollector_DumpTest.txt");
+     208             : 
+     209           1 :         EXPECT_EQ(input.size(), output.size());
+     210           2 :         EXPECT_EQ(output[0]->current.getEnergy(), c->current.getEnergy());
+     211           2 :         EXPECT_EQ(output[1]->getTrajectoryLength(), c->getTrajectoryLength());
+     212           2 :         EXPECT_EQ(output[2]->current.getId(), c->current.getId());
+     213           2 :         EXPECT_EQ(output[3]->getRedshift(), c->getRedshift());
+     214           2 : }
+     215             : 
+     216             : // Just test if the trajectory is on a line for rectilinear propagation
+     217           1 : TEST(ParticleCollector, getTrajectory) {
+     218             :         int pos_x[10];
+     219           1 :         int pos_x_expected[] = {9, 8, 7, 6, 5, 4, 3, 2, 1, 0};
+     220             : 
+     221           1 :         ParticleState p;
+     222           1 :         p.setPosition(Vector3d(10, 0, 0));
+     223           1 :         p.setDirection(Vector3d(-1, 0, 0));
+     224           1 :         ref_ptr<Candidate> c = new Candidate(p);
+     225             : 
+     226           1 :         ref_ptr<ParticleCollector> output = new ParticleCollector();
+     227           1 :         ref_ptr<ParticleCollector> trajectory = new ParticleCollector();
+     228           1 :         trajectory->setClone(true);
+     229             : 
+     230           1 :         ref_ptr<ModuleList> sim = new ModuleList();
+     231           1 :         sim->add(new SimplePropagation(1, 1));
+     232             : 
+     233           1 :         ref_ptr<Observer> obs = new Observer();
+     234           1 :         obs->add(new Observer1D());
+     235           1 :         obs->onDetection(output);
+     236           1 :         sim->add(obs);
+     237             : 
+     238           2 :         sim->run(c);
+     239             : 
+     240           2 :         output->getTrajectory(sim, 0, trajectory);
+     241             : 
+     242             :         Vector3d pos;
+     243             :         int i = 0;
+     244             : 
+     245           1 :         for (ParticleCollector::iterator itr = trajectory->begin();
+     246          11 :              itr != trajectory->end(); ++itr) {
+     247          10 :                 pos = (*(itr->get())).current.getPosition();
+     248          10 :                 pos_x[i] = pos.getX();
+     249          10 :                 ++i;
+     250             :         }
+     251             : 
+     252           1 :         EXPECT_TRUE(ArraysMatch(pos_x_expected, pos_x));
+     253           1 : }
+     254             : 
+     255           1 : TEST(ParticleCollector, runModuleList) {
+     256           1 :         ModuleList modules;
+     257           2 :         modules.add(new SimplePropagation());
+     258           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
+     259             : 
+     260           1 :         ParticleState p;
+     261           1 :         p.setPosition(Vector3d(10, 0, 0));
+     262           1 :         p.setDirection(Vector3d(-1, 0, 0));
+     263           1 :         ref_ptr<Candidate> c = new Candidate(p);
+     264             : 
+     265           1 :         ref_ptr<ParticleCollector> collector = new ParticleCollector();
+     266             : 
+     267           1 :         collector->process(c);
+     268             : 
+     269           1 :         modules.setShowProgress(false);
+     270           1 :         auto candidates = collector->getContainer();
+     271           1 :         modules.run(&candidates);
+     272           2 : }
+     273             : 
+     274           0 : int main(int argc, char **argv) {
+     275           0 :         ::testing::InitGoogleTest(&argc, argv);
+     276           0 :         return RUN_ALL_TESTS();
+     277             : }
+     278             : 
+     279             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testPropagation.cpp.func-sort-c.html b/doc/coverageReport/test/testPropagation.cpp.func-sort-c.html new file mode 100644 index 000000000..15ff4021f --- /dev/null +++ b/doc/coverageReport/test/testPropagation.cpp.func-sort-c.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testPropagation.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testPropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:33734099.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa29testPropagationBP_proton_Test8TestBodyEv1
_ZN7crpropa29testPropagationCK_proton_Test8TestBodyEv1
_ZN7crpropa30testPropagationBP_neutron_Test8TestBodyEv1
_ZN7crpropa30testPropagationCK_neutron_Test8TestBodyEv1
_ZN7crpropa31testPropagationBP_gyration_Test8TestBodyEv1
_ZN7crpropa31testPropagationCK_gyration_Test8TestBodyEv1
_ZN7crpropa31testSimplePropagation_step_Test8TestBodyEv1
_ZN7crpropa32testPropagationBP_zeroField_Test8TestBodyEv1
_ZN7crpropa32testPropagationCK_zeroField_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_reduceStep_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_reduceStep_Test8TestBodyEv1
_ZN7crpropa34testPropagationBP_constructor_Test8TestBodyEv1
_ZN7crpropa34testPropagationCK_constructor_Test8TestBodyEv1
_ZN7crpropa35testPropagationBP_increaseStep_Test8TestBodyEv1
_ZN7crpropa35testPropagationCK_increaseStep_Test8TestBodyEv1
_ZN7crpropa44testPropagationBP_fixedStepOptimization_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testPropagation.cpp.func.html b/doc/coverageReport/test/testPropagation.cpp.func.html new file mode 100644 index 000000000..586d6fcc2 --- /dev/null +++ b/doc/coverageReport/test/testPropagation.cpp.func.html @@ -0,0 +1,148 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testPropagation.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testPropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:33734099.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa29testPropagationBP_proton_Test8TestBodyEv1
_ZN7crpropa29testPropagationCK_proton_Test8TestBodyEv1
_ZN7crpropa30testPropagationBP_neutron_Test8TestBodyEv1
_ZN7crpropa30testPropagationCK_neutron_Test8TestBodyEv1
_ZN7crpropa31testPropagationBP_gyration_Test8TestBodyEv1
_ZN7crpropa31testPropagationCK_gyration_Test8TestBodyEv1
_ZN7crpropa31testSimplePropagation_step_Test8TestBodyEv1
_ZN7crpropa32testPropagationBP_zeroField_Test8TestBodyEv1
_ZN7crpropa32testPropagationCK_zeroField_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_reduceStep_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_reduceStep_Test8TestBodyEv1
_ZN7crpropa34testPropagationBP_constructor_Test8TestBodyEv1
_ZN7crpropa34testPropagationCK_constructor_Test8TestBodyEv1
_ZN7crpropa35testPropagationBP_increaseStep_Test8TestBodyEv1
_ZN7crpropa35testPropagationCK_increaseStep_Test8TestBodyEv1
_ZN7crpropa44testPropagationBP_fixedStepOptimization_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testPropagation.cpp.gcov.html b/doc/coverageReport/test/testPropagation.cpp.gcov.html new file mode 100644 index 000000000..f3e80ad45 --- /dev/null +++ b/doc/coverageReport/test/testPropagation.cpp.gcov.html @@ -0,0 +1,632 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testPropagation.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testPropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:33734099.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Candidate.h"
+       2             : #include "crpropa/ParticleID.h"
+       3             : #include "crpropa/module/SimplePropagation.h"
+       4             : #include "crpropa/module/PropagationBP.h"
+       5             : #include "crpropa/module/PropagationCK.h"
+       6             : #include "crpropa/magneticField/turbulentField/PlaneWaveTurbulence.h"
+       7             : 
+       8             : #include "gtest/gtest.h"
+       9             : 
+      10             : #include <string>
+      11             : #include <iostream>
+      12             : 
+      13             : namespace crpropa {
+      14             : 
+      15           1 : TEST(testSimplePropagation, step) {
+      16           1 :         double minStep = 20;
+      17           1 :         double maxStep = 100;
+      18           1 :         SimplePropagation propa(minStep, maxStep);
+      19             : 
+      20           1 :         ParticleState p;
+      21           1 :         p.setPosition(Vector3d(0, 0, 0));
+      22           1 :         p.setDirection(Vector3d(0, 1, 0));
+      23             : 
+      24           1 :         Candidate c(p);
+      25           1 :         c.setNextStep(10);
+      26             : 
+      27           1 :         propa.process(&c);
+      28             : 
+      29           1 :         EXPECT_EQ(minStep, c.getCurrentStep());
+      30           1 :         EXPECT_EQ(maxStep, c.getNextStep());
+      31           2 :         EXPECT_EQ(Vector3d(0,  0, 0), c.created.getPosition());
+      32           2 :         EXPECT_EQ(Vector3d(0,  1, 0), c.created.getDirection());
+      33           2 :         EXPECT_EQ(Vector3d(0,  0, 0), c.previous.getPosition());
+      34           2 :         EXPECT_EQ(Vector3d(0,  1, 0), c.previous.getDirection());
+      35           2 :         EXPECT_EQ(Vector3d(0, 20, 0), c.current.getPosition());
+      36           2 :         EXPECT_EQ(Vector3d(0,  1, 0), c.current.getDirection());
+      37           2 : }
+      38             : 
+      39             : 
+      40           1 : TEST(testPropagationCK, zeroField) {
+      41           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 0)));
+      42             : 
+      43             :         double minStep = 0.1 * kpc;
+      44           1 :         propa.setMinimumStep(minStep);
+      45             : 
+      46           1 :         ParticleState p;
+      47           1 :         p.setId(nucleusId(1, 1));
+      48           1 :         p.setEnergy(100 * EeV);
+      49           1 :         p.setPosition(Vector3d(0, 0, 0));
+      50           1 :         p.setDirection(Vector3d(0, 1, 0));
+      51           1 :         Candidate c(p);
+      52           1 :         c.setNextStep(0);
+      53             : 
+      54           1 :         propa.process(&c);
+      55             : 
+      56           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step
+      57           1 :         EXPECT_DOUBLE_EQ(5 * minStep, c.getNextStep());  // acceleration by factor 5
+      58           1 : }
+      59             : 
+      60             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
+      61           1 : TEST(testPropagationCK, exceptions) {
+      62             :         // minStep should be smaller than maxStep
+      63           2 :         EXPECT_THROW(PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 0.42, 10 , 0), std::runtime_error);
+      64             :         // Too large tolerance: tolerance should be between 0 and 1
+      65           2 :         EXPECT_THROW(PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 42., 10 * kpc , 20 * kpc), std::runtime_error);
+      66             : 
+      67           2 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+      68             : 
+      69             :         // set maximum step, so that it can be tested what happens if a larger minStep is set.
+      70           1 :         propa.setMaximumStep(1 * Mpc);
+      71             : 
+      72             :         // this tests _that_ the expected exception is thrown
+      73           1 :         EXPECT_THROW(propa.setTolerance(2.), std::runtime_error);
+      74           1 :         EXPECT_THROW(propa.setMinimumStep(-1.), std::runtime_error);
+      75           1 :         EXPECT_THROW(propa.setMinimumStep(2 * Mpc), std::runtime_error);
+      76             : 
+      77             :         // set minimum step, so that it can be tested what happens if a smaller maxStep is set.
+      78           1 :         propa.setMinimumStep(0.5 * Mpc);
+      79             : 
+      80           1 :         EXPECT_THROW(propa.setMaximumStep(0.1 * Mpc), std::runtime_error);
+      81           1 : }
+      82             : #endif
+      83             : 
+      84           1 : TEST(testPropagationCK, constructor) {
+      85             :         // Test construction and parameters
+      86           1 :         ref_ptr<MagneticField> bField = new UniformMagneticField(Vector3d(0, 0, 1 * nG));
+      87             : 
+      88           1 :         double minStep = 1.;
+      89           1 :         double maxStep = 100.;
+      90           1 :         double tolerance = 0.01;
+      91             : 
+      92           1 :         PropagationCK propa(bField, tolerance, minStep, maxStep);
+      93             : 
+      94           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
+      95           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
+      96           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
+      97           2 :         EXPECT_EQ(bField, propa.getField());
+      98             : 
+      99             :         // Update parameters
+     100           1 :         minStep = 10.;
+     101           1 :         maxStep = 10.;
+     102           1 :         propa.setTolerance(0.0001);
+     103           1 :         bField = new UniformMagneticField(Vector3d(10 * nG, 0, 1 * nG));
+     104             : 
+     105           1 :         propa.setTolerance(tolerance);
+     106           1 :         propa.setMinimumStep(minStep);
+     107           1 :         propa.setMaximumStep(maxStep);
+     108           1 :         propa.setField(bField);
+     109             : 
+     110           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
+     111           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
+     112           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
+     113           2 :         EXPECT_EQ(bField, propa.getField());
+     114             : 
+     115             :         // The propagation should be initialized with the default constructor
+     116           2 :         PropagationCK propaCKField(bField);
+     117           1 :         EXPECT_EQ(propaCKField.getMaximumStep(), 1 * Gpc);
+     118           2 : }
+     119             : 
+     120             : 
+     121             : // Test if the step size is reduced correctly if the error is too large with respect to the tolerance: r > 1
+     122           1 : TEST(testPropagationCK, reduceStep) {
+     123           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 100 * nG)));
+     124             : 
+     125             :         double minStep = 0.1 * kpc;
+     126             :         double maxStep = 1 * Gpc;
+     127           1 :         propa.setMinimumStep(minStep);
+     128           1 :         propa.setMaximumStep(maxStep);
+     129             :         // small tolerance leads to large values of r
+     130           1 :         propa.setTolerance(1e-15);
+     131             : 
+     132           1 :         ParticleState p;
+     133           1 :         p.setId(nucleusId(1, 1));
+     134           1 :         p.setEnergy(100 * TeV);
+     135           1 :         p.setPosition(Vector3d(0, 0, 0));
+     136           1 :         p.setDirection(Vector3d(0, 1, 0));
+     137           1 :         Candidate c(p);
+     138             :         // large step leads to large errors and thus in combination with the low tolerance to high values of r
+     139           1 :         c.setNextStep(maxStep);
+     140             : 
+     141           1 :         propa.process(&c);
+     142             : 
+     143             :         // adaptive algorithm should propagate particle with minimum step size due to the low value for the tolerance
+     144           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step because of large r due to small tolerance
+     145           1 :         EXPECT_DOUBLE_EQ(minStep, c.getNextStep());  // stay at minimum step because of large r due to small tolerance
+     146           1 : }
+     147             : 
+     148             : 
+     149             : // Test if the step size is increased correctly if the error is small with respect to the tolerance: r < 1
+     150           1 : TEST(testPropagationCK, increaseStep) {
+     151           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     152             : 
+     153             :         double minStep = 0.001 * pc;
+     154             :         double maxStep = 3.125 * pc;
+     155           1 :         propa.setMinimumStep(minStep);
+     156           1 :         propa.setMaximumStep(maxStep);
+     157             :         // large tolerance leads to small values of r. Consequently, the step size can be increased.
+     158           1 :         propa.setTolerance(0.9);
+     159             : 
+     160           1 :         ParticleState p;
+     161           1 :         p.setId(nucleusId(1, 1));
+     162           1 :         p.setEnergy(100 * EeV);
+     163           1 :         p.setPosition(Vector3d(0, 0, 0));
+     164           1 :         p.setDirection(Vector3d(0, 1, 0));
+     165           1 :         Candidate c(p);
+     166             : 
+     167             :         // each step the step size can be increased by a factor of 5.
+     168           6 :         for (int i = 1; i < 6; i++){
+     169           5 :                 propa.process(&c);
+     170           5 :                 EXPECT_DOUBLE_EQ(minStep*pow(5, i) / pc, c.getNextStep()/pc);
+     171             :         }
+     172             :         // after 5 steps the maxStep is reached. The current step is, however, less.
+     173           1 :         EXPECT_DOUBLE_EQ(maxStep/pc/5., c.getCurrentStep()/pc);
+     174           1 :         EXPECT_DOUBLE_EQ(maxStep/pc, c.getNextStep()/pc);
+     175           1 : }
+     176             : 
+     177             : 
+     178           1 : TEST(testPropagationCK, proton) {
+     179           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     180             : 
+     181             :         double minStep = 0.1 * kpc;
+     182           1 :         propa.setMinimumStep(minStep);
+     183             : 
+     184           1 :         ParticleState p;
+     185           1 :         p.setId(nucleusId(1, 1));
+     186           1 :         p.setEnergy(100 * EeV);
+     187           1 :         p.setPosition(Vector3d(0, 0, 0));
+     188           1 :         p.setDirection(Vector3d(0, 1, 0));
+     189           1 :         Candidate c(p);
+     190           1 :         c.setNextStep(0);
+     191             : 
+     192           1 :         propa.process(&c);
+     193             : 
+     194           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step
+     195           1 :         EXPECT_DOUBLE_EQ(5 * minStep, c.getNextStep());  // acceleration by factor 5
+     196           1 : }
+     197             : 
+     198             : 
+     199             : // Test the numerical results for parallel magnetic field lines along the z-axis
+     200           1 : TEST(testPropagationCK, gyration) {
+     201           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     202             : 
+     203             :         double step = 10. * Mpc;  // gyroradius is 108.1 Mpc
+     204           1 :         propa.setMaximumStep(step);
+     205           1 :         propa.setMinimumStep(step);
+     206             : 
+     207             : 
+     208           1 :         ParticleState p;
+     209           1 :         p.setId(nucleusId(1, 1));
+     210           1 :         p.setEnergy(100 * EeV);
+     211           1 :         p.setPosition(Vector3d(0, 0, 0));
+     212           1 :         p.setDirection(Vector3d(1, 1, 1));
+     213           1 :         Candidate c(p);
+     214           1 :         c.setNextStep(0);
+     215           1 :         propa.process(&c);
+     216             : 
+     217           1 :         double dirX = c.current.getDirection().x;
+     218           1 :         double dirY = c.current.getDirection().y;
+     219           1 :         double dirZ = c.current.getDirection().z;
+     220           1 :         double posZ = c.current.getPosition().z;
+     221             : 
+     222             :         // Test if the analytical solution is achieved for the components of the momentum with the CK method as expected in
+     223             :         // the background magnetic field.
+     224             :         double precision = 1e-7;
+     225             :         double expected = 2 / 3.;
+     226           1 :         EXPECT_NEAR(expected, dirX * dirX + dirY * dirY, expected * precision);  // constant momentum in the plane perpendicular to background magnetic field field
+     227             :         expected = 1 / 3.;
+     228           1 :         EXPECT_NEAR(expected, dirZ * dirZ, expected * precision);  // constant momentum parallel to the background magnetic field
+     229             :         expected = step * step / 3.;
+     230           1 :         EXPECT_NEAR(expected, posZ * posZ, expected * precision);  // constant velocity parallel to the background magnetic field
+     231             : 
+     232             :         // Nine new steps to have finally propagated the particle ten times
+     233          10 :         for (int i = 0; i < 9; i++){
+     234           9 :                 propa.process(&c);
+     235             :         }
+     236             : 
+     237           1 :         dirX = c.current.getDirection().x;
+     238           1 :         dirY = c.current.getDirection().y;
+     239           1 :         dirZ = c.current.getDirection().z;
+     240           1 :         posZ = c.current.getPosition().z;
+     241             : 
+     242             :         // Compare the numerical solutions after ten steps with the analytical solution of the trajectories
+     243             :         expected = 2 / 3.;
+     244           1 :         EXPECT_NEAR(expected, dirX * dirX + dirY * dirY, expected * precision);  // constant momentum in the plane perpendicular to background magnetic field field
+     245             :         expected = 1 / 3.;
+     246           1 :         EXPECT_NEAR(expected, dirZ * dirZ, expected * precision);  // constant momentum parallel to the background magnetic field
+     247             :         expected = 100 * step * step / 3.;
+     248           1 :         EXPECT_NEAR(expected, posZ * posZ, expected * precision);  // constant velocity parallel to the background magnetic field
+     249           1 : }
+     250             : 
+     251             : 
+     252           1 : TEST(testPropagationCK, neutron) {
+     253           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     254           1 :         propa.setMinimumStep(1 * kpc);
+     255           1 :         propa.setMaximumStep(42 * Mpc);
+     256             : 
+     257           1 :         ParticleState p;
+     258           1 :         p.setId(nucleusId(1, 0));
+     259           1 :         p.setEnergy(100 * EeV);
+     260           1 :         p.setPosition(Vector3d(0, 0, 0));
+     261           1 :         p.setDirection(Vector3d(0, 1, 0));
+     262           1 :         Candidate c(p);
+     263             : 
+     264           1 :         propa.process(&c);
+     265             : 
+     266           1 :         EXPECT_DOUBLE_EQ(1 * kpc, c.getCurrentStep());
+     267           1 :         EXPECT_DOUBLE_EQ(42 * Mpc, c.getNextStep());
+     268           2 :         EXPECT_EQ(Vector3d(0, 1 * kpc, 0), c.current.getPosition());
+     269           2 :         EXPECT_EQ(Vector3d(0, 1, 0), c.current.getDirection());
+     270           1 : }
+     271             : 
+     272             : 
+     273           1 : TEST(testPropagationBP, zeroField) {
+     274           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 0)), 1 * kpc);
+     275             : 
+     276             :         double minStep = 0.1 * kpc;
+     277           1 :         propa.setMinimumStep(minStep);
+     278           1 :         propa.setTolerance(0.42);
+     279             : 
+     280           1 :         ParticleState p;
+     281           1 :         p.setId(nucleusId(1, 1));
+     282           1 :         p.setEnergy(100 * EeV);
+     283           1 :         p.setPosition(Vector3d(0, 0, 0));
+     284           1 :         p.setDirection(Vector3d(0, 1, 0));
+     285           1 :         Candidate c(p);
+     286           1 :         c.setNextStep(0);
+     287             : 
+     288           1 :         propa.process(&c);
+     289             : 
+     290           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step
+     291           1 :         EXPECT_DOUBLE_EQ(5 * minStep, c.getNextStep());  // acceleration by factor 5
+     292           1 : }
+     293             : 
+     294             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
+     295           1 : TEST(testPropagationBP, exceptions) {
+     296             :         // minStep should be smaller than maxStep
+     297           2 :         EXPECT_THROW(PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 0.42, 10 , 0), std::runtime_error);
+     298             :         // Too large tolerance: tolerance should be between 0 and 1
+     299           2 :         EXPECT_THROW(PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 42., 10 * kpc , 20 * kpc), std::runtime_error);
+     300             : 
+     301           2 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     302             : 
+     303             :         // set maximum step, so that it can be tested what happens if a larger minStep is set.
+     304           1 :         propa.setMaximumStep(1 * Mpc);
+     305             : 
+     306             :         // this tests _that_ the expected exception is thrown
+     307           1 :         EXPECT_THROW(propa.setTolerance(2.), std::runtime_error);
+     308           1 :         EXPECT_THROW(propa.setMinimumStep(-1.), std::runtime_error);
+     309           1 :         EXPECT_THROW(propa.setMinimumStep(2 * Mpc), std::runtime_error);
+     310             : 
+     311             :         // set minimum step, so that it can be tested what happens if a smaller maxStep is set.
+     312           1 :         propa.setMinimumStep(0.5 * Mpc);
+     313             : 
+     314           1 :         EXPECT_THROW(propa.setMaximumStep(0.1 * Mpc), std::runtime_error);
+     315           1 : }
+     316             : #endif
+     317             : 
+     318             : 
+     319           1 : TEST(testPropagationBP, constructor) {
+     320             :         // Test construction and parameters
+     321           1 :         ref_ptr<MagneticField> bField = new UniformMagneticField(Vector3d(0, 0, 1 * nG));
+     322             : 
+     323           1 :         double minStep = 1.;
+     324           1 :         double maxStep = 100.;
+     325           1 :         double tolerance = 0.01;
+     326             : 
+     327           1 :         PropagationBP propa(bField, tolerance, minStep, maxStep);
+     328             : 
+     329           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
+     330           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
+     331           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
+     332           2 :         EXPECT_EQ(bField, propa.getField());
+     333             : 
+     334             :         // Update parameters
+     335           1 :         minStep = 10.;
+     336           1 :         maxStep = 10.;
+     337           1 :         propa.setTolerance(0.0001);
+     338           1 :         bField = new UniformMagneticField(Vector3d(10 * nG, 0, 1 * nG));
+     339             : 
+     340           1 :         propa.setTolerance(tolerance);
+     341           1 :         propa.setMinimumStep(minStep);
+     342           1 :         propa.setMaximumStep(maxStep);
+     343           1 :         propa.setField(bField);
+     344             : 
+     345           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
+     346           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
+     347           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
+     348           2 :         EXPECT_EQ(bField, propa.getField());
+     349             : 
+     350             :         // Test the fixed step size version of the Boris push
+     351           1 :         minStep = 10. * kpc;
+     352           2 :         PropagationBP propaBP(bField, minStep);
+     353           1 :         EXPECT_EQ(propaBP.getMaximumStep(), propaBP.getMaximumStep());
+     354             : 
+     355             :         // The propagation should be initialized with the default constructor
+     356           2 :         PropagationBP propaBPField(bField);
+     357           1 :         EXPECT_EQ(propaBPField.getMaximumStep(), 1 * kpc);
+     358           2 : }
+     359             : 
+     360             : 
+     361             : // Test if the step size is reduced correctly if the error is too large with respect to the tolerance: r > 1
+     362           1 : TEST(testPropagationBP, reduceStep) {
+     363           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 100 * nG)), 1 * kpc);
+     364             : 
+     365             :         double minStep = 0.1 * kpc;
+     366             :         double maxStep = 1 * Gpc;
+     367           1 :         propa.setMinimumStep(minStep);
+     368           1 :         propa.setMaximumStep(maxStep);
+     369             :         // small tolerance leads to large values of r
+     370           1 :         propa.setTolerance(1e-15);
+     371             : 
+     372           1 :         ParticleState p;
+     373           1 :         p.setId(nucleusId(1, 1));
+     374           1 :         p.setEnergy(100 * TeV);
+     375           1 :         p.setPosition(Vector3d(0, 0, 0));
+     376           1 :         p.setDirection(Vector3d(0, 1, 0));
+     377           1 :         Candidate c(p);
+     378             :         // large step leads to large errors and thus in combination with the low tolerance to high values of r
+     379           1 :         c.setNextStep(maxStep);
+     380             : 
+     381           1 :         propa.process(&c);
+     382             : 
+     383             :         // adaptive algorithm should propagate particle with minimum step size due to the low value for the tolerance
+     384           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step because of large r due to small tolerance
+     385           1 :         EXPECT_DOUBLE_EQ(minStep, c.getNextStep());  // stay at minimum step because of large r due to small tolerance
+     386           1 : }
+     387             : 
+     388             : 
+     389             : // Test if the step size is increased correctly if the error is small with respect to the tolerance: r < 1
+     390           1 : TEST(testPropagationBP, increaseStep) {
+     391           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 1 * kpc);
+     392             : 
+     393             :         double minStep = 0.001 * pc;
+     394             :         double maxStep = 3.125 * pc;
+     395           1 :         propa.setMinimumStep(minStep);
+     396           1 :         propa.setMaximumStep(maxStep);
+     397             :         // large tolerance leads to small values of r. Consequently, the step size can be increased.
+     398           1 :         propa.setTolerance(0.9);
+     399             : 
+     400           1 :         ParticleState p;
+     401           1 :         p.setId(nucleusId(1, 1));
+     402           1 :         p.setEnergy(100 * EeV);
+     403           1 :         p.setPosition(Vector3d(0, 0, 0));
+     404           1 :         p.setDirection(Vector3d(0, 1, 0));
+     405           1 :         Candidate c(p);
+     406             : 
+     407             :         // each step the step size can be increased by a factor of 5.
+     408           6 :         for (int i = 1; i < 6; i++){
+     409           5 :                 propa.process(&c);
+     410           5 :                 EXPECT_DOUBLE_EQ(minStep*pow(5, i) / pc, c.getNextStep()/pc);
+     411             :         }
+     412             :         // after 5 steps the maxStep is reached. The current step is, however, less.
+     413           1 :         EXPECT_DOUBLE_EQ(maxStep/pc/5., c.getCurrentStep()/pc);
+     414           1 :         EXPECT_DOUBLE_EQ(maxStep/pc, c.getNextStep()/pc);
+     415           1 : }
+     416             : 
+     417             : 
+     418           1 : TEST(testPropagationBP, proton) {
+     419           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     420             : 
+     421             :         double step = 0.01 * kpc;
+     422           1 :         propa.setMinimumStep(step);
+     423           1 :         propa.setMaximumStep(10*step);
+     424           1 :         propa.setTolerance(0.00001);
+     425             : 
+     426           1 :         ParticleState p;
+     427           1 :         p.setId(nucleusId(1, 1));
+     428           1 :         p.setEnergy(100 * EeV);
+     429           1 :         p.setPosition(Vector3d(0, 0, 0));
+     430           1 :         p.setDirection(Vector3d(0, 1, 0));
+     431           1 :         Candidate c(p);
+     432           1 :         c.setNextStep(0);
+     433             : 
+     434           1 :         propa.process(&c);
+     435             : 
+     436           1 :         EXPECT_DOUBLE_EQ(step, c.getCurrentStep());  // perform step
+     437           1 :         EXPECT_DOUBLE_EQ(5 * step, c.getNextStep());  // acceleration by factor 5
+     438           1 : }
+     439             : 
+     440             : 
+     441             : // Test the numerical results for parallel magnetic field lines along the z-axis
+     442           1 : TEST(testPropagationBP, gyration) {
+     443           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     444             : 
+     445             :         double step = 10. * Mpc;  // gyroradius is 108.1 Mpc
+     446           1 :         propa.setMaximumStep(step);
+     447           1 :         propa.setMinimumStep(step);
+     448             : 
+     449             : 
+     450           1 :         ParticleState p;
+     451           1 :         p.setId(nucleusId(1, 1));
+     452           1 :         p.setEnergy(100 * EeV);
+     453           1 :         p.setPosition(Vector3d(0, 0, 0));
+     454           1 :         p.setDirection(Vector3d(1, 1, 1));
+     455           1 :         Candidate c(p);
+     456           1 :         c.setNextStep(0);
+     457           1 :         propa.process(&c);
+     458             : 
+     459           1 :         double dirX = c.current.getDirection().x;
+     460           1 :         double dirY = c.current.getDirection().y;
+     461           1 :         double dirZ = c.current.getDirection().z;
+     462           1 :         double posZ = c.current.getPosition().z;
+     463             : 
+     464             :         // Test if the analytical solution is achieved for the components of the momentum with the Boris push as expected in
+     465             :         // the background magnetic field.
+     466           1 :         EXPECT_DOUBLE_EQ(2 / 3., dirX * dirX + dirY * dirY);  // constant momentum in the perpendicular plane to background magnetic field field
+     467           1 :         EXPECT_DOUBLE_EQ(1 / 3., dirZ * dirZ);  // constant momentum parallel to the background magnetic field
+     468           1 :         EXPECT_DOUBLE_EQ( step * step / 3., posZ * posZ);  // constant velocity parallel to the background magnetic field
+     469             : 
+     470             :         // Nine new steps to have finally propagated the particle ten times
+     471          10 :         for (int i = 0; i < 9; i++){
+     472           9 :                 propa.process(&c);
+     473             :         }
+     474             : 
+     475           1 :         dirX = c.current.getDirection().x;
+     476           1 :         dirY = c.current.getDirection().y;
+     477           1 :         dirZ = c.current.getDirection().z;
+     478           1 :         posZ = c.current.getPosition().z;
+     479             : 
+     480             :         // Compare the numerical solutions after ten steps with the analytical solution of the trajectories
+     481           1 :         EXPECT_DOUBLE_EQ(2 / 3., dirX * dirX + dirY * dirY);  // constant momentum in the perpendicular plane to background magnetic field field
+     482           1 :         EXPECT_DOUBLE_EQ(1 / 3., dirZ * dirZ);  // constant momentum parallel to the background magnetic field
+     483           1 :         EXPECT_DOUBLE_EQ(100 * step * step / 3., posZ * posZ);  // constant velocity parallel to the background magnetic field
+     484           1 : }
+     485             : 
+     486             : 
+     487             : // Test the that the optimization for fixed step sizes works
+     488           1 : TEST(testPropagationBP, fixedStepOptimization) {
+     489             :         // particle 1 with fixed step sizes
+     490             :         double fixed_step = pc;
+     491           2 :         PropagationBP propa1(new PlaneWaveTurbulence(TurbulenceSpectrum(gauss, pc, 100*pc), 10, 1), fixed_step);
+     492           1 :         ParticleState p1;
+     493           1 :         p1.setId(nucleusId(1, 1));
+     494           1 :         p1.setEnergy(100 * EeV);
+     495           1 :         p1.setPosition(Vector3d(0, 0, 0));
+     496           1 :         p1.setDirection(Vector3d(1, 1, 1));
+     497           1 :         Candidate c1(p1);
+     498           1 :         c1.setNextStep(0);
+     499             :         // Nine new steps to have finally propagated the particle ten times
+     500          10 :         for (int i = 0; i < 9; i++){
+     501           9 :                 propa1.process(&c1);
+     502             :         }
+     503             : 
+     504             :         // particle 2 with different min and max steps. The tolerance is chosen such that particle 2 will be
+     505             :         // propagated with the same step as particle 1, however not using the optimization for fixed step sizes
+     506             :         double tolerance = 1;
+     507           2 :         PropagationBP propa2(new PlaneWaveTurbulence(TurbulenceSpectrum(gauss, pc, 100*pc), 10, 1), tolerance, fixed_step, 1.1*fixed_step);
+     508           1 :         ParticleState p2;
+     509           1 :         p2.setId(nucleusId(1, 1));
+     510           1 :         p2.setEnergy(100 * EeV);
+     511           1 :         p2.setPosition(Vector3d(0, 0, 0));
+     512           1 :         p2.setDirection(Vector3d(1, 1, 1));
+     513           1 :         Candidate c2(p2);
+     514           1 :         c1.setNextStep(0);
+     515             :         // Nine new steps to have finally propagated the particle ten times
+     516          10 :         for (int i = 0; i < 9; i++){
+     517           9 :                 propa2.process(&c2);
+     518             :         }
+     519             : 
+     520           1 :         EXPECT_DOUBLE_EQ(c1.current.getDirection().x, c2.current.getDirection().x);
+     521           1 :         EXPECT_DOUBLE_EQ(c1.current.getDirection().y, c2.current.getDirection().y);
+     522           1 :         EXPECT_DOUBLE_EQ(c1.current.getDirection().z, c2.current.getDirection().z);
+     523           1 :         EXPECT_DOUBLE_EQ(c1.current.getPosition().x, c2.current.getPosition().x);
+     524           1 :         EXPECT_DOUBLE_EQ(c1.current.getPosition().y, c2.current.getPosition().y);
+     525           1 :         EXPECT_DOUBLE_EQ(c1.current.getPosition().z, c2.current.getPosition().z);
+     526           1 : }
+     527             : 
+     528             : 
+     529           1 : TEST(testPropagationBP, neutron) {
+     530           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
+     531             : 
+     532           1 :         propa.setMinimumStep(1 * kpc);
+     533           1 :         propa.setMaximumStep(1 * kpc);
+     534             : 
+     535           1 :         ParticleState p;
+     536           1 :         p.setId(nucleusId(1, 0));
+     537           1 :         p.setEnergy(100 * EeV);
+     538           1 :         p.setPosition(Vector3d(0, 0, 0));
+     539           1 :         p.setDirection(Vector3d(0, 1, 0));
+     540           1 :         Candidate c(p);
+     541             : 
+     542           1 :         propa.process(&c);
+     543             : 
+     544           1 :         EXPECT_DOUBLE_EQ(1 * kpc, c.getCurrentStep());
+     545           1 :         EXPECT_DOUBLE_EQ(1 * kpc, c.getNextStep());
+     546           2 :         EXPECT_EQ(Vector3d(0, 1 * kpc, 0), c.current.getPosition());
+     547           2 :         EXPECT_EQ(Vector3d(0, 1, 0), c.current.getDirection());
+     548           1 : }
+     549             : 
+     550             : 
+     551           0 : int main(int argc, char **argv) {
+     552           0 :         ::testing::InitGoogleTest(&argc, argv);
+     553           0 :         return RUN_ALL_TESTS();
+     554             : }
+     555             : 
+     556             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testSource.cpp.func-sort-c.html b/doc/coverageReport/test/testSource.cpp.func-sort-c.html new file mode 100644 index 000000000..d2aaccaf2 --- /dev/null +++ b/doc/coverageReport/test/testSource.cpp.func-sort-c.html @@ -0,0 +1,168 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testSource.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testSource.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:27928398.6 %
Date:2024-04-08 14:58:22Functions:232495.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa24SourceList_noSource_Test8TestBodyEv1
_ZN7crpropa24SourceTag_sourceTag_Test8TestBodyEv1
_ZN7crpropa26SourceList_luminosity_Test8TestBodyEv1
_ZN7crpropa26SourceList_simpleTest_Test8TestBodyEv1
_ZN7crpropa29Source_allPropertiesUsed_Test8TestBodyEv1
_ZN7crpropa30SourcePosition_simpleTest_Test8TestBodyEv1
_ZN7crpropa32SourceUniformBox_simpleTest_Test8TestBodyEv1
_ZN7crpropa33SourceComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa34SourceDensityGrid_withInRange_Test8TestBodyEv1
_ZN7crpropa34SourceEmissionCone_simpleTest_Test8TestBodyEv1
_ZN7crpropa35SourceUniformSphere_simpleTest_Test8TestBodyEv1
_ZN7crpropa36SourceDensityGrid1D_withInRange_Test8TestBodyEv1
_ZN7crpropa37SourceComposition_throwNoIsotope_Test8TestBodyEv1
_ZN7crpropa37SourceDensityGrid_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa37SourceSNRDistribution_simpleTest_Test8TestBodyEv1
_ZN7crpropa37SourceUniformCylinder_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourceDirectedEmission_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourcePowerLawSpectrum_simpleTest_Test8TestBodyEv1
_ZN7crpropa39SourceDensityGrid1D_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa39SourceMultiplePositions_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceGenericComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceRedshiftEvolution_testInRange_Test8TestBodyEv1
_ZN7crpropa41SourceUniformHollowSphere_simpleTest_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testSource.cpp.func.html b/doc/coverageReport/test/testSource.cpp.func.html new file mode 100644 index 000000000..03ae49b49 --- /dev/null +++ b/doc/coverageReport/test/testSource.cpp.func.html @@ -0,0 +1,168 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testSource.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testSource.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:27928398.6 %
Date:2024-04-08 14:58:22Functions:232495.8 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa24SourceList_noSource_Test8TestBodyEv1
_ZN7crpropa24SourceTag_sourceTag_Test8TestBodyEv1
_ZN7crpropa26SourceList_luminosity_Test8TestBodyEv1
_ZN7crpropa26SourceList_simpleTest_Test8TestBodyEv1
_ZN7crpropa29Source_allPropertiesUsed_Test8TestBodyEv1
_ZN7crpropa30SourcePosition_simpleTest_Test8TestBodyEv1
_ZN7crpropa32SourceUniformBox_simpleTest_Test8TestBodyEv1
_ZN7crpropa33SourceComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa34SourceDensityGrid_withInRange_Test8TestBodyEv1
_ZN7crpropa34SourceEmissionCone_simpleTest_Test8TestBodyEv1
_ZN7crpropa35SourceUniformSphere_simpleTest_Test8TestBodyEv1
_ZN7crpropa36SourceDensityGrid1D_withInRange_Test8TestBodyEv1
_ZN7crpropa37SourceComposition_throwNoIsotope_Test8TestBodyEv1
_ZN7crpropa37SourceDensityGrid_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa37SourceSNRDistribution_simpleTest_Test8TestBodyEv1
_ZN7crpropa37SourceUniformCylinder_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourceDirectedEmission_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourcePowerLawSpectrum_simpleTest_Test8TestBodyEv1
_ZN7crpropa39SourceDensityGrid1D_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa39SourceMultiplePositions_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceGenericComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceRedshiftEvolution_testInRange_Test8TestBodyEv1
_ZN7crpropa41SourceUniformHollowSphere_simpleTest_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testSource.cpp.gcov.html b/doc/coverageReport/test/testSource.cpp.gcov.html new file mode 100644 index 000000000..5c0300eea --- /dev/null +++ b/doc/coverageReport/test/testSource.cpp.gcov.html @@ -0,0 +1,516 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testSource.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testSource.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:27928398.6 %
Date:2024-04-08 14:58:22Functions:232495.8 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Source.h"
+       2             : #include "crpropa/Units.h"
+       3             : #include "crpropa/ParticleID.h"
+       4             : 
+       5             : #include "gtest/gtest.h"
+       6             : #include <stdexcept>
+       7             : 
+       8             : namespace crpropa {
+       9             : 
+      10           2 : TEST(SourcePosition, simpleTest) {
+      11             :         Vector3d position(1, 2, 3);
+      12           1 :         SourcePosition source(position);
+      13           1 :         ParticleState ps;
+      14           1 :         source.prepareParticle(ps);
+      15           2 :         EXPECT_EQ(position, ps.getPosition());
+      16           1 : }
+      17             : 
+      18           1 : TEST(SourceMultiplePositions, simpleTest) {
+      19           1 :         SourceMultiplePositions source;
+      20           1 :         source.add(Vector3d(1, 0, 0), 0.25);
+      21           1 :         source.add(Vector3d(2, 0, 0), 0.75);
+      22           1 :         ParticleState ps;
+      23             :         int n1 = 0;
+      24             :         int n2 = 0;
+      25       10001 :         for (int i = 0; i < 10000; i++) {
+      26       10000 :                 source.prepareParticle(ps);
+      27       10000 :                 if (ps.getPosition().x == 1)
+      28        2585 :                         n1++;
+      29        7415 :                 else if (ps.getPosition().x == 2)
+      30        7415 :                         n2++;
+      31             :         }
+      32           1 :         EXPECT_NEAR(n1, 2500, 5 * sqrt(2500));
+      33           1 :         EXPECT_NEAR(n2, 7500, 5 * sqrt(7500));
+      34           1 : }
+      35             : 
+      36           2 : TEST(SourceUniformSphere, simpleTest) {
+      37             :         Vector3d center(0, 0, 0);
+      38           1 :         double radius = 110;
+      39           1 :         SourceUniformSphere source(center, radius);
+      40           1 :         ParticleState ps;
+      41           1 :         source.prepareParticle(ps);
+      42           1 :         double distance = ps.getPosition().getDistanceTo(center);
+      43           1 :         EXPECT_GE(radius, distance);
+      44           1 : }
+      45             : 
+      46           2 : TEST(SourceUniformHollowSphere, simpleTest) {
+      47             :         Vector3d center(0, 0, 0);
+      48           1 :         double radius_inner = 50;
+      49           1 :         double radius_outer = 110;
+      50             :         SourceUniformHollowSphere source(center,
+      51             :                         radius_inner,
+      52           1 :                         radius_outer);
+      53         101 :         for (int i=0; i < 100; ++i) {
+      54         100 :                 ParticleState ps;
+      55         100 :                 source.prepareParticle(ps);
+      56         100 :                 double distance = ps.getPosition().getDistanceTo(center);
+      57         100 :                 EXPECT_GE(radius_outer, distance);
+      58         100 :                 EXPECT_LE(radius_inner, distance);
+      59             :         }
+      60           1 : }
+      61             : 
+      62           2 : TEST(SourceUniformBox, simpleTest) {
+      63             :         Vector3d origin(-7, -2, 0);
+      64             :         Vector3d size(13, 55, 192);
+      65           1 :         SourceUniformBox box(origin, size);
+      66           1 :         ParticleState p;
+      67           1 :         box.prepareParticle(p);
+      68           1 :         Vector3d pos = p.getPosition();
+      69           1 :         EXPECT_LE(origin.x, pos.x);
+      70           1 :         EXPECT_LE(origin.y, pos.y);
+      71           1 :         EXPECT_LE(origin.z, pos.z);
+      72           1 :         EXPECT_GE(size.x, pos.x);
+      73           1 :         EXPECT_GE(size.y, pos.y);
+      74           1 :         EXPECT_GE(size.z, pos.z);
+      75           1 : }
+      76             : 
+      77           2 : TEST(SourceUniformCylinder, simpleTest) {
+      78             :         Vector3d center(0, 0, 0);
+      79             :         double radius = 15;
+      80             :         double height = 2;
+      81           1 :         SourceUniformCylinder cylinder(center, height, radius);
+      82           1 :         ParticleState ps;
+      83           1 :         cylinder.prepareParticle(ps);
+      84           1 :         Vector3d pos = ps.getPosition();
+      85           1 :         double R2 = pos.x*pos.x+pos.y*pos.y;
+      86           1 :         double H = pow(pos.z*pos.z, 0.5);
+      87           1 :         EXPECT_GE(radius*radius, R2);
+      88           1 :         EXPECT_GE(height/2., H);
+      89           1 : }
+      90             : 
+      91           1 : TEST(SourceSNRDistribution, simpleTest) {
+      92             :         double R_earth = 8.5*kpc;
+      93             :         double alpha = 2.0;
+      94             :         double beta = 3.53;
+      95             :         double Z_G = 0.3*kpc;
+      96           1 :         SourceSNRDistribution snr(R_earth,alpha, beta, Z_G);
+      97           1 :         ParticleState ps;
+      98           1 :         snr.prepareParticle(ps);
+      99           1 :         Vector3d pos = ps.getPosition();
+     100           1 :         double R2 = pos.x*pos.x+pos.y*pos.y;
+     101           1 :         EXPECT_GE(20*kpc*20*kpc, R2); // radius must be smaller than 20 kpc
+     102             :         
+     103             :         double R2_mean = 0.;
+     104             :         double Z_mean = 0.;
+     105      100001 :         for (size_t i=0; i<100000; i++) {
+     106      100000 :                 snr.prepareParticle(ps);
+     107      100000 :                 Vector3d pos = ps.getPosition();
+     108      100000 :                 R2_mean += pow(pos.x/kpc, 2.)+pow(pos.y/kpc, 2.);
+     109      100000 :                 Z_mean += pos.z/kpc;
+     110             :         }
+     111           1 :         R2_mean/=100000.;
+     112           1 :         Z_mean/=100000.;
+     113           1 :         EXPECT_NEAR(100.306, R2_mean, 1);
+     114           1 :         EXPECT_NEAR(0., Z_mean, 0.1);
+     115           1 : }
+     116             : 
+     117           2 : TEST(SourceDensityGrid, withInRange) {
+     118             :         // Create a grid with 10^3 cells ranging from (0, 0, 0) to (10, 10, 10)
+     119             :         Vector3d origin(0, 0, 0);
+     120             :         int cells = 10;
+     121             :         double spacing = 1;
+     122           1 :         auto grid = new Grid1f(origin, cells, spacing);
+     123          11 :         for (int ix = 0; ix < cells; ix++)
+     124         110 :                 for (int iy = 0; iy < cells; iy++)
+     125        1100 :                         for (int iz = 0; iz < cells; iz++)
+     126        1000 :                                 grid->get(ix, iy, iz) = ix * iy * iz;
+     127             : 
+     128           2 :         SourceDensityGrid source(grid);
+     129           1 :         ParticleState p;
+     130             : 
+     131           1 :         source.prepareParticle(p);
+     132           1 :         Vector3d pos = p.getPosition();
+     133             : 
+     134             :         // dialed positions should be within the volume (0, 0, 0) - (10, 10, 10)
+     135           1 :         EXPECT_LE(0, pos.x);
+     136           1 :         EXPECT_GE(10, pos.x);
+     137           1 :         EXPECT_LE(0, pos.y);
+     138           1 :         EXPECT_GE(10, pos.y);
+     139           1 :         EXPECT_LE(0, pos.z);
+     140           1 :         EXPECT_GE(10, pos.z);
+     141           1 : }
+     142             : 
+     143           2 : TEST(SourceDensityGrid, OneAllowedCell) {
+     144             :         // Create a grid with 2^3 cells ranging from (0, 0, 0) to (4, 4, 4)
+     145             :         Vector3d origin(0, 0, 0);
+     146             :         int cells = 2;
+     147             :         double spacing = 2;
+     148           1 :         auto grid = new Grid1f(origin, cells, spacing);
+     149             :         
+     150             :         // set all but one cells to 0
+     151           3 :         for (int ix = 0; ix < cells; ix++)
+     152           6 :                 for (int iy = 0; iy < cells; iy++)
+     153          12 :                         for (int iz = 0; iz < cells; iz++)
+     154           8 :                                 grid->get(ix, iy, iz) = 0;
+     155             : 
+     156             :         // set the first cell ((0, 0, 0) to (2, 2, 2))
+     157           1 :         grid->get(0, 0, 0) = 1;
+     158             : 
+     159           2 :         SourceDensityGrid source(grid);
+     160           1 :         ParticleState p;
+     161             : 
+     162           1 :         int nFalse = 0;
+     163             :         Vector3d mean(0, 0, 0);
+     164       10001 :         for (int i = 0; i < 10000; i++) {
+     165       10000 :                 source.prepareParticle(p);
+     166       10000 :                 Vector3d pos = p.getPosition();
+     167             :                 mean += pos;
+     168       10000 :                 if ((pos.x < 0) or (pos.x > 2) or (pos.y < 0) or (pos.y > 2)
+     169       10000 :                                 or (pos.z < 0) or (pos.z > 2))
+     170           0 :                         nFalse++;
+     171             :         }
+     172             : 
+     173             :         // only the first bin should get dialed
+     174           1 :         EXPECT_EQ(0, nFalse);
+     175             : 
+     176             :         // mean should be close to (1, 1, 1) if random positions are uniform in (0, 0, 0) - (2, 2, 2)
+     177             :         mean /= 10000;
+     178           1 :         EXPECT_NEAR(1, mean.x, 0.2);
+     179           1 :         EXPECT_NEAR(1, mean.y, 0.2);
+     180           1 :         EXPECT_NEAR(1, mean.z, 0.2);
+     181           1 : }
+     182             : 
+     183           2 : TEST(SourceDensityGrid1D, withInRange) {
+     184             :         // Create a grid with 10 cells ranging from 0 to 10
+     185             :         Vector3d origin(0, 0, 0);
+     186             :         int nCells = 10;
+     187             :         double spacing = 1.;
+     188           1 :         auto grid = new Grid1f(origin, nCells, 1, 1, spacing);
+     189             : 
+     190             :         // set some values
+     191          11 :         for (int i = 0; i < 10; i++) {
+     192          10 :                 grid->get(i, 0, 0) = 2;
+     193             :         }
+     194             : 
+     195           2 :         SourceDensityGrid1D source(grid);
+     196           1 :         ParticleState p;
+     197             : 
+     198           1 :         source.prepareParticle(p);
+     199           1 :         Vector3d pos = p.getPosition();
+     200             :         // dialed position should be within the range 0 - 10
+     201           1 :         EXPECT_LE(0, pos.x);
+     202           1 :         EXPECT_GE(10, pos.x);
+     203           1 : }
+     204             : 
+     205           2 : TEST(SourceDensityGrid1D, OneAllowedCell) {
+     206             :         // Test if the only allowed cells is repeatedly selected
+     207             :         Vector3d origin(0, 0, 0);
+     208             :         int nCells = 10;
+     209             :         double spacing = 1.;
+     210           1 :         auto grid = new Grid1f(origin, nCells, 1, 1, spacing);
+     211             : 
+     212             :         // set some values
+     213          11 :         for (int i = 0; i < 10; i++) {
+     214          10 :                 grid->get(i, 0, 0) = 0;
+     215             :         }
+     216           1 :         grid->get(5, 0, 0) = 1;
+     217             : 
+     218           2 :         SourceDensityGrid1D source(grid);
+     219           1 :         ParticleState p;
+     220             : 
+     221         101 :         for (int i = 0; i < 100; i++) {
+     222         100 :                 source.prepareParticle(p);
+     223             :                 // dialed position should be in range 5-6
+     224         100 :                 Vector3d pos = p.getPosition();
+     225         100 :                 EXPECT_LE(5, pos.x);
+     226         100 :                 EXPECT_GE(6, pos.x);
+     227             :         }
+     228           1 : }
+     229             : 
+     230           1 : TEST(SourcePowerLawSpectrum, simpleTest) {
+     231           1 :         double Emin = 4 * EeV;
+     232           1 :         double Emax = 200 * EeV;
+     233             :         double index = -2.7;
+     234           1 :         SourcePowerLawSpectrum spectrum(Emin, Emax, index);
+     235           1 :         ParticleState ps;
+     236           1 :         spectrum.prepareParticle(ps);
+     237             : 
+     238             :         // energy should be within Emin - Emax
+     239           1 :         EXPECT_LE(Emin, ps.getEnergy());
+     240           1 :         EXPECT_GE(Emax, ps.getEnergy());
+     241           1 : }
+     242             : 
+     243           1 : TEST(SourceComposition, simpleTest) {
+     244           1 :         double Emin = 10;
+     245             :         double Rmax = 100;
+     246             :         double index = -1;
+     247           1 :         SourceComposition source(Emin, Rmax, index);
+     248           1 :         source.add(nucleusId(6, 3), 1);
+     249           1 :         ParticleState p;
+     250           1 :         source.prepareParticle(p);
+     251           1 :         EXPECT_EQ(nucleusId(6, 3), p.getId());
+     252           1 :         EXPECT_LE(Emin, p.getEnergy());
+     253           1 :         EXPECT_GE(6 * Rmax, p.getEnergy());
+     254           1 : }
+     255             : 
+     256           2 : TEST(SourceDirectedEmission, simpleTest) {
+     257             :         Vector3d mu(1., 0., 0.);
+     258             :         double kappa = 1000.;
+     259           1 :         SourceDirectedEmission source(mu, kappa);
+     260           1 :         Candidate c;
+     261             :         Vector3d meanDir(0., 0., 0.);
+     262        1001 :         for (size_t i = 0; i < 1000; i++) {
+     263        1000 :                 source.prepareCandidate(c);
+     264        1000 :                 meanDir += c.source.getDirection();
+     265        1000 :                 double w = c.getWeight();
+     266        1000 :                 EXPECT_GE(w, 0.);
+     267             :         }
+     268             :         meanDir /= 1000.;
+     269           1 :         EXPECT_NEAR(meanDir.x, 1., 0.1);
+     270           1 :         EXPECT_NEAR(meanDir.y, 0., 0.01);
+     271           1 :         EXPECT_NEAR(meanDir.z, 0., 0.01);
+     272           2 : }
+     273             : 
+     274           2 : TEST(SourceEmissionCone, simpleTest) {
+     275             :         Vector3d direction(42., 0., 0.);
+     276           1 :         double aperture = 1/42.;
+     277             :         
+     278           1 :         SourceEmissionCone source(direction, aperture);
+     279             :         
+     280           1 :         ParticleState p;
+     281           1 :         source.prepareParticle(p);
+     282           1 :         double angle = direction.getAngleTo(p.getDirection());
+     283           1 :         EXPECT_LE(angle, aperture);
+     284           1 : }
+     285             : 
+     286             : #ifdef CRPROPA_HAVE_MUPARSER
+     287           1 : TEST(SourceGenericComposition, simpleTest) {
+     288             :         double Emin = 10;
+     289             :         double Emax = 100;
+     290           1 :         SourceGenericComposition source(Emin, Emax, "E^-2");
+     291           1 :         int id1 = nucleusId(6, 3);
+     292           1 :         int id2 = nucleusId(12, 6);
+     293           1 :         source.add(id1, 1);
+     294           1 :         source.add(id2, 10);
+     295           1 :         ParticleState p;
+     296             :         size_t id1Count = 0, id2Count = 0;
+     297             :         size_t ElowCount = 0, EhighCount = 0;
+     298           1 :         size_t n = 100000;
+     299      100001 :         for (size_t i = 0; i < n; i++) {
+     300      100000 :                 source.prepareParticle(p);
+     301      100000 :                 if (p.getId() == id1)
+     302        8964 :                         id1Count++;
+     303      100000 :                 if (p.getId() == id2)
+     304       91036 :                         id2Count++;
+     305      100000 :                 double e = p.getEnergy();
+     306      100000 :                 if ( (e >= Emin) && (e < 20))
+     307       55702 :                         ElowCount++;
+     308      100000 :                 if ( (e >= 20) && (e <= Emax))
+     309       44298 :                         EhighCount++;
+     310             : 
+     311             :         }
+     312           1 :         EXPECT_EQ(n, id1Count + id2Count);
+     313           1 :         EXPECT_EQ(n, ElowCount + EhighCount);
+     314           1 :         EXPECT_NEAR((float)id1Count/(float)id2Count, 0.1, 0.01);
+     315           1 :         EXPECT_NEAR((float)ElowCount/(float)EhighCount, 1.25, 0.1);
+     316           1 : }
+     317             : #endif
+     318             : 
+     319           1 : TEST(SourceComposition, throwNoIsotope) {
+     320           1 :         SourceComposition source(1, 10, -1);
+     321           1 :         ParticleState ps;
+     322           1 :         EXPECT_THROW(source.prepareParticle(ps), std::runtime_error);
+     323           1 : }
+     324             : 
+     325           1 : TEST(SourceRedshiftEvolution, testInRange) {
+     326           1 :         Candidate c;
+     327             : 
+     328           1 :         double zmin = 0.5;
+     329           1 :         double zmax = 2.5;
+     330             : 
+     331             :         // general case: m
+     332           1 :         SourceRedshiftEvolution source1(3.2, zmin, zmax);
+     333         101 :         for (int i = 0; i < 100; i++) {
+     334         100 :                 source1.prepareCandidate(c);
+     335         100 :                 EXPECT_LE(zmin, c.getRedshift());
+     336         100 :                 EXPECT_GE(zmax, c.getRedshift());
+     337             :         }
+     338             : 
+     339             :         // general case: m = -1
+     340           1 :         SourceRedshiftEvolution source2(-1, zmin, zmax);
+     341         101 :         for (int i = 0; i < 100; i++) {
+     342         100 :                 source2.prepareCandidate(c);
+     343         100 :                 EXPECT_LE(zmin, c.getRedshift());
+     344         100 :                 EXPECT_GE(zmax, c.getRedshift());
+     345             :         }
+     346           1 : }
+     347             : 
+     348           2 : TEST(Source, allPropertiesUsed) {
+     349             :         Source source;
+     350           1 :         source.add(new SourcePosition(Vector3d(10, 0, 0) * Mpc));
+     351           2 :         source.add(new SourceIsotropicEmission());
+     352           1 :         source.add(new SourcePowerLawSpectrum(5 * EeV, 100 * EeV, -2));
+     353           1 :         source.add(new SourceParticleType(nucleusId(8, 4)));
+     354           1 :         source.add(new SourceRedshift(2));
+     355             : 
+     356           1 :         Candidate c = *source.getCandidate();
+     357             : 
+     358           1 :         EXPECT_EQ(2, c.getRedshift());
+     359             : 
+     360           1 :         ParticleState p;
+     361             : 
+     362             :         p = c.source;
+     363           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
+     364           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
+     365           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
+     366           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
+     367             : 
+     368             :         p = c.created;
+     369           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
+     370           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
+     371           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
+     372           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
+     373             : 
+     374             :         p = c.previous;
+     375           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
+     376           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
+     377           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
+     378           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
+     379             : 
+     380             :         p = c.current;
+     381           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
+     382           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
+     383           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
+     384           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
+     385           2 : }
+     386             : 
+     387           2 : TEST(SourceList, simpleTest) {
+     388             :         // test if source list works with one source
+     389             :         SourceList sourceList;
+     390           1 :         ref_ptr<Source> source = new Source;
+     391           1 :         source->add(new SourcePosition(Vector3d(10, 0, 0)));
+     392           1 :         sourceList.add(source);
+     393             : 
+     394           1 :         ref_ptr<Candidate> c = sourceList.getCandidate();
+     395             : 
+     396           2 :         EXPECT_EQ(Vector3d(10, 0, 0), c->created.getPosition());
+     397           2 :         EXPECT_EQ(Vector3d(10, 0, 0), c->previous.getPosition());
+     398           2 :         EXPECT_EQ(Vector3d(10, 0, 0), c->current.getPosition());
+     399           1 : }
+     400             : 
+     401           2 : TEST(SourceList, noSource) {
+     402             :         // test if an error is thrown when source list empty
+     403             :         SourceList sourceList;
+     404           1 :         EXPECT_THROW(sourceList.getCandidate(), std::runtime_error);
+     405           1 : }
+     406             : 
+     407           2 : TEST(SourceList, luminosity) {
+     408             :         // test if the sources are dialed according to their luminosities
+     409             :         SourceList sourceList;
+     410             : 
+     411           1 :         ref_ptr<Source> source1 = new Source;
+     412           1 :         source1->add(new SourceEnergy(100));
+     413           1 :         sourceList.add(source1, 80);
+     414             : 
+     415           1 :         ref_ptr<Source> source2 = new Source;
+     416           1 :         source2->add(new SourceEnergy(0));
+     417           1 :         sourceList.add(source2, 20);
+     418             : 
+     419             :         double meanE = 0;
+     420        1001 :         for (int i = 0; i < 1000; i++) {
+     421        1000 :                 ref_ptr<Candidate> c = sourceList.getCandidate();
+     422        1000 :                 meanE += c->created.getEnergy();
+     423             :         }
+     424           1 :         meanE /= 1000;
+     425           1 :         EXPECT_NEAR(80, meanE, 4); // this test can stochastically fail
+     426           1 : }
+     427             : 
+     428           1 : TEST(SourceTag, sourceTag) {
+     429           1 :         SourceTag tag("mySourceTag");
+     430           1 :         Candidate c;
+     431           1 :         tag.prepareCandidate(c);
+     432           2 :         EXPECT_TRUE(c.getTagOrigin() == "mySourceTag");
+     433           1 : }
+     434             : 
+     435           0 : int main(int argc, char **argv) {
+     436           0 :         ::testing::InitGoogleTest(&argc, argv);
+     437           0 :         return RUN_ALL_TESTS();
+     438             : }
+     439             : 
+     440             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html b/doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html new file mode 100644 index 000000000..f9a2c170f --- /dev/null +++ b/doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testTurbulentField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testTurbulentField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4646100.0 %
Date:2024-04-08 14:58:22Functions:88100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN39testGridTurbulence_Turbulence_seed_Test8TestBodyEv1
_ZN39testTurbulenceSpectrum_constructor_Test8TestBodyEv1
_ZN40testVectorFieldGrid_Turbulence_seed_Test8TestBodyEv1
_ZN45testTurbulenceSpectrum_correlationLength_Test8TestBodyEv1
_ZN46testVectorFieldGrid_Turbulence_bmean_brms_Test8TestBodyEv1
_ZN46testVectorFieldGrid_turbulence_Exceptions_Test8TestBodyEv1
_ZN60testSimpleGridTurbulence_oldFunctionForCrrelationLength_Test8TestBodyEv1
main1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testTurbulentField.cpp.func.html b/doc/coverageReport/test/testTurbulentField.cpp.func.html new file mode 100644 index 000000000..4a96c6309 --- /dev/null +++ b/doc/coverageReport/test/testTurbulentField.cpp.func.html @@ -0,0 +1,104 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testTurbulentField.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testTurbulentField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4646100.0 %
Date:2024-04-08 14:58:22Functions:88100.0 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN39testGridTurbulence_Turbulence_seed_Test8TestBodyEv1
_ZN39testTurbulenceSpectrum_constructor_Test8TestBodyEv1
_ZN40testVectorFieldGrid_Turbulence_seed_Test8TestBodyEv1
_ZN45testTurbulenceSpectrum_correlationLength_Test8TestBodyEv1
_ZN46testVectorFieldGrid_Turbulence_bmean_brms_Test8TestBodyEv1
_ZN46testVectorFieldGrid_turbulence_Exceptions_Test8TestBodyEv1
_ZN60testSimpleGridTurbulence_oldFunctionForCrrelationLength_Test8TestBodyEv1
main1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testTurbulentField.cpp.gcov.html b/doc/coverageReport/test/testTurbulentField.cpp.gcov.html new file mode 100644 index 000000000..642a3acef --- /dev/null +++ b/doc/coverageReport/test/testTurbulentField.cpp.gcov.html @@ -0,0 +1,218 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testTurbulentField.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testTurbulentField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4646100.0 %
Date:2024-04-08 14:58:22Functions:88100.0 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include <stdexcept>
+       2             : 
+       3             : #include "crpropa/Grid.h"
+       4             : #include "crpropa/Units.h"
+       5             : #include "crpropa/Common.h"
+       6             : #include "crpropa/GridTools.h"
+       7             : #include "crpropa/magneticField/turbulentField/TurbulentField.h"
+       8             : #include "crpropa/magneticField/turbulentField/GridTurbulence.h"
+       9             : #include "crpropa/magneticField/turbulentField/PlaneWaveTurbulence.h"
+      10             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
+      11             : 
+      12             : #include "gtest/gtest.h"
+      13             : 
+      14             : using namespace crpropa;
+      15             : 
+      16             : //check problems brought up in https://github.com/CRPropa/CRPropa3/issues/322
+      17           1 : TEST(testTurbulenceSpectrum, constructor) {
+      18             :         double sIndex = 5./3.;
+      19             :         double qIndex = 4.;
+      20             :         double bendOver = 1.;
+      21             :         double lMin = 1.; 
+      22             :         double lMax = 10.; 
+      23             :         double brms = 1*muG;
+      24           1 :         auto spectrum = TurbulenceSpectrum(brms, lMin, lMax);
+      25           1 :         EXPECT_DOUBLE_EQ(spectrum.getBrms(), brms);
+      26           1 :         EXPECT_DOUBLE_EQ(spectrum.getLmin(), lMin);
+      27           1 :         EXPECT_DOUBLE_EQ(spectrum.getLmax(), lMax);
+      28           1 :         EXPECT_DOUBLE_EQ(spectrum.getLbendover(), bendOver); //default
+      29           1 :         EXPECT_DOUBLE_EQ(spectrum.getSindex(), sIndex); //default
+      30           1 :         EXPECT_DOUBLE_EQ(spectrum.getQindex(), qIndex); //default
+      31           1 : }
+      32             : 
+      33           1 : TEST(testTurbulenceSpectrum, correlationLength) {
+      34             :         double lMin = 0.00001; // not used for Lc
+      35             :         double lMax = 9999999; // not used for Lc
+      36             :         double lBo = 100;
+      37           1 :         auto spectrum = TurbulenceSpectrum(1*muG, lMin, lMax, lBo);
+      38             :         auto Lc = spectrum.getCorrelationLength();
+      39           1 :     EXPECT_NEAR(Lc, 0.498*lBo, 0.001*lBo);
+      40           1 : }
+      41             : 
+      42             : #ifdef CRPROPA_HAVE_FFTW3F
+      43             : 
+      44           1 : TEST(testSimpleGridTurbulence, oldFunctionForCrrelationLength) { //TODO: remove in future
+      45             :         double lMin = 1*kpc;
+      46             :         double lMax = 1*Gpc;
+      47             :         double alpha = -11/3.;
+      48           1 :         auto Lc = turbulentCorrelationLength(lMin, lMax, alpha);
+      49           1 :     EXPECT_NEAR(Lc, lMax/5, 1*Mpc);
+      50           1 : }
+      51             : 
+      52           2 : TEST(testVectorFieldGrid, Turbulence_bmean_brms) {
+      53             :         // Test for zero mean: <B> = 0
+      54             :         size_t n = 64;
+      55             :         double spacing = 10 * Mpc / n;
+      56             :         double Brms = 1;
+      57             :         double lMin = 2 * spacing;
+      58             :         double lMax = 8 * spacing;
+      59             : 
+      60             :         auto spectrum = SimpleTurbulenceSpectrum(Brms, lMin, lMax);
+      61             :         auto gp = GridProperties(Vector3d(0, 0, 0), n, spacing);
+      62           1 :     auto tf = SimpleGridTurbulence(spectrum, gp);
+      63           1 :         auto grid = tf.getGrid();
+      64             : 
+      65             :         double precision = 1e-7;
+      66           1 :         Vector3f bMean = meanFieldVector(grid);
+      67           1 :         EXPECT_NEAR(0, bMean.x, precision);
+      68           1 :         EXPECT_NEAR(0, bMean.y, precision);
+      69           1 :         EXPECT_NEAR(0, bMean.z, precision);
+      70           2 :         EXPECT_NEAR(1, rmsFieldStrength(grid), precision);
+      71           1 : }
+      72             : 
+      73           2 : TEST(testVectorFieldGrid, Turbulence_seed) {
+      74             :         // Test if seeding produces 2 identical fields
+      75             :         size_t n = 64;
+      76             :         double spacing = 1 * Mpc;
+      77             :         double Brms = 1;
+      78             :         double lMin = 2 * spacing;
+      79             :         double lMax = 8 * spacing;
+      80             :         int seed = 753;
+      81             :         
+      82             :         auto spectrum = SimpleTurbulenceSpectrum(Brms, lMin, lMax);
+      83             : 
+      84             :         auto gp1 = GridProperties(Vector3d(0, 0, 0), n, spacing);
+      85           1 :     auto tf1 = SimpleGridTurbulence(spectrum, gp1,  seed);
+      86             : 
+      87             :         auto gp2 = GridProperties(Vector3d(0, 0, 0), n, spacing);
+      88           1 :     auto tf2 = SimpleGridTurbulence(spectrum, gp2, seed);
+      89             : 
+      90             :         Vector3d pos(22 * Mpc);
+      91           1 :         EXPECT_FLOAT_EQ(tf1.getField(pos).x, tf2.getField(pos).x);
+      92           1 : }
+      93             : 
+      94             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
+      95           2 : TEST(testVectorFieldGrid, turbulence_Exceptions) {
+      96             :         // Test exceptions
+      97             :         size_t n = 64;
+      98             :         double spacing = 10 * Mpc / n;
+      99             :         double brms = 1;
+     100           1 :         ref_ptr<Grid3f> grid = new Grid3f(Vector3d(0, 0, 0), n, spacing);
+     101             : 
+     102             :         // should be fine
+     103           2 :         EXPECT_NO_THROW(initTurbulence(grid, brms, 2 * spacing, 8 * spacing));
+     104             :         // lMin too small
+     105           2 :         EXPECT_THROW(initTurbulence(grid, brms, 1.5 * spacing, 8 * spacing),
+     106             :                         std::runtime_error);
+     107             :         // lMin > lMax
+     108           2 :         EXPECT_THROW(initTurbulence(grid, brms, 8.1 * spacing, 8 * spacing),
+     109             :                         std::runtime_error);
+     110             :         // lMax too large
+     111           2 :         EXPECT_THROW(initTurbulence(grid, brms, 2 * spacing, 65 * spacing),
+     112             :                         std::runtime_error);
+     113           1 : }
+     114             : #endif
+     115             : 
+     116           1 : TEST(testGridTurbulence, Turbulence_seed) {
+     117             :         // Test if seeding produces 2 identical fields
+     118             :         size_t n = 64;
+     119             :         double spacing = 1 * Mpc;
+     120             :         double Brms = 1;
+     121             :         double lMin = 2 * spacing;
+     122             :         double lMax = 8 * spacing;
+     123             :         double lBo = lMax/6;
+     124             :         int seed = 137;
+     125             :         
+     126           1 :         auto spectrum = TurbulenceSpectrum(Brms, lMin, lMax, lBo);
+     127             : 
+     128             :         auto gp1 = GridProperties(Vector3d(0, 0, 0), n, spacing);
+     129           1 :     auto tf1 = GridTurbulence(spectrum, gp1, seed);
+     130             : 
+     131             :         auto gp2 = GridProperties(Vector3d(0, 0, 0), n, spacing);
+     132           1 :     auto tf2 = GridTurbulence(spectrum, gp2, seed);
+     133             : 
+     134             :         Vector3d pos(22 * Mpc);
+     135           1 :         EXPECT_FLOAT_EQ(tf1.getField(pos).x, tf2.getField(pos).x);
+     136           1 : }
+     137             : #endif // CRPROPA_HAVE_FFTW3F
+     138             : 
+     139           1 : int main(int argc, char **argv) {
+     140           1 :         ::testing::InitGoogleTest(&argc, argv);
+     141             :         return RUN_ALL_TESTS();
+     142             : }
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testVector3.cpp.func-sort-c.html b/doc/coverageReport/test/testVector3.cpp.func-sort-c.html new file mode 100644 index 000000000..b7177d48e --- /dev/null +++ b/doc/coverageReport/test/testVector3.cpp.func-sort-c.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testVector3.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testVector3.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:909396.8 %
Date:2024-04-08 14:58:22Functions:121392.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa16Vector3_dot_Test8TestBodyEv1
_ZN7crpropa16Vector3_mod_Test8TestBodyEv1
_ZN7crpropa18Vector3_angle_Test8TestBodyEv1
_ZN7crpropa18Vector3_cross_Test8TestBodyEv1
_ZN7crpropa21Vector3_distance_Test8TestBodyEv1
_ZN7crpropa21Vector3_division_Test8TestBodyEv1
_ZN7crpropa21Vector3_rotation_Test8TestBodyEv1
_ZN7crpropa22Vector3_magnitude_Test8TestBodyEv1
_ZN7crpropa23Vector3_comparison_Test8TestBodyEv1
_ZN7crpropa24Vector3_unitVectors_Test8TestBodyEv1
_ZN7crpropa27Vector3_multiplication_Test8TestBodyEv1
_ZN7crpropa34Vector3_parallelPerpendicular_Test8TestBodyEv1
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testVector3.cpp.func.html b/doc/coverageReport/test/testVector3.cpp.func.html new file mode 100644 index 000000000..f79586ce3 --- /dev/null +++ b/doc/coverageReport/test/testVector3.cpp.func.html @@ -0,0 +1,124 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testVector3.cpp - functions + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testVector3.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:909396.8 %
Date:2024-04-08 14:58:22Functions:121392.3 %
+
+ +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16Vector3_dot_Test8TestBodyEv1
_ZN7crpropa16Vector3_mod_Test8TestBodyEv1
_ZN7crpropa18Vector3_angle_Test8TestBodyEv1
_ZN7crpropa18Vector3_cross_Test8TestBodyEv1
_ZN7crpropa21Vector3_distance_Test8TestBodyEv1
_ZN7crpropa21Vector3_division_Test8TestBodyEv1
_ZN7crpropa21Vector3_rotation_Test8TestBodyEv1
_ZN7crpropa22Vector3_magnitude_Test8TestBodyEv1
_ZN7crpropa23Vector3_comparison_Test8TestBodyEv1
_ZN7crpropa24Vector3_unitVectors_Test8TestBodyEv1
_ZN7crpropa27Vector3_multiplication_Test8TestBodyEv1
_ZN7crpropa34Vector3_parallelPerpendicular_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
+
+
+ + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/test/testVector3.cpp.gcov.html b/doc/coverageReport/test/testVector3.cpp.gcov.html new file mode 100644 index 000000000..a1e919522 --- /dev/null +++ b/doc/coverageReport/test/testVector3.cpp.gcov.html @@ -0,0 +1,238 @@ + + + + + + + LCOV - coverage.info.cleaned - test/testVector3.cpp + + + + + + + + + + + + + + +
LCOV - code coverage report
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
Current view:top level - test - testVector3.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:909396.8 %
Date:2024-04-08 14:58:22Functions:121392.3 %
+
+ + + + + + + + +

+
          Line data    Source code
+
+       1             : #include "crpropa/Vector3.h"
+       2             : #include "gtest/gtest.h"
+       3             : 
+       4             : namespace crpropa {
+       5             : 
+       6           2 : TEST(Vector3, comparison) {
+       7             :         EXPECT_TRUE(Vector3d(1, 2, 3) == Vector3d(1, 2, 3));
+       8             :         EXPECT_FALSE(Vector3d(1, 2, 3) == Vector3d(2, 3, 4));
+       9           1 : }
+      10             : 
+      11           1 : TEST(Vector3, multiplication) {
+      12             :         Vector3d v(1);
+      13             :         v *= 10;
+      14           1 :         EXPECT_DOUBLE_EQ(v.x, 10);
+      15           1 :         EXPECT_DOUBLE_EQ(v.y, 10);
+      16           1 :         EXPECT_DOUBLE_EQ(v.z, 10);
+      17             :         v = Vector3d(1) * Vector3d(2); // element-wise multiplication
+      18           1 :         EXPECT_DOUBLE_EQ(v.x, 2);
+      19           1 :         EXPECT_DOUBLE_EQ(v.y, 2);
+      20           1 :         EXPECT_DOUBLE_EQ(v.z, 2);
+      21           1 : }
+      22             : 
+      23           1 : TEST(Vector3, division) {
+      24             :         Vector3d v(10);
+      25             :         v /= 10;
+      26           1 :         EXPECT_DOUBLE_EQ(v.x, 1);
+      27           1 :         EXPECT_DOUBLE_EQ(v.y, 1);
+      28           1 :         EXPECT_DOUBLE_EQ(v.z, 1);
+      29             :         v = Vector3d(10) / Vector3d(2); // element-wise division
+      30           1 :         EXPECT_DOUBLE_EQ(v.x, 5);
+      31           1 :         EXPECT_DOUBLE_EQ(v.y, 5);
+      32           1 :         EXPECT_DOUBLE_EQ(v.z, 5);
+      33           1 : }
+      34             : 
+      35           2 : TEST(Vector3, mod) {
+      36             :         Vector3d v(10.1, 10.2, 10.3);
+      37           1 :         v %= 10.2;
+      38           1 :         EXPECT_NEAR(v.x, 10.1, 1e-10); // mod doesn't preserve double precision
+      39           1 :         EXPECT_NEAR(v.y, 0, 1e-10);
+      40           1 :         EXPECT_NEAR(v.z, 0.1, 1e-10);
+      41           1 : }
+      42             : 
+      43           1 : TEST(Vector3, dot) {
+      44             :         double a = Vector3d(1, 0, 0).dot(Vector3d(0, 1, 0));
+      45           1 :         EXPECT_DOUBLE_EQ(a, 0);
+      46             :         double b = Vector3d(-1, 10, 2).dot(Vector3d(5, 1, -3));
+      47           1 :         EXPECT_DOUBLE_EQ(b, -1);
+      48           1 : }
+      49             : 
+      50           2 : TEST(Vector3, cross) {
+      51             :         Vector3d v = Vector3d(1, 0, 0).cross(Vector3d(0, 1, 0));
+      52             :         EXPECT_TRUE(v == Vector3d(0, 0, 1));
+      53           1 : }
+      54             : 
+      55           2 : TEST(Vector3, angle) {
+      56             :         // 45 degrees
+      57           1 :         double a = Vector3d(1, 1, 0).getAngleTo(Vector3d(1, 0, 0));
+      58           1 :         EXPECT_DOUBLE_EQ(a, 45 * M_PI / 180);
+      59             :         // perpendicular vectors
+      60           1 :         double b = Vector3d(0, 0, 1).getAngleTo(Vector3d(0, 0, 1));
+      61           1 :         EXPECT_DOUBLE_EQ(b, 0);
+      62           1 : }
+      63             : 
+      64           2 : TEST(Vector3, unitVectors) {
+      65             :         Vector3d v = Vector3d(2, 0, 0);
+      66           1 :         Vector3d er = v.getUnitVector();
+      67           1 :         Vector3d et = v.getUnitVectorTheta();
+      68           1 :         Vector3d ep = v.getUnitVectorPhi();
+      69             : 
+      70             :         // trigonometrical functions don't preserve double precision
+      71             :         double eps = 1e-16;
+      72           1 :         EXPECT_NEAR(er.x, 1, eps);
+      73           1 :         EXPECT_NEAR(er.y, 0, eps);
+      74           1 :         EXPECT_NEAR(er.z, 0, eps);
+      75             : 
+      76           1 :         EXPECT_NEAR(et.x, 0, eps);
+      77           1 :         EXPECT_NEAR(et.y, 0, eps);
+      78           1 :         EXPECT_NEAR(et.z, -1, eps);
+      79             : 
+      80           1 :         EXPECT_NEAR(ep.x, 0, eps);
+      81           1 :         EXPECT_NEAR(ep.y, 1, eps);
+      82           1 :         EXPECT_NEAR(ep.z, 0, eps);
+      83           1 : }
+      84             : 
+      85           1 : TEST(Vector3, magnitude) {
+      86             :         Vector3d v = Vector3d(1, 2, -2);
+      87           1 :         EXPECT_DOUBLE_EQ(v.getR(), 3);
+      88           1 :         EXPECT_DOUBLE_EQ(v.getR2(), 9);
+      89           1 : }
+      90             : 
+      91           2 : TEST(Vector3, distance) {
+      92           1 :         double a = Vector3d(10, 0, 10).getDistanceTo(Vector3d(10, 0, 0));
+      93           1 :         EXPECT_DOUBLE_EQ(a, 10);
+      94           1 : }
+      95             : 
+      96           2 : TEST(Vector3, rotation) {
+      97             :         Vector3d v, w;
+      98             : 
+      99             :         // rotation by 180 degrees
+     100             :         v = Vector3d(10, 0, 0);
+     101           1 :         w = v.getRotated(Vector3d(0, 2, 0), M_PI);
+     102           1 :         EXPECT_NEAR(w.x, -10, 1e-9);
+     103           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
+     104           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
+     105             : 
+     106             :         // rotation axis parallel to vector --> no rotation
+     107             :         v = Vector3d(10, 0, 0);
+     108           1 :         w = v.getRotated(Vector3d(1, 0, 0), M_PI);
+     109           1 :         EXPECT_NEAR(w.x, 10, 1e-9);
+     110           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
+     111           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
+     112             : 
+     113             :         // rotation by 360 degrees
+     114             :         v = Vector3d(5, 2, 7);
+     115           1 :         w = v.getRotated(Vector3d(1, 8, -4), 2 * M_PI);
+     116           1 :         EXPECT_NEAR(w.x, 5, 1e-9);
+     117           1 :         EXPECT_NEAR(w.y, 2, 1e-9);
+     118           1 :         EXPECT_NEAR(w.z, 7, 1e-9);
+     119             : 
+     120             :         // rotation by zero degrees
+     121             :         v = Vector3d(1, 0, 0);
+     122           1 :         w = v.getRotated(Vector3d(0,1,0), 0);
+     123             : 
+     124           1 :         EXPECT_NEAR(w.x, 1, 1e-9);
+     125           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
+     126           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
+     127             : 
+     128             :         // rotation around zero axis
+     129             :         v = Vector3d(1, 0, 0);
+     130             :         Vector3d a = v.cross(v);
+     131           1 :         w = v.getRotated(a, 0);
+     132             : 
+     133           1 :         EXPECT_NEAR(w.x, 1, 1e-9);
+     134           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
+     135           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
+     136             : 
+     137             : 
+     138             : 
+     139             : 
+     140           1 : }
+     141             : 
+     142           2 : TEST(Vector3, parallelPerpendicular) {
+     143             :         Vector3d v(3, 2, 1);
+     144             :         Vector3d w(0, 1, 0);
+     145             : 
+     146           1 :         Vector3d vpara = v.getParallelTo(w);
+     147           1 :         Vector3d vperp = v.getPerpendicularTo(w);
+     148             : 
+     149           1 :         EXPECT_DOUBLE_EQ(vpara.x, 0);
+     150           1 :         EXPECT_DOUBLE_EQ(vpara.y, 2);
+     151           1 :         EXPECT_DOUBLE_EQ(vpara.z, 0);
+     152           1 :         EXPECT_DOUBLE_EQ(vperp.x, 3);
+     153           1 :         EXPECT_DOUBLE_EQ(vperp.y, 0);
+     154           1 :         EXPECT_DOUBLE_EQ(vperp.z, 1);
+     155           1 : }
+     156             : 
+     157           0 : int main(int argc, char **argv) {
+     158           0 :         ::testing::InitGoogleTest(&argc, argv);
+     159           0 :         return RUN_ALL_TESTS();
+     160             : }
+     161             : 
+     162             : } // namespace crpropa
+
+
+
+ + + + +
Generated by: LCOV version 1.14
+
+ + + diff --git a/doc/coverageReport/updown.png b/doc/coverageReport/updown.png new file mode 100644 index 0000000000000000000000000000000000000000..aa56a238b3e6c435265250f9266cd1b8caba0f20 GIT binary patch literal 117 zcmeAS@N?(olHy`uVBq!ia0vp^AT}Qd8;}%R+`Ae`*?77*hG?8mPH5^{)z4*}Q$iB}huR`+ literal 0 HcmV?d00001 diff --git a/doc/pages/Code-Coverage.md b/doc/pages/Code-Coverage.md index 699f79eab..a70872b04 100644 --- a/doc/pages/Code-Coverage.md +++ b/doc/pages/Code-Coverage.md @@ -16,3 +16,10 @@ make test make coverage ``` The final report is in ```~/build/coverageReport/index.html``` + + +### Code Coverage for the current master version +The report for the current master branch version can be found here. + +.. toctree:: + conerageReport/index.html \ No newline at end of file From 2468e864561697c94f1d0425b4472f65784f7bfb Mon Sep 17 00:00:00 2001 From: Julien Date: Tue, 9 Apr 2024 10:49:25 +0200 Subject: [PATCH 10/45] add coverage report link in docu, remove pre-build coveragereport and use build instead --- .github/workflows/create_documentation.yml | 1 + doc/coverageReport/amber.png | Bin 141 -> 0 bytes doc/coverageReport/emerald.png | Bin 141 -> 0 bytes doc/coverageReport/gcov.css | 519 ----- doc/coverageReport/glass.png | Bin 167 -> 0 bytes .../numpy/__multiarray_api.h.func-sort-c.html | 76 - .../numpy/__multiarray_api.h.func.html | 76 - .../numpy/__multiarray_api.h.gcov.html | 1642 ------------- .../numpy/__ufunc_api.h.func-sort-c.html | 76 - .../include/numpy/__ufunc_api.h.func.html | 76 - .../include/numpy/__ufunc_api.h.gcov.html | 390 ---- .../core/include/numpy/index-sort-f.html | 113 - .../core/include/numpy/index-sort-l.html | 113 - .../numpy/core/include/numpy/index.html | 113 - .../numpy/ndarraytypes.h.func-sort-c.html | 72 - .../include/numpy/ndarraytypes.h.func.html | 72 - .../include/numpy/ndarraytypes.h.gcov.html | 2021 ---------------- .../crpropa/AssocVector.h.func-sort-c.html | 92 - .../include/crpropa/AssocVector.h.func.html | 92 - .../include/crpropa/AssocVector.h.gcov.html | 457 ---- .../crpropa/Candidate.h.func-sort-c.html | 72 - .../include/crpropa/Candidate.h.func.html | 72 - .../include/crpropa/Candidate.h.gcov.html | 258 -- .../include/crpropa/Common.h.func-sort-c.html | 80 - .../include/crpropa/Common.h.func.html | 80 - .../include/crpropa/Common.h.gcov.html | 163 -- .../crpropa/EmissionMap.h.func-sort-c.html | 72 - .../include/crpropa/EmissionMap.h.func.html | 72 - .../include/crpropa/EmissionMap.h.gcov.html | 212 -- .../crpropa/Geometry.h.func-sort-c.html | 76 - .../include/crpropa/Geometry.h.func.html | 76 - .../include/crpropa/Geometry.h.gcov.html | 165 -- .../include/crpropa/Grid.h.func-sort-c.html | 296 --- .../include/crpropa/Grid.h.func.html | 296 --- .../include/crpropa/Grid.h.gcov.html | 640 ----- .../crpropa/Logging.h.func-sort-c.html | 96 - .../include/crpropa/Logging.h.func.html | 96 - .../include/crpropa/Logging.h.gcov.html | 111 - .../include/crpropa/Module.h.func-sort-c.html | 72 - .../include/crpropa/Module.h.func.html | 72 - .../include/crpropa/Module.h.gcov.html | 141 -- .../crpropa/ParticleState.h.func-sort-c.html | 72 - .../include/crpropa/ParticleState.h.func.html | 72 - .../include/crpropa/ParticleState.h.gcov.html | 196 -- .../PhotonBackground.h.func-sort-c.html | 148 -- .../crpropa/PhotonBackground.h.func.html | 148 -- .../crpropa/PhotonBackground.h.gcov.html | 398 ---- .../include/crpropa/Random.h.func-sort-c.html | 72 - .../include/crpropa/Random.h.func.html | 72 - .../include/crpropa/Random.h.gcov.html | 317 --- .../crpropa/Referenced.h.func-sort-c.html | 148 -- .../include/crpropa/Referenced.h.func.html | 148 -- .../include/crpropa/Referenced.h.gcov.html | 320 --- .../include/crpropa/Source.h.func-sort-c.html | 76 - .../include/crpropa/Source.h.func.html | 76 - .../include/crpropa/Source.h.gcov.html | 1002 -------- .../crpropa/Variant.h.func-sort-c.html | 136 -- .../include/crpropa/Variant.h.func.html | 136 -- .../include/crpropa/Variant.h.gcov.html | 410 ---- .../crpropa/Vector3.h.func-sort-c.html | 236 -- .../include/crpropa/Vector3.h.func.html | 236 -- .../include/crpropa/Vector3.h.gcov.html | 516 ---- .../AdvectionField.h.func-sort-c.html | 72 - .../advectionField/AdvectionField.h.func.html | 72 - .../advectionField/AdvectionField.h.gcov.html | 367 --- .../crpropa/advectionField/index-sort-f.html | 93 - .../crpropa/advectionField/index-sort-l.html | 93 - .../include/crpropa/advectionField/index.html | 93 - .../include/crpropa/index-sort-f.html | 233 -- .../include/crpropa/index-sort-l.html | 233 -- doc/coverageReport/include/crpropa/index.html | 233 -- .../GalacticMagneticField.h.func-sort-c.html | 88 - .../GalacticMagneticField.h.func.html | 88 - .../GalacticMagneticField.h.gcov.html | 210 -- .../MagneticField.h.func-sort-c.html | 100 - .../magneticField/MagneticField.h.func.html | 100 - .../magneticField/MagneticField.h.gcov.html | 248 -- .../MagneticFieldGrid.h.func-sort-c.html | 72 - .../MagneticFieldGrid.h.func.html | 72 - .../MagneticFieldGrid.h.gcov.html | 139 -- .../crpropa/magneticField/index-sort-f.html | 113 - .../crpropa/magneticField/index-sort-l.html | 113 - .../include/crpropa/magneticField/index.html | 113 - .../GridTurbulence.h.func-sort-c.html | 72 - .../turbulentField/GridTurbulence.h.func.html | 72 - .../turbulentField/GridTurbulence.h.gcov.html | 151 -- .../HelicalGridTurbulence.h.func-sort-c.html | 76 - .../HelicalGridTurbulence.h.func.html | 76 - .../HelicalGridTurbulence.h.gcov.html | 147 -- .../SimpleGridTurbulence.h.func-sort-c.html | 100 - .../SimpleGridTurbulence.h.func.html | 100 - .../SimpleGridTurbulence.h.gcov.html | 192 -- .../TurbulentField.h.func-sort-c.html | 108 - .../turbulentField/TurbulentField.h.func.html | 108 - .../turbulentField/TurbulentField.h.gcov.html | 195 -- .../turbulentField/index-sort-f.html | 123 - .../turbulentField/index-sort-l.html | 123 - .../magneticField/turbulentField/index.html | 123 - .../MagneticLens.h.func-sort-c.html | 96 - .../magneticLens/MagneticLens.h.func.html | 96 - .../magneticLens/MagneticLens.h.gcov.html | 352 --- .../ParticleMapsContainer.h.func-sort-c.html | 80 - .../ParticleMapsContainer.h.func.html | 80 - .../ParticleMapsContainer.h.gcov.html | 221 -- .../Pixelization.h.func-sort-c.html | 84 - .../magneticLens/Pixelization.h.func.html | 84 - .../magneticLens/Pixelization.h.gcov.html | 217 -- .../crpropa/magneticLens/index-sort-f.html | 113 - .../crpropa/magneticLens/index-sort-l.html | 113 - .../include/crpropa/magneticLens/index.html | 113 - .../Cordes.h.func-sort-c.html | 72 - .../massDistribution/Cordes.h.func.html | 72 - .../massDistribution/Cordes.h.gcov.html | 121 - .../Density.h.func-sort-c.html | 116 - .../massDistribution/Density.h.func.html | 116 - .../massDistribution/Density.h.gcov.html | 134 -- .../Ferriere.h.func-sort-c.html | 72 - .../massDistribution/Ferriere.h.func.html | 72 - .../massDistribution/Ferriere.h.gcov.html | 153 -- .../Massdistribution.h.func-sort-c.html | 72 - .../Massdistribution.h.func.html | 72 - .../Massdistribution.h.gcov.html | 212 -- .../Nakanishi.h.func-sort-c.html | 72 - .../massDistribution/Nakanishi.h.func.html | 72 - .../massDistribution/Nakanishi.h.gcov.html | 150 -- .../massDistribution/index-sort-f.html | 133 -- .../massDistribution/index-sort-l.html | 133 -- .../crpropa/massDistribution/index.html | 133 -- .../module/Boundary.h.func-sort-c.html | 72 - .../crpropa/module/Boundary.h.func.html | 72 - .../crpropa/module/Boundary.h.gcov.html | 283 --- .../module/BreakCondition.h.func-sort-c.html | 72 - .../crpropa/module/BreakCondition.h.func.html | 72 - .../crpropa/module/BreakCondition.h.gcov.html | 221 -- .../module/HDF5Output.h.func-sort-c.html | 72 - .../crpropa/module/HDF5Output.h.func.html | 72 - .../crpropa/module/HDF5Output.h.gcov.html | 217 -- .../module/NuclearDecay.h.func-sort-c.html | 72 - .../crpropa/module/NuclearDecay.h.func.html | 72 - .../crpropa/module/NuclearDecay.h.gcov.html | 163 -- .../module/Observer.h.func-sort-c.html | 72 - .../crpropa/module/Observer.h.func.html | 72 - .../crpropa/module/Observer.h.gcov.html | 351 --- .../module/OutputShell.h.func-sort-c.html | 72 - .../crpropa/module/OutputShell.h.func.html | 72 - .../crpropa/module/OutputShell.h.gcov.html | 124 - .../PhotoDisintegration.h.func-sort-c.html | 72 - .../module/PhotoDisintegration.h.func.html | 72 - .../module/PhotoDisintegration.h.gcov.html | 167 -- .../module/PropagationBP.h.func-sort-c.html | 72 - .../crpropa/module/PropagationBP.h.func.html | 72 - .../crpropa/module/PropagationBP.h.gcov.html | 225 -- .../module/PropagationCK.h.func-sort-c.html | 72 - .../crpropa/module/PropagationCK.h.func.html | 72 - .../crpropa/module/PropagationCK.h.gcov.html | 178 -- .../module/Redshift.h.func-sort-c.html | 72 - .../crpropa/module/Redshift.h.func.html | 72 - .../crpropa/module/Redshift.h.gcov.html | 111 - .../SimplePropagation.h.func-sort-c.html | 72 - .../module/SimplePropagation.h.func.html | 72 - .../module/SimplePropagation.h.gcov.html | 115 - .../module/TextOutput.h.func-sort-c.html | 72 - .../crpropa/module/TextOutput.h.func.html | 72 - .../crpropa/module/TextOutput.h.gcov.html | 155 -- .../crpropa/module/Tools.h.func-sort-c.html | 72 - .../include/crpropa/module/Tools.h.func.html | 72 - .../include/crpropa/module/Tools.h.gcov.html | 150 -- .../include/crpropa/module/index-sort-f.html | 213 -- .../include/crpropa/module/index-sort-l.html | 213 -- .../include/crpropa/module/index.html | 213 -- doc/coverageReport/index-sort-f.html | 293 --- doc/coverageReport/index-sort-l.html | 293 --- doc/coverageReport/index.html | 293 --- .../src/ParticleIDMethods.cc.func-sort-c.html | 200 -- .../HepPID/src/ParticleIDMethods.cc.func.html | 200 -- .../HepPID/src/ParticleIDMethods.cc.gcov.html | 641 ----- .../src/ParticleName.cc.func-sort-c.html | 124 - .../libs/HepPID/src/ParticleName.cc.func.html | 124 - .../libs/HepPID/src/ParticleName.cc.gcov.html | 2075 ----------------- .../HepPID/src/Version.cc.func-sort-c.html | 84 - .../libs/HepPID/src/Version.cc.func.html | 84 - .../libs/HepPID/src/Version.cc.gcov.html | 106 - .../libs/HepPID/src/index-sort-f.html | 113 - .../libs/HepPID/src/index-sort-l.html | 113 - doc/coverageReport/libs/HepPID/src/index.html | 113 - .../error_handling.cc.func-sort-c.html | 100 - .../healpix_base/error_handling.cc.func.html | 100 - .../healpix_base/error_handling.cc.gcov.html | 136 -- .../geom_utils.cc.func-sort-c.html | 84 - .../libs/healpix_base/geom_utils.cc.func.html | 84 - .../libs/healpix_base/geom_utils.cc.gcov.html | 151 -- .../healpix_base.cc.func-sort-c.html | 436 ---- .../healpix_base/healpix_base.cc.func.html | 436 ---- .../healpix_base/healpix_base.cc.gcov.html | 1454 ------------ .../alloc_utils.h.func-sort-c.html | 96 - .../healpix_base/alloc_utils.h.func.html | 96 - .../healpix_base/alloc_utils.h.gcov.html | 154 -- .../healpix_base/arr.h.func-sort-c.html | 76 - .../include/healpix_base/arr.h.func.html | 76 - .../include/healpix_base/arr.h.gcov.html | 734 ------ .../error_handling.h.func-sort-c.html | 76 - .../healpix_base/error_handling.h.func.html | 76 - .../healpix_base/error_handling.h.gcov.html | 180 -- .../geom_utils.h.func-sort-c.html | 80 - .../healpix_base/geom_utils.h.func.html | 80 - .../healpix_base/geom_utils.h.gcov.html | 161 -- .../healpix_base.h.func-sort-c.html | 208 -- .../healpix_base/healpix_base.h.func.html | 208 -- .../healpix_base/healpix_base.h.gcov.html | 457 ---- .../include/healpix_base/index-sort-f.html | 173 -- .../include/healpix_base/index-sort-l.html | 173 -- .../include/healpix_base/index.html | 173 -- .../math_utils.h.func-sort-c.html | 88 - .../healpix_base/math_utils.h.func.html | 88 - .../healpix_base/math_utils.h.gcov.html | 259 -- .../healpix_base/pointing.h.func-sort-c.html | 72 - .../include/healpix_base/pointing.h.func.html | 72 - .../include/healpix_base/pointing.h.gcov.html | 161 -- .../healpix_base/rangeset.h.func-sort-c.html | 120 - .../include/healpix_base/rangeset.h.func.html | 120 - .../include/healpix_base/rangeset.h.gcov.html | 363 --- .../healpix_base/vec3.h.func-sort-c.html | 80 - .../include/healpix_base/vec3.h.func.html | 80 - .../include/healpix_base/vec3.h.gcov.html | 229 -- .../libs/healpix_base/index-sort-f.html | 123 - .../libs/healpix_base/index-sort-l.html | 123 - .../libs/healpix_base/index.html | 123 - .../healpix_base/pointing.cc.func-sort-c.html | 92 - .../libs/healpix_base/pointing.cc.func.html | 92 - .../libs/healpix_base/pointing.cc.gcov.html | 148 -- .../include/kiss/convert.h.func-sort-c.html | 76 - .../kiss/include/kiss/convert.h.func.html | 76 - .../kiss/include/kiss/convert.h.gcov.html | 150 -- .../libs/kiss/include/kiss/index-sort-f.html | 103 - .../libs/kiss/include/kiss/index-sort-l.html | 103 - .../libs/kiss/include/kiss/index.html | 103 - .../include/kiss/logger.h.func-sort-c.html | 336 --- .../libs/kiss/include/kiss/logger.h.func.html | 336 --- .../libs/kiss/include/kiss/logger.h.gcov.html | 131 -- .../libs/kiss/src/index-sort-f.html | 113 - .../libs/kiss/src/index-sort-l.html | 113 - doc/coverageReport/libs/kiss/src/index.html | 113 - .../libs/kiss/src/logger.cpp.func-sort-c.html | 104 - .../libs/kiss/src/logger.cpp.func.html | 104 - .../libs/kiss/src/logger.cpp.gcov.html | 161 -- .../libs/kiss/src/path.cpp.func-sort-c.html | 104 - .../libs/kiss/src/path.cpp.func.html | 104 - .../libs/kiss/src/path.cpp.gcov.html | 245 -- .../libs/kiss/src/string.cpp.func-sort-c.html | 100 - .../libs/kiss/src/string.cpp.func.html | 100 - .../libs/kiss/src/string.cpp.gcov.html | 165 -- doc/coverageReport/ruby.png | Bin 141 -> 0 bytes doc/coverageReport/snow.png | Bin 141 -> 0 bytes .../src/Candidate.cpp.func-sort-c.html | 212 -- .../src/Candidate.cpp.func.html | 212 -- .../src/Candidate.cpp.gcov.html | 331 --- .../src/Clock.cpp.func-sort-c.html | 104 - doc/coverageReport/src/Clock.cpp.func.html | 104 - doc/coverageReport/src/Clock.cpp.gcov.html | 231 -- .../src/Common.cpp.func-sort-c.html | 96 - doc/coverageReport/src/Common.cpp.func.html | 96 - doc/coverageReport/src/Common.cpp.gcov.html | 212 -- .../src/Cosmology.cpp.func-sort-c.html | 132 -- .../src/Cosmology.cpp.func.html | 132 -- .../src/Cosmology.cpp.gcov.html | 245 -- .../src/EmissionMap.cpp.func-sort-c.html | 204 -- .../src/EmissionMap.cpp.func.html | 204 -- .../src/EmissionMap.cpp.gcov.html | 370 --- .../src/Geometry.cpp.func-sort-c.html | 124 - doc/coverageReport/src/Geometry.cpp.func.html | 124 - doc/coverageReport/src/Geometry.cpp.gcov.html | 200 -- .../src/GridTools.cpp.func-sort-c.html | 148 -- .../src/GridTools.cpp.func.html | 148 -- .../src/GridTools.cpp.gcov.html | 491 ---- .../src/Module.cpp.func-sort-c.html | 120 - doc/coverageReport/src/Module.cpp.func.html | 120 - doc/coverageReport/src/Module.cpp.gcov.html | 156 -- .../src/ParticleID.cpp.func-sort-c.html | 92 - .../src/ParticleID.cpp.func.html | 92 - .../src/ParticleID.cpp.gcov.html | 130 -- .../src/ParticleMass.cpp.func-sort-c.html | 88 - .../src/ParticleMass.cpp.func.html | 88 - .../src/ParticleMass.cpp.gcov.html | 150 -- .../src/ParticleState.cpp.func-sort-c.html | 140 -- .../src/ParticleState.cpp.func.html | 140 -- .../src/ParticleState.cpp.gcov.html | 178 -- .../src/PhotonBackground.cpp.func-sort-c.html | 132 -- .../src/PhotonBackground.cpp.func.html | 132 -- .../src/PhotonBackground.cpp.gcov.html | 291 --- .../src/ProgressBar.cpp.func-sort-c.html | 92 - .../src/ProgressBar.cpp.func.html | 92 - .../src/ProgressBar.cpp.gcov.html | 153 -- .../src/Random.cpp.func-sort-c.html | 256 -- doc/coverageReport/src/Random.cpp.func.html | 256 -- doc/coverageReport/src/Random.cpp.gcov.html | 605 ----- .../src/Source.cpp.func-sort-c.html | 656 ------ doc/coverageReport/src/Source.cpp.func.html | 656 ------ doc/coverageReport/src/Source.cpp.gcov.html | 1218 ---------- .../src/Variant.cpp.func-sort-c.html | 264 --- doc/coverageReport/src/Variant.cpp.func.html | 264 --- doc/coverageReport/src/Variant.cpp.gcov.html | 1200 ---------- .../AdvectionField.cpp.func-sort-c.html | 408 ---- .../AdvectionField.cpp.func.html | 408 ---- .../AdvectionField.cpp.gcov.html | 610 ----- .../src/advectionField/index-sort-f.html | 93 - .../src/advectionField/index-sort-l.html | 93 - .../src/advectionField/index.html | 93 - .../src/base64.cpp.func-sort-c.html | 80 - doc/coverageReport/src/base64.cpp.func.html | 80 - doc/coverageReport/src/base64.cpp.gcov.html | 205 -- doc/coverageReport/src/index-sort-f.html | 253 -- doc/coverageReport/src/index-sort-l.html | 253 -- doc/coverageReport/src/index.html | 253 -- ...rchimedeanSpiralField.cpp.func-sort-c.html | 112 - .../ArchimedeanSpiralField.cpp.func.html | 112 - .../ArchimedeanSpiralField.cpp.gcov.html | 162 -- .../CMZField.cpp.func-sort-c.html | 144 -- .../src/magneticField/CMZField.cpp.func.html | 144 -- .../src/magneticField/CMZField.cpp.gcov.html | 382 --- .../JF12Field.cpp.func-sort-c.html | 188 -- .../src/magneticField/JF12Field.cpp.func.html | 188 -- .../src/magneticField/JF12Field.cpp.gcov.html | 452 ---- .../JF12FieldSolenoidal.cpp.func-sort-c.html | 128 - .../JF12FieldSolenoidal.cpp.func.html | 128 - .../JF12FieldSolenoidal.cpp.gcov.html | 378 --- .../MagneticField.cpp.func-sort-c.html | 136 -- .../magneticField/MagneticField.cpp.func.html | 136 -- .../magneticField/MagneticField.cpp.gcov.html | 188 -- .../MagneticFieldGrid.cpp.func-sort-c.html | 116 - .../MagneticFieldGrid.cpp.func.html | 116 - .../MagneticFieldGrid.cpp.gcov.html | 133 -- .../PT11Field.cpp.func-sort-c.html | 108 - .../src/magneticField/PT11Field.cpp.func.html | 108 - .../src/magneticField/PT11Field.cpp.gcov.html | 206 -- ...ngleModeMagneticField.cpp.func-sort-c.html | 80 - ...rizedSingleModeMagneticField.cpp.func.html | 80 - ...rizedSingleModeMagneticField.cpp.gcov.html | 142 -- .../TF17Field.cpp.func-sort-c.html | 188 -- .../src/magneticField/TF17Field.cpp.func.html | 188 -- .../src/magneticField/TF17Field.cpp.gcov.html | 383 --- .../src/magneticField/index-sort-f.html | 173 -- .../src/magneticField/index-sort-l.html | 173 -- .../src/magneticField/index.html | 173 -- .../GridTurbulence.cpp.func-sort-c.html | 124 - .../GridTurbulence.cpp.func.html | 124 - .../GridTurbulence.cpp.gcov.html | 289 --- ...HelicalGridTurbulence.cpp.func-sort-c.html | 80 - .../HelicalGridTurbulence.cpp.func.html | 80 - .../HelicalGridTurbulence.cpp.gcov.html | 206 -- .../PlaneWaveTurbulence.cpp.func-sort-c.html | 80 - .../PlaneWaveTurbulence.cpp.func.html | 80 - .../PlaneWaveTurbulence.cpp.gcov.html | 517 ---- .../SimpleGridTurbulence.cpp.func-sort-c.html | 80 - .../SimpleGridTurbulence.cpp.func.html | 80 - .../SimpleGridTurbulence.cpp.gcov.html | 193 -- .../turbulentField/index-sort-f.html | 123 - .../turbulentField/index-sort-l.html | 123 - .../magneticField/turbulentField/index.html | 123 - .../MagneticLens.cpp.func-sort-c.html | 124 - .../magneticLens/MagneticLens.cpp.func.html | 124 - .../magneticLens/MagneticLens.cpp.gcov.html | 353 --- .../ModelMatrix.cpp.func-sort-c.html | 100 - .../magneticLens/ModelMatrix.cpp.func.html | 100 - .../magneticLens/ModelMatrix.cpp.gcov.html | 237 -- ...ParticleMapsContainer.cpp.func-sort-c.html | 124 - .../ParticleMapsContainer.cpp.func.html | 124 - .../ParticleMapsContainer.cpp.gcov.html | 275 --- .../Pixelization.cpp.func-sort-c.html | 104 - .../magneticLens/Pixelization.cpp.func.html | 104 - .../magneticLens/Pixelization.cpp.gcov.html | 205 -- .../src/magneticLens/index-sort-f.html | 123 - .../src/magneticLens/index-sort-l.html | 123 - .../src/magneticLens/index.html | 123 - .../ConstantDensity.cpp.func-sort-c.html | 148 -- .../ConstantDensity.cpp.func.html | 148 -- .../ConstantDensity.cpp.gcov.html | 213 -- .../Cordes.cpp.func-sort-c.html | 100 - .../src/massDistribution/Cordes.cpp.func.html | 100 - .../src/massDistribution/Cordes.cpp.gcov.html | 122 - .../Ferriere.cpp.func-sort-c.html | 128 - .../massDistribution/Ferriere.cpp.func.html | 128 - .../massDistribution/Ferriere.cpp.gcov.html | 349 --- .../Massdistribution.cpp.func-sort-c.html | 160 -- .../Massdistribution.cpp.func.html | 160 -- .../Massdistribution.cpp.gcov.html | 222 -- .../Nakanishi.cpp.func-sort-c.html | 128 - .../massDistribution/Nakanishi.cpp.func.html | 128 - .../massDistribution/Nakanishi.cpp.gcov.html | 195 -- .../src/massDistribution/index-sort-f.html | 133 -- .../src/massDistribution/index-sort-l.html | 133 -- .../src/massDistribution/index.html | 133 -- .../module/Acceleration.cpp.func-sort-c.html | 128 - .../src/module/Acceleration.cpp.func.html | 128 - .../src/module/Acceleration.cpp.gcov.html | 260 --- .../AdiabaticCooling.cpp.func-sort-c.html | 92 - .../src/module/AdiabaticCooling.cpp.func.html | 92 - .../src/module/AdiabaticCooling.cpp.gcov.html | 130 -- .../src/module/Boundary.cpp.func-sort-c.html | 252 -- .../src/module/Boundary.cpp.func.html | 252 -- .../src/module/Boundary.cpp.gcov.html | 370 --- .../BreakCondition.cpp.func-sort-c.html | 224 -- .../src/module/BreakCondition.cpp.func.html | 224 -- .../src/module/BreakCondition.cpp.gcov.html | 343 --- .../CandidateSplitting.cpp.func-sort-c.html | 116 - .../module/CandidateSplitting.cpp.func.html | 116 - .../module/CandidateSplitting.cpp.gcov.html | 194 -- .../module/DiffusionSDE.cpp.func-sort-c.html | 172 -- .../src/module/DiffusionSDE.cpp.func.html | 172 -- .../src/module/DiffusionSDE.cpp.gcov.html | 480 ---- ...MDoublePairProduction.cpp.func-sort-c.html | 112 - .../EMDoublePairProduction.cpp.func.html | 112 - .../EMDoublePairProduction.cpp.gcov.html | 209 -- ...erseComptonScattering.cpp.func-sort-c.html | 124 - .../EMInverseComptonScattering.cpp.func.html | 124 - .../EMInverseComptonScattering.cpp.gcov.html | 325 --- .../EMPairProduction.cpp.func-sort-c.html | 124 - .../src/module/EMPairProduction.cpp.func.html | 124 - .../src/module/EMPairProduction.cpp.gcov.html | 340 --- ...TripletPairProduction.cpp.func-sort-c.html | 116 - .../EMTripletPairProduction.cpp.func.html | 116 - .../EMTripletPairProduction.cpp.gcov.html | 263 --- .../ElasticScattering.cpp.func-sort-c.html | 100 - .../module/ElasticScattering.cpp.func.html | 100 - .../module/ElasticScattering.cpp.gcov.html | 212 -- ...lectronPairProduction.cpp.func-sort-c.html | 112 - .../ElectronPairProduction.cpp.func.html | 112 - .../ElectronPairProduction.cpp.gcov.html | 233 -- .../module/HDF5Output.cpp.func-sort-c.html | 128 - .../src/module/HDF5Output.cpp.func.html | 128 - .../src/module/HDF5Output.cpp.gcov.html | 468 ---- .../MomentumDiffusion.cpp.func-sort-c.html | 112 - .../module/MomentumDiffusion.cpp.func.html | 112 - .../module/MomentumDiffusion.cpp.gcov.html | 147 -- .../module/NuclearDecay.cpp.func-sort-c.html | 124 - .../src/module/NuclearDecay.cpp.func.html | 124 - .../src/module/NuclearDecay.cpp.gcov.html | 395 ---- .../src/module/Observer.cpp.func-sort-c.html | 248 -- .../src/module/Observer.cpp.func.html | 248 -- .../src/module/Observer.cpp.gcov.html | 427 ---- .../src/module/Output.cpp.func-sort-c.html | 136 -- .../src/module/Output.cpp.func.html | 136 -- .../src/module/Output.cpp.gcov.html | 210 -- .../module/OutputShell.cpp.func-sort-c.html | 96 - .../src/module/OutputShell.cpp.func.html | 96 - .../src/module/OutputShell.cpp.gcov.html | 134 -- .../ParticleCollector.cpp.func-sort-c.html | 168 -- .../module/ParticleCollector.cpp.func.html | 168 -- .../module/ParticleCollector.cpp.gcov.html | 194 -- .../PhotoDisintegration.cpp.func-sort-c.html | 120 - .../module/PhotoDisintegration.cpp.func.html | 120 - .../module/PhotoDisintegration.cpp.gcov.html | 406 ---- .../PhotoPionProduction.cpp.func-sort-c.html | 232 -- .../module/PhotoPionProduction.cpp.func.html | 232 -- .../module/PhotoPionProduction.cpp.gcov.html | 758 ------ .../PhotonOutput1D.cpp.func-sort-c.html | 108 - .../src/module/PhotonOutput1D.cpp.func.html | 108 - .../src/module/PhotonOutput1D.cpp.gcov.html | 180 -- .../module/PropagationBP.cpp.func-sort-c.html | 136 -- .../src/module/PropagationBP.cpp.func.html | 136 -- .../src/module/PropagationBP.cpp.gcov.html | 285 --- .../module/PropagationCK.cpp.func-sort-c.html | 128 - .../src/module/PropagationCK.cpp.func.html | 128 - .../src/module/PropagationCK.cpp.gcov.html | 278 --- .../src/module/Redshift.cpp.func-sort-c.html | 88 - .../src/module/Redshift.cpp.func.html | 88 - .../src/module/Redshift.cpp.gcov.html | 138 -- .../RestrictToRegion.cpp.func-sort-c.html | 84 - .../src/module/RestrictToRegion.cpp.func.html | 84 - .../src/module/RestrictToRegion.cpp.gcov.html | 101 - .../SimplePropagation.cpp.func-sort-c.html | 100 - .../module/SimplePropagation.cpp.func.html | 100 - .../module/SimplePropagation.cpp.gcov.html | 128 - .../SynchrotronRadiation.cpp.func-sort-c.html | 156 -- .../module/SynchrotronRadiation.cpp.func.html | 156 -- .../module/SynchrotronRadiation.cpp.gcov.html | 306 --- .../module/TextOutput.cpp.func-sort-c.html | 128 - .../src/module/TextOutput.cpp.func.html | 128 - .../src/module/TextOutput.cpp.gcov.html | 457 ---- .../src/module/Tools.cpp.func-sort-c.html | 136 -- .../src/module/Tools.cpp.func.html | 136 -- .../src/module/Tools.cpp.gcov.html | 199 -- .../src/module/index-sort-f.html | 383 --- .../src/module/index-sort-l.html | 383 --- doc/coverageReport/src/module/index.html | 383 --- doc/coverageReport/test/index-sort-f.html | 243 -- doc/coverageReport/test/index-sort-l.html | 243 -- doc/coverageReport/test/index.html | 243 -- .../testAdiabaticCooling.cpp.func-sort-c.html | 80 - .../test/testAdiabaticCooling.cpp.func.html | 80 - .../test/testAdiabaticCooling.cpp.gcov.html | 131 -- .../testAdvectionField.cpp.func-sort-c.html | 92 - .../test/testAdvectionField.cpp.func.html | 92 - .../test/testAdvectionField.cpp.gcov.html | 245 -- .../testBreakCondition.cpp.func-sort-c.html | 196 -- .../test/testBreakCondition.cpp.func.html | 196 -- .../test/testBreakCondition.cpp.gcov.html | 621 ----- ...estCandidateSplitting.cpp.func-sort-c.html | 80 - .../test/testCandidateSplitting.cpp.func.html | 80 - .../test/testCandidateSplitting.cpp.gcov.html | 166 -- .../test/testCore.cpp.func-sort-c.html | 308 --- .../test/testCore.cpp.func.html | 308 --- .../test/testCore.cpp.gcov.html | 1144 --------- .../test/testDensity.cpp.func-sort-c.html | 100 - .../test/testDensity.cpp.func.html | 100 - .../test/testDensity.cpp.gcov.html | 372 --- .../testFunctionalGroups.cpp.func-sort-c.html | 80 - .../test/testFunctionalGroups.cpp.func.html | 80 - .../test/testFunctionalGroups.cpp.gcov.html | 126 - .../test/testInteraction.cpp.func-sort-c.html | 284 --- .../test/testInteraction.cpp.func.html | 284 --- .../test/testInteraction.cpp.gcov.html | 1229 ---------- .../testMagneticField.cpp.func-sort-c.html | 136 -- .../test/testMagneticField.cpp.func.html | 136 -- .../test/testMagneticField.cpp.gcov.html | 292 --- .../testMagneticLens.cpp.func-sort-c.html | 100 - .../test/testMagneticLens.cpp.func.html | 100 - .../test/testMagneticLens.cpp.gcov.html | 248 -- .../test/testModuleList.cpp.func-sort-c.html | 100 - .../test/testModuleList.cpp.func.html | 100 - .../test/testModuleList.cpp.gcov.html | 155 -- .../test/testOutput.cpp.func-sort-c.html | 144 -- .../test/testOutput.cpp.func.html | 144 -- .../test/testOutput.cpp.gcov.html | 355 --- .../test/testPropagation.cpp.func-sort-c.html | 148 -- .../test/testPropagation.cpp.func.html | 148 -- .../test/testPropagation.cpp.gcov.html | 632 ----- .../test/testSource.cpp.func-sort-c.html | 168 -- .../test/testSource.cpp.func.html | 168 -- .../test/testSource.cpp.gcov.html | 516 ---- .../testTurbulentField.cpp.func-sort-c.html | 104 - .../test/testTurbulentField.cpp.func.html | 104 - .../test/testTurbulentField.cpp.gcov.html | 218 -- .../test/testVector3.cpp.func-sort-c.html | 124 - .../test/testVector3.cpp.func.html | 124 - .../test/testVector3.cpp.gcov.html | 238 -- doc/coverageReport/updown.png | Bin 117 -> 0 bytes doc/index.rst | 4 +- doc/pages/Code-Coverage.md | 8 +- 538 files changed, 4 insertions(+), 101309 deletions(-) delete mode 100644 doc/coverageReport/amber.png delete mode 100644 doc/coverageReport/emerald.png delete mode 100644 doc/coverageReport/gcov.css delete mode 100644 doc/coverageReport/glass.png delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html delete mode 100644 doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/AssocVector.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/AssocVector.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Candidate.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Candidate.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Common.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Common.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Common.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/EmissionMap.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Geometry.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Geometry.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Grid.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Grid.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Logging.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Logging.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Module.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Module.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Module.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/ParticleState.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/ParticleState.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/PhotonBackground.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Random.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Random.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Random.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Referenced.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Referenced.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Source.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Source.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Source.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Variant.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Variant.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/Vector3.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/Vector3.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/advectionField/index-sort-f.html delete mode 100644 doc/coverageReport/include/crpropa/advectionField/index-sort-l.html delete mode 100644 doc/coverageReport/include/crpropa/advectionField/index.html delete mode 100644 doc/coverageReport/include/crpropa/index-sort-f.html delete mode 100644 doc/coverageReport/include/crpropa/index-sort-l.html delete mode 100644 doc/coverageReport/include/crpropa/index.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/index-sort-f.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/index-sort-l.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/index.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html delete mode 100644 doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html delete mode 100644 doc/coverageReport/include/crpropa/magneticLens/index.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html delete mode 100644 doc/coverageReport/include/crpropa/massDistribution/index.html delete mode 100644 doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/Boundary.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/Observer.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/Observer.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/OutputShell.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/Redshift.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/TextOutput.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html delete mode 100644 doc/coverageReport/include/crpropa/module/Tools.h.func.html delete mode 100644 doc/coverageReport/include/crpropa/module/Tools.h.gcov.html delete mode 100644 doc/coverageReport/include/crpropa/module/index-sort-f.html delete mode 100644 doc/coverageReport/include/crpropa/module/index-sort-l.html delete mode 100644 doc/coverageReport/include/crpropa/module/index.html delete mode 100644 doc/coverageReport/index-sort-f.html delete mode 100644 doc/coverageReport/index-sort-l.html delete mode 100644 doc/coverageReport/index.html delete mode 100644 doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html delete mode 100644 doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html delete mode 100644 doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html delete mode 100644 doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html delete mode 100644 doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html delete mode 100644 doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html delete mode 100644 doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html delete mode 100644 doc/coverageReport/libs/HepPID/src/Version.cc.func.html delete mode 100644 doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html delete mode 100644 doc/coverageReport/libs/HepPID/src/index-sort-f.html delete mode 100644 doc/coverageReport/libs/HepPID/src/index-sort-l.html delete mode 100644 doc/coverageReport/libs/HepPID/src/index.html delete mode 100644 doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/error_handling.cc.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/index.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html delete mode 100644 doc/coverageReport/libs/healpix_base/index-sort-f.html delete mode 100644 doc/coverageReport/libs/healpix_base/index-sort-l.html delete mode 100644 doc/coverageReport/libs/healpix_base/index.html delete mode 100644 doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html delete mode 100644 doc/coverageReport/libs/healpix_base/pointing.cc.func.html delete mode 100644 doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/index.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html delete mode 100644 doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html delete mode 100644 doc/coverageReport/libs/kiss/src/index-sort-f.html delete mode 100644 doc/coverageReport/libs/kiss/src/index-sort-l.html delete mode 100644 doc/coverageReport/libs/kiss/src/index.html delete mode 100644 doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/libs/kiss/src/logger.cpp.func.html delete mode 100644 doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html delete mode 100644 doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/libs/kiss/src/path.cpp.func.html delete mode 100644 doc/coverageReport/libs/kiss/src/path.cpp.gcov.html delete mode 100644 doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/libs/kiss/src/string.cpp.func.html delete mode 100644 doc/coverageReport/libs/kiss/src/string.cpp.gcov.html delete mode 100644 doc/coverageReport/ruby.png delete mode 100644 doc/coverageReport/snow.png delete mode 100644 doc/coverageReport/src/Candidate.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Candidate.cpp.func.html delete mode 100644 doc/coverageReport/src/Candidate.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Clock.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Clock.cpp.func.html delete mode 100644 doc/coverageReport/src/Clock.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Common.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Common.cpp.func.html delete mode 100644 doc/coverageReport/src/Common.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Cosmology.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Cosmology.cpp.func.html delete mode 100644 doc/coverageReport/src/Cosmology.cpp.gcov.html delete mode 100644 doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/EmissionMap.cpp.func.html delete mode 100644 doc/coverageReport/src/EmissionMap.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Geometry.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Geometry.cpp.func.html delete mode 100644 doc/coverageReport/src/Geometry.cpp.gcov.html delete mode 100644 doc/coverageReport/src/GridTools.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/GridTools.cpp.func.html delete mode 100644 doc/coverageReport/src/GridTools.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Module.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Module.cpp.func.html delete mode 100644 doc/coverageReport/src/Module.cpp.gcov.html delete mode 100644 doc/coverageReport/src/ParticleID.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/ParticleID.cpp.func.html delete mode 100644 doc/coverageReport/src/ParticleID.cpp.gcov.html delete mode 100644 doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/ParticleMass.cpp.func.html delete mode 100644 doc/coverageReport/src/ParticleMass.cpp.gcov.html delete mode 100644 doc/coverageReport/src/ParticleState.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/ParticleState.cpp.func.html delete mode 100644 doc/coverageReport/src/ParticleState.cpp.gcov.html delete mode 100644 doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/PhotonBackground.cpp.func.html delete mode 100644 doc/coverageReport/src/PhotonBackground.cpp.gcov.html delete mode 100644 doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/ProgressBar.cpp.func.html delete mode 100644 doc/coverageReport/src/ProgressBar.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Random.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Random.cpp.func.html delete mode 100644 doc/coverageReport/src/Random.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Source.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Source.cpp.func.html delete mode 100644 doc/coverageReport/src/Source.cpp.gcov.html delete mode 100644 doc/coverageReport/src/Variant.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/Variant.cpp.func.html delete mode 100644 doc/coverageReport/src/Variant.cpp.gcov.html delete mode 100644 doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html delete mode 100644 doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html delete mode 100644 doc/coverageReport/src/advectionField/index-sort-f.html delete mode 100644 doc/coverageReport/src/advectionField/index-sort-l.html delete mode 100644 doc/coverageReport/src/advectionField/index.html delete mode 100644 doc/coverageReport/src/base64.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/base64.cpp.func.html delete mode 100644 doc/coverageReport/src/base64.cpp.gcov.html delete mode 100644 doc/coverageReport/src/index-sort-f.html delete mode 100644 doc/coverageReport/src/index-sort-l.html delete mode 100644 doc/coverageReport/src/index.html delete mode 100644 doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/CMZField.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/JF12Field.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/MagneticField.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/PT11Field.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/TF17Field.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/index-sort-f.html delete mode 100644 doc/coverageReport/src/magneticField/index-sort-l.html delete mode 100644 doc/coverageReport/src/magneticField/index.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html delete mode 100644 doc/coverageReport/src/magneticField/turbulentField/index.html delete mode 100644 doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html delete mode 100644 doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html delete mode 100644 doc/coverageReport/src/magneticLens/index-sort-f.html delete mode 100644 doc/coverageReport/src/magneticLens/index-sort-l.html delete mode 100644 doc/coverageReport/src/magneticLens/index.html delete mode 100644 doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html delete mode 100644 doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html delete mode 100644 doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/massDistribution/Cordes.cpp.func.html delete mode 100644 doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html delete mode 100644 doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html delete mode 100644 doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html delete mode 100644 doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html delete mode 100644 doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html delete mode 100644 doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html delete mode 100644 doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html delete mode 100644 doc/coverageReport/src/massDistribution/index-sort-f.html delete mode 100644 doc/coverageReport/src/massDistribution/index-sort-l.html delete mode 100644 doc/coverageReport/src/massDistribution/index.html delete mode 100644 doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/Acceleration.cpp.func.html delete mode 100644 doc/coverageReport/src/module/Acceleration.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html delete mode 100644 doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/Boundary.cpp.func.html delete mode 100644 doc/coverageReport/src/module/Boundary.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/BreakCondition.cpp.func.html delete mode 100644 doc/coverageReport/src/module/BreakCondition.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/CandidateSplitting.cpp.func.html delete mode 100644 doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/DiffusionSDE.cpp.func.html delete mode 100644 doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html delete mode 100644 doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html delete mode 100644 doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/EMPairProduction.cpp.func.html delete mode 100644 doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html delete mode 100644 doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/ElasticScattering.cpp.func.html delete mode 100644 doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html delete mode 100644 doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/HDF5Output.cpp.func.html delete mode 100644 doc/coverageReport/src/module/HDF5Output.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html delete mode 100644 doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/NuclearDecay.cpp.func.html delete mode 100644 doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/Observer.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/Observer.cpp.func.html delete mode 100644 doc/coverageReport/src/module/Observer.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/Output.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/Output.cpp.func.html delete mode 100644 doc/coverageReport/src/module/Output.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/OutputShell.cpp.func.html delete mode 100644 doc/coverageReport/src/module/OutputShell.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/ParticleCollector.cpp.func.html delete mode 100644 doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html delete mode 100644 doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html delete mode 100644 doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html delete mode 100644 doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/PropagationBP.cpp.func.html delete mode 100644 doc/coverageReport/src/module/PropagationBP.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/PropagationCK.cpp.func.html delete mode 100644 doc/coverageReport/src/module/PropagationCK.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/Redshift.cpp.func.html delete mode 100644 doc/coverageReport/src/module/Redshift.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/RestrictToRegion.cpp.func.html delete mode 100644 doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/SimplePropagation.cpp.func.html delete mode 100644 doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html delete mode 100644 doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/TextOutput.cpp.func.html delete mode 100644 doc/coverageReport/src/module/TextOutput.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/Tools.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/src/module/Tools.cpp.func.html delete mode 100644 doc/coverageReport/src/module/Tools.cpp.gcov.html delete mode 100644 doc/coverageReport/src/module/index-sort-f.html delete mode 100644 doc/coverageReport/src/module/index-sort-l.html delete mode 100644 doc/coverageReport/src/module/index.html delete mode 100644 doc/coverageReport/test/index-sort-f.html delete mode 100644 doc/coverageReport/test/index-sort-l.html delete mode 100644 doc/coverageReport/test/index.html delete mode 100644 doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testAdiabaticCooling.cpp.func.html delete mode 100644 doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testAdvectionField.cpp.func.html delete mode 100644 doc/coverageReport/test/testAdvectionField.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testBreakCondition.cpp.func.html delete mode 100644 doc/coverageReport/test/testBreakCondition.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testCandidateSplitting.cpp.func.html delete mode 100644 doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testCore.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testCore.cpp.func.html delete mode 100644 doc/coverageReport/test/testCore.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testDensity.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testDensity.cpp.func.html delete mode 100644 doc/coverageReport/test/testDensity.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testFunctionalGroups.cpp.func.html delete mode 100644 doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testInteraction.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testInteraction.cpp.func.html delete mode 100644 doc/coverageReport/test/testInteraction.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testMagneticField.cpp.func.html delete mode 100644 doc/coverageReport/test/testMagneticField.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testMagneticLens.cpp.func.html delete mode 100644 doc/coverageReport/test/testMagneticLens.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testModuleList.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testModuleList.cpp.func.html delete mode 100644 doc/coverageReport/test/testModuleList.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testOutput.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testOutput.cpp.func.html delete mode 100644 doc/coverageReport/test/testOutput.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testPropagation.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testPropagation.cpp.func.html delete mode 100644 doc/coverageReport/test/testPropagation.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testSource.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testSource.cpp.func.html delete mode 100644 doc/coverageReport/test/testSource.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testTurbulentField.cpp.func.html delete mode 100644 doc/coverageReport/test/testTurbulentField.cpp.gcov.html delete mode 100644 doc/coverageReport/test/testVector3.cpp.func-sort-c.html delete mode 100644 doc/coverageReport/test/testVector3.cpp.func.html delete mode 100644 doc/coverageReport/test/testVector3.cpp.gcov.html delete mode 100644 doc/coverageReport/updown.png diff --git a/.github/workflows/create_documentation.yml b/.github/workflows/create_documentation.yml index b1a0bee70..190591189 100644 --- a/.github/workflows/create_documentation.yml +++ b/.github/workflows/create_documentation.yml @@ -55,6 +55,7 @@ jobs: run: | cd build make doc + cp -r coverageReport doc/pages/coverageReport tar -zcvf documentation.tar.gz doc - name: archive documentation uses: actions/upload-artifact@v4 diff --git a/doc/coverageReport/amber.png b/doc/coverageReport/amber.png deleted file mode 100644 index 2cab170d8359081983a4e343848dfe06bc490f12..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 141 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)ga>?NMQuI!iC1^G2tW}LqE04T&+ z;1OBOz`!j8!i<;h*8KqrvZOouIx;Y9?C1WI$O`1M1^9%x{(levWG?NMQuI!iC1^Jb!lvI6;R0X`wF(yt=9xVZRt1vCRixIA4P dLn>}1Cji+@42)0J?}79&c)I$ztaD0e0sy@GAL0N2 diff --git a/doc/coverageReport/gcov.css b/doc/coverageReport/gcov.css deleted file mode 100644 index bfd0a83e1..000000000 --- a/doc/coverageReport/gcov.css +++ /dev/null @@ -1,519 +0,0 @@ -/* All views: initial background and text color */ -body -{ - color: #000000; - background-color: #FFFFFF; -} - -/* All views: standard link format*/ -a:link -{ - color: #284FA8; - text-decoration: underline; -} - -/* All views: standard link - visited format */ -a:visited -{ - color: #00CB40; - text-decoration: underline; -} - -/* All views: standard link - activated format */ -a:active -{ - color: #FF0040; - text-decoration: underline; -} - -/* All views: main title format */ -td.title -{ - text-align: center; - padding-bottom: 10px; - font-family: sans-serif; - font-size: 20pt; - font-style: italic; - font-weight: bold; -} - -/* All views: header item format */ -td.headerItem -{ - text-align: right; - padding-right: 6px; - font-family: sans-serif; - font-weight: bold; - vertical-align: top; - white-space: nowrap; -} - -/* All views: header item value format */ -td.headerValue -{ - text-align: left; - color: #284FA8; - font-family: sans-serif; - font-weight: bold; - white-space: nowrap; -} - -/* All views: header item coverage table heading */ -td.headerCovTableHead -{ - text-align: center; - padding-right: 6px; - padding-left: 6px; - padding-bottom: 0px; - font-family: sans-serif; - font-size: 80%; - white-space: nowrap; -} - -/* All views: header item coverage table entry */ -td.headerCovTableEntry -{ - text-align: right; - color: #284FA8; - font-family: sans-serif; - font-weight: bold; - white-space: nowrap; - padding-left: 12px; - padding-right: 4px; - background-color: #DAE7FE; -} - -/* All views: header item coverage table entry for high coverage rate */ -td.headerCovTableEntryHi -{ - text-align: right; - color: #000000; - font-family: sans-serif; - font-weight: bold; - white-space: nowrap; - padding-left: 12px; - padding-right: 4px; - background-color: #A7FC9D; -} - -/* All views: header item coverage table entry for medium coverage rate */ -td.headerCovTableEntryMed -{ - text-align: right; - color: #000000; - font-family: sans-serif; - font-weight: bold; - white-space: nowrap; - padding-left: 12px; - padding-right: 4px; - background-color: #FFEA20; -} - -/* All views: header item coverage table entry for ow coverage rate */ -td.headerCovTableEntryLo -{ - text-align: right; - color: #000000; - font-family: sans-serif; - font-weight: bold; - white-space: nowrap; - padding-left: 12px; - padding-right: 4px; - background-color: #FF0000; -} - -/* All views: header legend value for legend entry */ -td.headerValueLeg -{ - text-align: left; - color: #000000; - font-family: sans-serif; - font-size: 80%; - white-space: nowrap; - padding-top: 4px; -} - -/* All views: color of horizontal ruler */ -td.ruler -{ - background-color: #6688D4; -} - -/* All views: version string format */ -td.versionInfo -{ - text-align: center; - padding-top: 2px; - font-family: sans-serif; - font-style: italic; -} - -/* Directory view/File view (all)/Test case descriptions: - table headline format */ -td.tableHead -{ - text-align: center; - color: #FFFFFF; - background-color: #6688D4; - font-family: sans-serif; - font-size: 120%; - font-weight: bold; - white-space: nowrap; - padding-left: 4px; - padding-right: 4px; -} - -span.tableHeadSort -{ - padding-right: 4px; -} - -/* Directory view/File view (all): filename entry format */ -td.coverFile -{ - text-align: left; - padding-left: 10px; - padding-right: 20px; - color: #284FA8; - background-color: #DAE7FE; - font-family: monospace; -} - -/* Directory view/File view (all): bar-graph entry format*/ -td.coverBar -{ - padding-left: 10px; - padding-right: 10px; - background-color: #DAE7FE; -} - -/* Directory view/File view (all): bar-graph outline color */ -td.coverBarOutline -{ - background-color: #000000; -} - -/* Directory view/File view (all): percentage entry for files with - high coverage rate */ -td.coverPerHi -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #A7FC9D; - font-weight: bold; - font-family: sans-serif; -} - -/* Directory view/File view (all): line count entry for files with - high coverage rate */ -td.coverNumHi -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #A7FC9D; - white-space: nowrap; - font-family: sans-serif; -} - -/* Directory view/File view (all): percentage entry for files with - medium coverage rate */ -td.coverPerMed -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #FFEA20; - font-weight: bold; - font-family: sans-serif; -} - -/* Directory view/File view (all): line count entry for files with - medium coverage rate */ -td.coverNumMed -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #FFEA20; - white-space: nowrap; - font-family: sans-serif; -} - -/* Directory view/File view (all): percentage entry for files with - low coverage rate */ -td.coverPerLo -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #FF0000; - font-weight: bold; - font-family: sans-serif; -} - -/* Directory view/File view (all): line count entry for files with - low coverage rate */ -td.coverNumLo -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #FF0000; - white-space: nowrap; - font-family: sans-serif; -} - -/* File view (all): "show/hide details" link format */ -a.detail:link -{ - color: #B8D0FF; - font-size:80%; -} - -/* File view (all): "show/hide details" link - visited format */ -a.detail:visited -{ - color: #B8D0FF; - font-size:80%; -} - -/* File view (all): "show/hide details" link - activated format */ -a.detail:active -{ - color: #FFFFFF; - font-size:80%; -} - -/* File view (detail): test name entry */ -td.testName -{ - text-align: right; - padding-right: 10px; - background-color: #DAE7FE; - font-family: sans-serif; -} - -/* File view (detail): test percentage entry */ -td.testPer -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #DAE7FE; - font-family: sans-serif; -} - -/* File view (detail): test lines count entry */ -td.testNum -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #DAE7FE; - font-family: sans-serif; -} - -/* Test case descriptions: test name format*/ -dt -{ - font-family: sans-serif; - font-weight: bold; -} - -/* Test case descriptions: description table body */ -td.testDescription -{ - padding-top: 10px; - padding-left: 30px; - padding-bottom: 10px; - padding-right: 30px; - background-color: #DAE7FE; -} - -/* Source code view: function entry */ -td.coverFn -{ - text-align: left; - padding-left: 10px; - padding-right: 20px; - color: #284FA8; - background-color: #DAE7FE; - font-family: monospace; -} - -/* Source code view: function entry zero count*/ -td.coverFnLo -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #FF0000; - font-weight: bold; - font-family: sans-serif; -} - -/* Source code view: function entry nonzero count*/ -td.coverFnHi -{ - text-align: right; - padding-left: 10px; - padding-right: 10px; - background-color: #DAE7FE; - font-weight: bold; - font-family: sans-serif; -} - -/* Source code view: source code format */ -pre.source -{ - font-family: monospace; - white-space: pre; - margin-top: 2px; -} - -/* Source code view: line number format */ -span.lineNum -{ - background-color: #EFE383; -} - -/* Source code view: format for lines which were executed */ -td.lineCov, -span.lineCov -{ - background-color: #CAD7FE; -} - -/* Source code view: format for Cov legend */ -span.coverLegendCov -{ - padding-left: 10px; - padding-right: 10px; - padding-bottom: 2px; - background-color: #CAD7FE; -} - -/* Source code view: format for lines which were not executed */ -td.lineNoCov, -span.lineNoCov -{ - background-color: #FF6230; -} - -/* Source code view: format for NoCov legend */ -span.coverLegendNoCov -{ - padding-left: 10px; - padding-right: 10px; - padding-bottom: 2px; - background-color: #FF6230; -} - -/* Source code view (function table): standard link - visited format */ -td.lineNoCov > a:visited, -td.lineCov > a:visited -{ - color: black; - text-decoration: underline; -} - -/* Source code view: format for lines which were executed only in a - previous version */ -span.lineDiffCov -{ - background-color: #B5F7AF; -} - -/* Source code view: format for branches which were executed - * and taken */ -span.branchCov -{ - background-color: #CAD7FE; -} - -/* Source code view: format for branches which were executed - * but not taken */ -span.branchNoCov -{ - background-color: #FF6230; -} - -/* Source code view: format for branches which were not executed */ -span.branchNoExec -{ - background-color: #FF6230; -} - -/* Source code view: format for the source code heading line */ -pre.sourceHeading -{ - white-space: pre; - font-family: monospace; - font-weight: bold; - margin: 0px; -} - -/* All views: header legend value for low rate */ -td.headerValueLegL -{ - font-family: sans-serif; - text-align: center; - white-space: nowrap; - padding-left: 4px; - padding-right: 2px; - background-color: #FF0000; - font-size: 80%; -} - -/* All views: header legend value for med rate */ -td.headerValueLegM -{ - font-family: sans-serif; - text-align: center; - white-space: nowrap; - padding-left: 2px; - padding-right: 2px; - background-color: #FFEA20; - font-size: 80%; -} - -/* All views: header legend value for hi rate */ -td.headerValueLegH -{ - font-family: sans-serif; - text-align: center; - white-space: nowrap; - padding-left: 2px; - padding-right: 4px; - background-color: #A7FC9D; - font-size: 80%; -} - -/* All views except source code view: legend format for low coverage */ -span.coverLegendCovLo -{ - padding-left: 10px; - padding-right: 10px; - padding-top: 2px; - background-color: #FF0000; -} - -/* All views except source code view: legend format for med coverage */ -span.coverLegendCovMed -{ - padding-left: 10px; - padding-right: 10px; - padding-top: 2px; - background-color: #FFEA20; -} - -/* All views except source code view: legend format for hi coverage */ -span.coverLegendCovHi -{ - padding-left: 10px; - padding-right: 10px; - padding-top: 2px; - background-color: #A7FC9D; -} diff --git a/doc/coverageReport/glass.png b/doc/coverageReport/glass.png deleted file mode 100644 index e1abc00680a3093c49fdb775ae6bdb6764c95af2..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 167 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)gaEa{HEjtmSN`?>!lvI6;R0X`wF z|Ns97GD8ntt^-nxB|(0{3=Yq3q=7g|-tI089jvk*Kn`btM`SSr1Gf+eGhVt|_XjA* zUgGKN%6^Gmn4d%Ph(nkFP>9RZ#WAE}PI3Z}&BVayv3^M*kj3EX>gTe~DWM4f=_Dpv diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html deleted file mode 100644 index 0de34274a..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __multiarray_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:132748.1 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_import_array4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html deleted file mode 100644 index 6d2267253..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __multiarray_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:132748.1 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_import_array4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html deleted file mode 100644 index 5aee35675..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h.gcov.html +++ /dev/null @@ -1,1642 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__multiarray_api.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __multiarray_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:132748.1 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : 
-       2             : #if defined(_MULTIARRAYMODULE) || defined(WITH_CPYCHECKER_STEALS_REFERENCE_TO_ARG_ATTRIBUTE)
-       3             : 
-       4             : typedef struct {
-       5             :         PyObject_HEAD
-       6             :         npy_bool obval;
-       7             : } PyBoolScalarObject;
-       8             : 
-       9             : extern NPY_NO_EXPORT PyTypeObject PyArrayMapIter_Type;
-      10             : extern NPY_NO_EXPORT PyTypeObject PyArrayNeighborhoodIter_Type;
-      11             : extern NPY_NO_EXPORT PyBoolScalarObject _PyArrayScalar_BoolValues[2];
-      12             : 
-      13             : NPY_NO_EXPORT  unsigned int PyArray_GetNDArrayCVersion \
-      14             :        (void);
-      15             : extern NPY_NO_EXPORT PyTypeObject PyBigArray_Type;
-      16             : 
-      17             : extern NPY_NO_EXPORT PyTypeObject PyArray_Type;
-      18             : 
-      19             : extern NPY_NO_EXPORT PyArray_DTypeMeta PyArrayDescr_TypeFull;
-      20             : #define PyArrayDescr_Type (*(PyTypeObject *)(&PyArrayDescr_TypeFull))
-      21             : 
-      22             : extern NPY_NO_EXPORT PyTypeObject PyArrayFlags_Type;
-      23             : 
-      24             : extern NPY_NO_EXPORT PyTypeObject PyArrayIter_Type;
-      25             : 
-      26             : extern NPY_NO_EXPORT PyTypeObject PyArrayMultiIter_Type;
-      27             : 
-      28             : extern NPY_NO_EXPORT int NPY_NUMUSERTYPES;
-      29             : 
-      30             : extern NPY_NO_EXPORT PyTypeObject PyBoolArrType_Type;
-      31             : 
-      32             : extern NPY_NO_EXPORT PyBoolScalarObject _PyArrayScalar_BoolValues[2];
-      33             : 
-      34             : extern NPY_NO_EXPORT PyTypeObject PyGenericArrType_Type;
-      35             : 
-      36             : extern NPY_NO_EXPORT PyTypeObject PyNumberArrType_Type;
-      37             : 
-      38             : extern NPY_NO_EXPORT PyTypeObject PyIntegerArrType_Type;
-      39             : 
-      40             : extern NPY_NO_EXPORT PyTypeObject PySignedIntegerArrType_Type;
-      41             : 
-      42             : extern NPY_NO_EXPORT PyTypeObject PyUnsignedIntegerArrType_Type;
-      43             : 
-      44             : extern NPY_NO_EXPORT PyTypeObject PyInexactArrType_Type;
-      45             : 
-      46             : extern NPY_NO_EXPORT PyTypeObject PyFloatingArrType_Type;
-      47             : 
-      48             : extern NPY_NO_EXPORT PyTypeObject PyComplexFloatingArrType_Type;
-      49             : 
-      50             : extern NPY_NO_EXPORT PyTypeObject PyFlexibleArrType_Type;
-      51             : 
-      52             : extern NPY_NO_EXPORT PyTypeObject PyCharacterArrType_Type;
-      53             : 
-      54             : extern NPY_NO_EXPORT PyTypeObject PyByteArrType_Type;
-      55             : 
-      56             : extern NPY_NO_EXPORT PyTypeObject PyShortArrType_Type;
-      57             : 
-      58             : extern NPY_NO_EXPORT PyTypeObject PyIntArrType_Type;
-      59             : 
-      60             : extern NPY_NO_EXPORT PyTypeObject PyLongArrType_Type;
-      61             : 
-      62             : extern NPY_NO_EXPORT PyTypeObject PyLongLongArrType_Type;
-      63             : 
-      64             : extern NPY_NO_EXPORT PyTypeObject PyUByteArrType_Type;
-      65             : 
-      66             : extern NPY_NO_EXPORT PyTypeObject PyUShortArrType_Type;
-      67             : 
-      68             : extern NPY_NO_EXPORT PyTypeObject PyUIntArrType_Type;
-      69             : 
-      70             : extern NPY_NO_EXPORT PyTypeObject PyULongArrType_Type;
-      71             : 
-      72             : extern NPY_NO_EXPORT PyTypeObject PyULongLongArrType_Type;
-      73             : 
-      74             : extern NPY_NO_EXPORT PyTypeObject PyFloatArrType_Type;
-      75             : 
-      76             : extern NPY_NO_EXPORT PyTypeObject PyDoubleArrType_Type;
-      77             : 
-      78             : extern NPY_NO_EXPORT PyTypeObject PyLongDoubleArrType_Type;
-      79             : 
-      80             : extern NPY_NO_EXPORT PyTypeObject PyCFloatArrType_Type;
-      81             : 
-      82             : extern NPY_NO_EXPORT PyTypeObject PyCDoubleArrType_Type;
-      83             : 
-      84             : extern NPY_NO_EXPORT PyTypeObject PyCLongDoubleArrType_Type;
-      85             : 
-      86             : extern NPY_NO_EXPORT PyTypeObject PyObjectArrType_Type;
-      87             : 
-      88             : extern NPY_NO_EXPORT PyTypeObject PyStringArrType_Type;
-      89             : 
-      90             : extern NPY_NO_EXPORT PyTypeObject PyUnicodeArrType_Type;
-      91             : 
-      92             : extern NPY_NO_EXPORT PyTypeObject PyVoidArrType_Type;
-      93             : 
-      94             : NPY_NO_EXPORT  int PyArray_SetNumericOps \
-      95             :        (PyObject *);
-      96             : NPY_NO_EXPORT  PyObject * PyArray_GetNumericOps \
-      97             :        (void);
-      98             : NPY_NO_EXPORT  int PyArray_INCREF \
-      99             :        (PyArrayObject *);
-     100             : NPY_NO_EXPORT  int PyArray_XDECREF \
-     101             :        (PyArrayObject *);
-     102             : NPY_NO_EXPORT  void PyArray_SetStringFunction \
-     103             :        (PyObject *, int);
-     104             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromType \
-     105             :        (int);
-     106             : NPY_NO_EXPORT  PyObject * PyArray_TypeObjectFromType \
-     107             :        (int);
-     108             : NPY_NO_EXPORT  char * PyArray_Zero \
-     109             :        (PyArrayObject *);
-     110             : NPY_NO_EXPORT  char * PyArray_One \
-     111             :        (PyArrayObject *);
-     112             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_CastToType \
-     113             :        (PyArrayObject *, PyArray_Descr *, int);
-     114             : NPY_NO_EXPORT  int PyArray_CastTo \
-     115             :        (PyArrayObject *, PyArrayObject *);
-     116             : NPY_NO_EXPORT  int PyArray_CastAnyTo \
-     117             :        (PyArrayObject *, PyArrayObject *);
-     118             : NPY_NO_EXPORT  int PyArray_CanCastSafely \
-     119             :        (int, int);
-     120             : NPY_NO_EXPORT  npy_bool PyArray_CanCastTo \
-     121             :        (PyArray_Descr *, PyArray_Descr *);
-     122             : NPY_NO_EXPORT  int PyArray_ObjectType \
-     123             :        (PyObject *, int);
-     124             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromObject \
-     125             :        (PyObject *, PyArray_Descr *);
-     126             : NPY_NO_EXPORT  PyArrayObject ** PyArray_ConvertToCommonType \
-     127             :        (PyObject *, int *);
-     128             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromScalar \
-     129             :        (PyObject *);
-     130             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrFromTypeObject \
-     131             :        (PyObject *);
-     132             : NPY_NO_EXPORT  npy_intp PyArray_Size \
-     133             :        (PyObject *);
-     134             : NPY_NO_EXPORT  PyObject * PyArray_Scalar \
-     135             :        (void *, PyArray_Descr *, PyObject *);
-     136             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromScalar \
-     137             :        (PyObject *, PyArray_Descr *);
-     138             : NPY_NO_EXPORT  void PyArray_ScalarAsCtype \
-     139             :        (PyObject *, void *);
-     140             : NPY_NO_EXPORT  int PyArray_CastScalarToCtype \
-     141             :        (PyObject *, void *, PyArray_Descr *);
-     142             : NPY_NO_EXPORT  int PyArray_CastScalarDirect \
-     143             :        (PyObject *, PyArray_Descr *, void *, int);
-     144             : NPY_NO_EXPORT  PyObject * PyArray_ScalarFromObject \
-     145             :        (PyObject *);
-     146             : NPY_NO_EXPORT  PyArray_VectorUnaryFunc * PyArray_GetCastFunc \
-     147             :        (PyArray_Descr *, int);
-     148             : NPY_NO_EXPORT  PyObject * PyArray_FromDims \
-     149             :        (int NPY_UNUSED(nd), int *NPY_UNUSED(d), int NPY_UNUSED(type));
-     150             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_FromDimsAndDataAndDescr \
-     151             :        (int NPY_UNUSED(nd), int *NPY_UNUSED(d), PyArray_Descr *, char *NPY_UNUSED(data));
-     152             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromAny \
-     153             :        (PyObject *, PyArray_Descr *, int, int, int, PyObject *);
-     154             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(1) PyObject * PyArray_EnsureArray \
-     155             :        (PyObject *);
-     156             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(1) PyObject * PyArray_EnsureAnyArray \
-     157             :        (PyObject *);
-     158             : NPY_NO_EXPORT  PyObject * PyArray_FromFile \
-     159             :        (FILE *, PyArray_Descr *, npy_intp, char *);
-     160             : NPY_NO_EXPORT  PyObject * PyArray_FromString \
-     161             :        (char *, npy_intp, PyArray_Descr *, npy_intp, char *);
-     162             : NPY_NO_EXPORT  PyObject * PyArray_FromBuffer \
-     163             :        (PyObject *, PyArray_Descr *, npy_intp, npy_intp);
-     164             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromIter \
-     165             :        (PyObject *, PyArray_Descr *, npy_intp);
-     166             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(1) PyObject * PyArray_Return \
-     167             :        (PyArrayObject *);
-     168             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_GetField \
-     169             :        (PyArrayObject *, PyArray_Descr *, int);
-     170             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) int PyArray_SetField \
-     171             :        (PyArrayObject *, PyArray_Descr *, int, PyObject *);
-     172             : NPY_NO_EXPORT  PyObject * PyArray_Byteswap \
-     173             :        (PyArrayObject *, npy_bool);
-     174             : NPY_NO_EXPORT  PyObject * PyArray_Resize \
-     175             :        (PyArrayObject *, PyArray_Dims *, int, NPY_ORDER NPY_UNUSED(order));
-     176             : NPY_NO_EXPORT  int PyArray_MoveInto \
-     177             :        (PyArrayObject *, PyArrayObject *);
-     178             : NPY_NO_EXPORT  int PyArray_CopyInto \
-     179             :        (PyArrayObject *, PyArrayObject *);
-     180             : NPY_NO_EXPORT  int PyArray_CopyAnyInto \
-     181             :        (PyArrayObject *, PyArrayObject *);
-     182             : NPY_NO_EXPORT  int PyArray_CopyObject \
-     183             :        (PyArrayObject *, PyObject *);
-     184             : NPY_NO_EXPORT  PyObject * PyArray_NewCopy \
-     185             :        (PyArrayObject *, NPY_ORDER);
-     186             : NPY_NO_EXPORT  PyObject * PyArray_ToList \
-     187             :        (PyArrayObject *);
-     188             : NPY_NO_EXPORT  PyObject * PyArray_ToString \
-     189             :        (PyArrayObject *, NPY_ORDER);
-     190             : NPY_NO_EXPORT  int PyArray_ToFile \
-     191             :        (PyArrayObject *, FILE *, char *, char *);
-     192             : NPY_NO_EXPORT  int PyArray_Dump \
-     193             :        (PyObject *, PyObject *, int);
-     194             : NPY_NO_EXPORT  PyObject * PyArray_Dumps \
-     195             :        (PyObject *, int);
-     196             : NPY_NO_EXPORT  int PyArray_ValidType \
-     197             :        (int);
-     198             : NPY_NO_EXPORT  void PyArray_UpdateFlags \
-     199             :        (PyArrayObject *, int);
-     200             : NPY_NO_EXPORT  PyObject * PyArray_New \
-     201             :        (PyTypeObject *, int, npy_intp const *, int, npy_intp const *, void *, int, int, PyObject *);
-     202             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_NewFromDescr \
-     203             :        (PyTypeObject *, PyArray_Descr *, int, npy_intp const *, npy_intp const *, void *, int, PyObject *);
-     204             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrNew \
-     205             :        (PyArray_Descr *);
-     206             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrNewFromType \
-     207             :        (int);
-     208             : NPY_NO_EXPORT  double PyArray_GetPriority \
-     209             :        (PyObject *, double);
-     210             : NPY_NO_EXPORT  PyObject * PyArray_IterNew \
-     211             :        (PyObject *);
-     212             : NPY_NO_EXPORT  PyObject* PyArray_MultiIterNew \
-     213             :        (int, ...);
-     214             : NPY_NO_EXPORT  int PyArray_PyIntAsInt \
-     215             :        (PyObject *);
-     216             : NPY_NO_EXPORT  npy_intp PyArray_PyIntAsIntp \
-     217             :        (PyObject *);
-     218             : NPY_NO_EXPORT  int PyArray_Broadcast \
-     219             :        (PyArrayMultiIterObject *);
-     220             : NPY_NO_EXPORT  void PyArray_FillObjectArray \
-     221             :        (PyArrayObject *, PyObject *);
-     222             : NPY_NO_EXPORT  int PyArray_FillWithScalar \
-     223             :        (PyArrayObject *, PyObject *);
-     224             : NPY_NO_EXPORT  npy_bool PyArray_CheckStrides \
-     225             :        (int, int, npy_intp, npy_intp, npy_intp const *, npy_intp const *);
-     226             : NPY_NO_EXPORT  PyArray_Descr * PyArray_DescrNewByteorder \
-     227             :        (PyArray_Descr *, char);
-     228             : NPY_NO_EXPORT  PyObject * PyArray_IterAllButAxis \
-     229             :        (PyObject *, int *);
-     230             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_CheckFromAny \
-     231             :        (PyObject *, PyArray_Descr *, int, int, int, PyObject *);
-     232             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_FromArray \
-     233             :        (PyArrayObject *, PyArray_Descr *, int);
-     234             : NPY_NO_EXPORT  PyObject * PyArray_FromInterface \
-     235             :        (PyObject *);
-     236             : NPY_NO_EXPORT  PyObject * PyArray_FromStructInterface \
-     237             :        (PyObject *);
-     238             : NPY_NO_EXPORT  PyObject * PyArray_FromArrayAttr \
-     239             :        (PyObject *, PyArray_Descr *, PyObject *);
-     240             : NPY_NO_EXPORT  NPY_SCALARKIND PyArray_ScalarKind \
-     241             :        (int, PyArrayObject **);
-     242             : NPY_NO_EXPORT  int PyArray_CanCoerceScalar \
-     243             :        (int, int, NPY_SCALARKIND);
-     244             : NPY_NO_EXPORT  PyObject * PyArray_NewFlagsObject \
-     245             :        (PyObject *);
-     246             : NPY_NO_EXPORT  npy_bool PyArray_CanCastScalar \
-     247             :        (PyTypeObject *, PyTypeObject *);
-     248             : NPY_NO_EXPORT  int PyArray_CompareUCS4 \
-     249             :        (npy_ucs4 const *, npy_ucs4 const *, size_t);
-     250             : NPY_NO_EXPORT  int PyArray_RemoveSmallest \
-     251             :        (PyArrayMultiIterObject *);
-     252             : NPY_NO_EXPORT  int PyArray_ElementStrides \
-     253             :        (PyObject *);
-     254             : NPY_NO_EXPORT  void PyArray_Item_INCREF \
-     255             :        (char *, PyArray_Descr *);
-     256             : NPY_NO_EXPORT  void PyArray_Item_XDECREF \
-     257             :        (char *, PyArray_Descr *);
-     258             : NPY_NO_EXPORT  PyObject * PyArray_FieldNames \
-     259             :        (PyObject *);
-     260             : NPY_NO_EXPORT  PyObject * PyArray_Transpose \
-     261             :        (PyArrayObject *, PyArray_Dims *);
-     262             : NPY_NO_EXPORT  PyObject * PyArray_TakeFrom \
-     263             :        (PyArrayObject *, PyObject *, int, PyArrayObject *, NPY_CLIPMODE);
-     264             : NPY_NO_EXPORT  PyObject * PyArray_PutTo \
-     265             :        (PyArrayObject *, PyObject*, PyObject *, NPY_CLIPMODE);
-     266             : NPY_NO_EXPORT  PyObject * PyArray_PutMask \
-     267             :        (PyArrayObject *, PyObject*, PyObject*);
-     268             : NPY_NO_EXPORT  PyObject * PyArray_Repeat \
-     269             :        (PyArrayObject *, PyObject *, int);
-     270             : NPY_NO_EXPORT  PyObject * PyArray_Choose \
-     271             :        (PyArrayObject *, PyObject *, PyArrayObject *, NPY_CLIPMODE);
-     272             : NPY_NO_EXPORT  int PyArray_Sort \
-     273             :        (PyArrayObject *, int, NPY_SORTKIND);
-     274             : NPY_NO_EXPORT  PyObject * PyArray_ArgSort \
-     275             :        (PyArrayObject *, int, NPY_SORTKIND);
-     276             : NPY_NO_EXPORT  PyObject * PyArray_SearchSorted \
-     277             :        (PyArrayObject *, PyObject *, NPY_SEARCHSIDE, PyObject *);
-     278             : NPY_NO_EXPORT  PyObject * PyArray_ArgMax \
-     279             :        (PyArrayObject *, int, PyArrayObject *);
-     280             : NPY_NO_EXPORT  PyObject * PyArray_ArgMin \
-     281             :        (PyArrayObject *, int, PyArrayObject *);
-     282             : NPY_NO_EXPORT  PyObject * PyArray_Reshape \
-     283             :        (PyArrayObject *, PyObject *);
-     284             : NPY_NO_EXPORT  PyObject * PyArray_Newshape \
-     285             :        (PyArrayObject *, PyArray_Dims *, NPY_ORDER);
-     286             : NPY_NO_EXPORT  PyObject * PyArray_Squeeze \
-     287             :        (PyArrayObject *);
-     288             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) PyObject * PyArray_View \
-     289             :        (PyArrayObject *, PyArray_Descr *, PyTypeObject *);
-     290             : NPY_NO_EXPORT  PyObject * PyArray_SwapAxes \
-     291             :        (PyArrayObject *, int, int);
-     292             : NPY_NO_EXPORT  PyObject * PyArray_Max \
-     293             :        (PyArrayObject *, int, PyArrayObject *);
-     294             : NPY_NO_EXPORT  PyObject * PyArray_Min \
-     295             :        (PyArrayObject *, int, PyArrayObject *);
-     296             : NPY_NO_EXPORT  PyObject * PyArray_Ptp \
-     297             :        (PyArrayObject *, int, PyArrayObject *);
-     298             : NPY_NO_EXPORT  PyObject * PyArray_Mean \
-     299             :        (PyArrayObject *, int, int, PyArrayObject *);
-     300             : NPY_NO_EXPORT  PyObject * PyArray_Trace \
-     301             :        (PyArrayObject *, int, int, int, int, PyArrayObject *);
-     302             : NPY_NO_EXPORT  PyObject * PyArray_Diagonal \
-     303             :        (PyArrayObject *, int, int, int);
-     304             : NPY_NO_EXPORT  PyObject * PyArray_Clip \
-     305             :        (PyArrayObject *, PyObject *, PyObject *, PyArrayObject *);
-     306             : NPY_NO_EXPORT  PyObject * PyArray_Conjugate \
-     307             :        (PyArrayObject *, PyArrayObject *);
-     308             : NPY_NO_EXPORT  PyObject * PyArray_Nonzero \
-     309             :        (PyArrayObject *);
-     310             : NPY_NO_EXPORT  PyObject * PyArray_Std \
-     311             :        (PyArrayObject *, int, int, PyArrayObject *, int);
-     312             : NPY_NO_EXPORT  PyObject * PyArray_Sum \
-     313             :        (PyArrayObject *, int, int, PyArrayObject *);
-     314             : NPY_NO_EXPORT  PyObject * PyArray_CumSum \
-     315             :        (PyArrayObject *, int, int, PyArrayObject *);
-     316             : NPY_NO_EXPORT  PyObject * PyArray_Prod \
-     317             :        (PyArrayObject *, int, int, PyArrayObject *);
-     318             : NPY_NO_EXPORT  PyObject * PyArray_CumProd \
-     319             :        (PyArrayObject *, int, int, PyArrayObject *);
-     320             : NPY_NO_EXPORT  PyObject * PyArray_All \
-     321             :        (PyArrayObject *, int, PyArrayObject *);
-     322             : NPY_NO_EXPORT  PyObject * PyArray_Any \
-     323             :        (PyArrayObject *, int, PyArrayObject *);
-     324             : NPY_NO_EXPORT  PyObject * PyArray_Compress \
-     325             :        (PyArrayObject *, PyObject *, int, PyArrayObject *);
-     326             : NPY_NO_EXPORT  PyObject * PyArray_Flatten \
-     327             :        (PyArrayObject *, NPY_ORDER);
-     328             : NPY_NO_EXPORT  PyObject * PyArray_Ravel \
-     329             :        (PyArrayObject *, NPY_ORDER);
-     330             : NPY_NO_EXPORT  npy_intp PyArray_MultiplyList \
-     331             :        (npy_intp const *, int);
-     332             : NPY_NO_EXPORT  int PyArray_MultiplyIntList \
-     333             :        (int const *, int);
-     334             : NPY_NO_EXPORT  void * PyArray_GetPtr \
-     335             :        (PyArrayObject *, npy_intp const*);
-     336             : NPY_NO_EXPORT  int PyArray_CompareLists \
-     337             :        (npy_intp const *, npy_intp const *, int);
-     338             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(5) int PyArray_AsCArray \
-     339             :        (PyObject **, void *, npy_intp *, int, PyArray_Descr*);
-     340             : NPY_NO_EXPORT  int PyArray_As1D \
-     341             :        (PyObject **NPY_UNUSED(op), char **NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int NPY_UNUSED(typecode));
-     342             : NPY_NO_EXPORT  int PyArray_As2D \
-     343             :        (PyObject **NPY_UNUSED(op), char ***NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int *NPY_UNUSED(d2), int NPY_UNUSED(typecode));
-     344             : NPY_NO_EXPORT  int PyArray_Free \
-     345             :        (PyObject *, void *);
-     346             : NPY_NO_EXPORT  int PyArray_Converter \
-     347             :        (PyObject *, PyObject **);
-     348             : NPY_NO_EXPORT  int PyArray_IntpFromSequence \
-     349             :        (PyObject *, npy_intp *, int);
-     350             : NPY_NO_EXPORT  PyObject * PyArray_Concatenate \
-     351             :        (PyObject *, int);
-     352             : NPY_NO_EXPORT  PyObject * PyArray_InnerProduct \
-     353             :        (PyObject *, PyObject *);
-     354             : NPY_NO_EXPORT  PyObject * PyArray_MatrixProduct \
-     355             :        (PyObject *, PyObject *);
-     356             : NPY_NO_EXPORT  PyObject * PyArray_CopyAndTranspose \
-     357             :        (PyObject *);
-     358             : NPY_NO_EXPORT  PyObject * PyArray_Correlate \
-     359             :        (PyObject *, PyObject *, int);
-     360             : NPY_NO_EXPORT  int PyArray_TypestrConvert \
-     361             :        (int, int);
-     362             : NPY_NO_EXPORT  int PyArray_DescrConverter \
-     363             :        (PyObject *, PyArray_Descr **);
-     364             : NPY_NO_EXPORT  int PyArray_DescrConverter2 \
-     365             :        (PyObject *, PyArray_Descr **);
-     366             : NPY_NO_EXPORT  int PyArray_IntpConverter \
-     367             :        (PyObject *, PyArray_Dims *);
-     368             : NPY_NO_EXPORT  int PyArray_BufferConverter \
-     369             :        (PyObject *, PyArray_Chunk *);
-     370             : NPY_NO_EXPORT  int PyArray_AxisConverter \
-     371             :        (PyObject *, int *);
-     372             : NPY_NO_EXPORT  int PyArray_BoolConverter \
-     373             :        (PyObject *, npy_bool *);
-     374             : NPY_NO_EXPORT  int PyArray_ByteorderConverter \
-     375             :        (PyObject *, char *);
-     376             : NPY_NO_EXPORT  int PyArray_OrderConverter \
-     377             :        (PyObject *, NPY_ORDER *);
-     378             : NPY_NO_EXPORT  unsigned char PyArray_EquivTypes \
-     379             :        (PyArray_Descr *, PyArray_Descr *);
-     380             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_Zeros \
-     381             :        (int, npy_intp const *, PyArray_Descr *, int);
-     382             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_Empty \
-     383             :        (int, npy_intp const *, PyArray_Descr *, int);
-     384             : NPY_NO_EXPORT  PyObject * PyArray_Where \
-     385             :        (PyObject *, PyObject *, PyObject *);
-     386             : NPY_NO_EXPORT  PyObject * PyArray_Arange \
-     387             :        (double, double, double, int);
-     388             : NPY_NO_EXPORT  PyObject * PyArray_ArangeObj \
-     389             :        (PyObject *, PyObject *, PyObject *, PyArray_Descr *);
-     390             : NPY_NO_EXPORT  int PyArray_SortkindConverter \
-     391             :        (PyObject *, NPY_SORTKIND *);
-     392             : NPY_NO_EXPORT  PyObject * PyArray_LexSort \
-     393             :        (PyObject *, int);
-     394             : NPY_NO_EXPORT  PyObject * PyArray_Round \
-     395             :        (PyArrayObject *, int, PyArrayObject *);
-     396             : NPY_NO_EXPORT  unsigned char PyArray_EquivTypenums \
-     397             :        (int, int);
-     398             : NPY_NO_EXPORT  int PyArray_RegisterDataType \
-     399             :        (PyArray_Descr *);
-     400             : NPY_NO_EXPORT  int PyArray_RegisterCastFunc \
-     401             :        (PyArray_Descr *, int, PyArray_VectorUnaryFunc *);
-     402             : NPY_NO_EXPORT  int PyArray_RegisterCanCast \
-     403             :        (PyArray_Descr *, int, NPY_SCALARKIND);
-     404             : NPY_NO_EXPORT  void PyArray_InitArrFuncs \
-     405             :        (PyArray_ArrFuncs *);
-     406             : NPY_NO_EXPORT  PyObject * PyArray_IntTupleFromIntp \
-     407             :        (int, npy_intp const *);
-     408             : NPY_NO_EXPORT  int PyArray_TypeNumFromName \
-     409             :        (char const *);
-     410             : NPY_NO_EXPORT  int PyArray_ClipmodeConverter \
-     411             :        (PyObject *, NPY_CLIPMODE *);
-     412             : NPY_NO_EXPORT  int PyArray_OutputConverter \
-     413             :        (PyObject *, PyArrayObject **);
-     414             : NPY_NO_EXPORT  PyObject * PyArray_BroadcastToShape \
-     415             :        (PyObject *, npy_intp *, int);
-     416             : NPY_NO_EXPORT  void _PyArray_SigintHandler \
-     417             :        (int);
-     418             : NPY_NO_EXPORT  void* _PyArray_GetSigintBuf \
-     419             :        (void);
-     420             : NPY_NO_EXPORT  int PyArray_DescrAlignConverter \
-     421             :        (PyObject *, PyArray_Descr **);
-     422             : NPY_NO_EXPORT  int PyArray_DescrAlignConverter2 \
-     423             :        (PyObject *, PyArray_Descr **);
-     424             : NPY_NO_EXPORT  int PyArray_SearchsideConverter \
-     425             :        (PyObject *, void *);
-     426             : NPY_NO_EXPORT  PyObject * PyArray_CheckAxis \
-     427             :        (PyArrayObject *, int *, int);
-     428             : NPY_NO_EXPORT  npy_intp PyArray_OverflowMultiplyList \
-     429             :        (npy_intp const *, int);
-     430             : NPY_NO_EXPORT  int PyArray_CompareString \
-     431             :        (const char *, const char *, size_t);
-     432             : NPY_NO_EXPORT  PyObject* PyArray_MultiIterFromObjects \
-     433             :        (PyObject **, int, int, ...);
-     434             : NPY_NO_EXPORT  int PyArray_GetEndianness \
-     435             :        (void);
-     436             : NPY_NO_EXPORT  unsigned int PyArray_GetNDArrayCFeatureVersion \
-     437             :        (void);
-     438             : NPY_NO_EXPORT  PyObject * PyArray_Correlate2 \
-     439             :        (PyObject *, PyObject *, int);
-     440             : NPY_NO_EXPORT  PyObject* PyArray_NeighborhoodIterNew \
-     441             :        (PyArrayIterObject *, const npy_intp *, int, PyArrayObject*);
-     442             : extern NPY_NO_EXPORT PyTypeObject PyTimeIntegerArrType_Type;
-     443             : 
-     444             : extern NPY_NO_EXPORT PyTypeObject PyDatetimeArrType_Type;
-     445             : 
-     446             : extern NPY_NO_EXPORT PyTypeObject PyTimedeltaArrType_Type;
-     447             : 
-     448             : extern NPY_NO_EXPORT PyTypeObject PyHalfArrType_Type;
-     449             : 
-     450             : extern NPY_NO_EXPORT PyTypeObject NpyIter_Type;
-     451             : 
-     452             : NPY_NO_EXPORT  void PyArray_SetDatetimeParseFunction \
-     453             :        (PyObject *NPY_UNUSED(op));
-     454             : NPY_NO_EXPORT  void PyArray_DatetimeToDatetimeStruct \
-     455             :        (npy_datetime NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *);
-     456             : NPY_NO_EXPORT  void PyArray_TimedeltaToTimedeltaStruct \
-     457             :        (npy_timedelta NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *);
-     458             : NPY_NO_EXPORT  npy_datetime PyArray_DatetimeStructToDatetime \
-     459             :        (NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *NPY_UNUSED(d));
-     460             : NPY_NO_EXPORT  npy_datetime PyArray_TimedeltaStructToTimedelta \
-     461             :        (NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *NPY_UNUSED(d));
-     462             : NPY_NO_EXPORT  NpyIter * NpyIter_New \
-     463             :        (PyArrayObject *, npy_uint32, NPY_ORDER, NPY_CASTING, PyArray_Descr*);
-     464             : NPY_NO_EXPORT  NpyIter * NpyIter_MultiNew \
-     465             :        (int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **);
-     466             : NPY_NO_EXPORT  NpyIter * NpyIter_AdvancedNew \
-     467             :        (int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **, int, int **, npy_intp *, npy_intp);
-     468             : NPY_NO_EXPORT  NpyIter * NpyIter_Copy \
-     469             :        (NpyIter *);
-     470             : NPY_NO_EXPORT  int NpyIter_Deallocate \
-     471             :        (NpyIter *);
-     472             : NPY_NO_EXPORT  npy_bool NpyIter_HasDelayedBufAlloc \
-     473             :        (NpyIter *);
-     474             : NPY_NO_EXPORT  npy_bool NpyIter_HasExternalLoop \
-     475             :        (NpyIter *);
-     476             : NPY_NO_EXPORT  int NpyIter_EnableExternalLoop \
-     477             :        (NpyIter *);
-     478             : NPY_NO_EXPORT  npy_intp * NpyIter_GetInnerStrideArray \
-     479             :        (NpyIter *);
-     480             : NPY_NO_EXPORT  npy_intp * NpyIter_GetInnerLoopSizePtr \
-     481             :        (NpyIter *);
-     482             : NPY_NO_EXPORT  int NpyIter_Reset \
-     483             :        (NpyIter *, char **);
-     484             : NPY_NO_EXPORT  int NpyIter_ResetBasePointers \
-     485             :        (NpyIter *, char **, char **);
-     486             : NPY_NO_EXPORT  int NpyIter_ResetToIterIndexRange \
-     487             :        (NpyIter *, npy_intp, npy_intp, char **);
-     488             : NPY_NO_EXPORT  int NpyIter_GetNDim \
-     489             :        (NpyIter *);
-     490             : NPY_NO_EXPORT  int NpyIter_GetNOp \
-     491             :        (NpyIter *);
-     492             : NPY_NO_EXPORT  NpyIter_IterNextFunc * NpyIter_GetIterNext \
-     493             :        (NpyIter *, char **);
-     494             : NPY_NO_EXPORT  npy_intp NpyIter_GetIterSize \
-     495             :        (NpyIter *);
-     496             : NPY_NO_EXPORT  void NpyIter_GetIterIndexRange \
-     497             :        (NpyIter *, npy_intp *, npy_intp *);
-     498             : NPY_NO_EXPORT  npy_intp NpyIter_GetIterIndex \
-     499             :        (NpyIter *);
-     500             : NPY_NO_EXPORT  int NpyIter_GotoIterIndex \
-     501             :        (NpyIter *, npy_intp);
-     502             : NPY_NO_EXPORT  npy_bool NpyIter_HasMultiIndex \
-     503             :        (NpyIter *);
-     504             : NPY_NO_EXPORT  int NpyIter_GetShape \
-     505             :        (NpyIter *, npy_intp *);
-     506             : NPY_NO_EXPORT  NpyIter_GetMultiIndexFunc * NpyIter_GetGetMultiIndex \
-     507             :        (NpyIter *, char **);
-     508             : NPY_NO_EXPORT  int NpyIter_GotoMultiIndex \
-     509             :        (NpyIter *, npy_intp const *);
-     510             : NPY_NO_EXPORT  int NpyIter_RemoveMultiIndex \
-     511             :        (NpyIter *);
-     512             : NPY_NO_EXPORT  npy_bool NpyIter_HasIndex \
-     513             :        (NpyIter *);
-     514             : NPY_NO_EXPORT  npy_bool NpyIter_IsBuffered \
-     515             :        (NpyIter *);
-     516             : NPY_NO_EXPORT  npy_bool NpyIter_IsGrowInner \
-     517             :        (NpyIter *);
-     518             : NPY_NO_EXPORT  npy_intp NpyIter_GetBufferSize \
-     519             :        (NpyIter *);
-     520             : NPY_NO_EXPORT  npy_intp * NpyIter_GetIndexPtr \
-     521             :        (NpyIter *);
-     522             : NPY_NO_EXPORT  int NpyIter_GotoIndex \
-     523             :        (NpyIter *, npy_intp);
-     524             : NPY_NO_EXPORT  char ** NpyIter_GetDataPtrArray \
-     525             :        (NpyIter *);
-     526             : NPY_NO_EXPORT  PyArray_Descr ** NpyIter_GetDescrArray \
-     527             :        (NpyIter *);
-     528             : NPY_NO_EXPORT  PyArrayObject ** NpyIter_GetOperandArray \
-     529             :        (NpyIter *);
-     530             : NPY_NO_EXPORT  PyArrayObject * NpyIter_GetIterView \
-     531             :        (NpyIter *, npy_intp);
-     532             : NPY_NO_EXPORT  void NpyIter_GetReadFlags \
-     533             :        (NpyIter *, char *);
-     534             : NPY_NO_EXPORT  void NpyIter_GetWriteFlags \
-     535             :        (NpyIter *, char *);
-     536             : NPY_NO_EXPORT  void NpyIter_DebugPrint \
-     537             :        (NpyIter *);
-     538             : NPY_NO_EXPORT  npy_bool NpyIter_IterationNeedsAPI \
-     539             :        (NpyIter *);
-     540             : NPY_NO_EXPORT  void NpyIter_GetInnerFixedStrideArray \
-     541             :        (NpyIter *, npy_intp *);
-     542             : NPY_NO_EXPORT  int NpyIter_RemoveAxis \
-     543             :        (NpyIter *, int);
-     544             : NPY_NO_EXPORT  npy_intp * NpyIter_GetAxisStrideArray \
-     545             :        (NpyIter *, int);
-     546             : NPY_NO_EXPORT  npy_bool NpyIter_RequiresBuffering \
-     547             :        (NpyIter *);
-     548             : NPY_NO_EXPORT  char ** NpyIter_GetInitialDataPtrArray \
-     549             :        (NpyIter *);
-     550             : NPY_NO_EXPORT  int NpyIter_CreateCompatibleStrides \
-     551             :        (NpyIter *, npy_intp, npy_intp *);
-     552             : NPY_NO_EXPORT  int PyArray_CastingConverter \
-     553             :        (PyObject *, NPY_CASTING *);
-     554             : NPY_NO_EXPORT  npy_intp PyArray_CountNonzero \
-     555             :        (PyArrayObject *);
-     556             : NPY_NO_EXPORT  PyArray_Descr * PyArray_PromoteTypes \
-     557             :        (PyArray_Descr *, PyArray_Descr *);
-     558             : NPY_NO_EXPORT  PyArray_Descr * PyArray_MinScalarType \
-     559             :        (PyArrayObject *);
-     560             : NPY_NO_EXPORT  PyArray_Descr * PyArray_ResultType \
-     561             :        (npy_intp, PyArrayObject *arrs[], npy_intp, PyArray_Descr *descrs[]);
-     562             : NPY_NO_EXPORT  npy_bool PyArray_CanCastArrayTo \
-     563             :        (PyArrayObject *, PyArray_Descr *, NPY_CASTING);
-     564             : NPY_NO_EXPORT  npy_bool PyArray_CanCastTypeTo \
-     565             :        (PyArray_Descr *, PyArray_Descr *, NPY_CASTING);
-     566             : NPY_NO_EXPORT  PyArrayObject * PyArray_EinsteinSum \
-     567             :        (char *, npy_intp, PyArrayObject **, PyArray_Descr *, NPY_ORDER, NPY_CASTING, PyArrayObject *);
-     568             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(3) PyObject * PyArray_NewLikeArray \
-     569             :        (PyArrayObject *, NPY_ORDER, PyArray_Descr *, int);
-     570             : NPY_NO_EXPORT  int PyArray_GetArrayParamsFromObject \
-     571             :        (PyObject *NPY_UNUSED(op), PyArray_Descr *NPY_UNUSED(requested_dtype), npy_bool NPY_UNUSED(writeable), PyArray_Descr **NPY_UNUSED(out_dtype), int *NPY_UNUSED(out_ndim), npy_intp *NPY_UNUSED(out_dims), PyArrayObject **NPY_UNUSED(out_arr), PyObject *NPY_UNUSED(context));
-     572             : NPY_NO_EXPORT  int PyArray_ConvertClipmodeSequence \
-     573             :        (PyObject *, NPY_CLIPMODE *, int);
-     574             : NPY_NO_EXPORT  PyObject * PyArray_MatrixProduct2 \
-     575             :        (PyObject *, PyObject *, PyArrayObject*);
-     576             : NPY_NO_EXPORT  npy_bool NpyIter_IsFirstVisit \
-     577             :        (NpyIter *, int);
-     578             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) int PyArray_SetBaseObject \
-     579             :        (PyArrayObject *, PyObject *);
-     580             : NPY_NO_EXPORT  void PyArray_CreateSortedStridePerm \
-     581             :        (int, npy_intp const *, npy_stride_sort_item *);
-     582             : NPY_NO_EXPORT  void PyArray_RemoveAxesInPlace \
-     583             :        (PyArrayObject *, const npy_bool *);
-     584             : NPY_NO_EXPORT  void PyArray_DebugPrint \
-     585             :        (PyArrayObject *);
-     586             : NPY_NO_EXPORT  int PyArray_FailUnlessWriteable \
-     587             :        (PyArrayObject *, const char *);
-     588             : NPY_NO_EXPORT NPY_STEALS_REF_TO_ARG(2) int PyArray_SetUpdateIfCopyBase \
-     589             :        (PyArrayObject *, PyArrayObject *);
-     590             : NPY_NO_EXPORT  void * PyDataMem_NEW \
-     591             :        (size_t);
-     592             : NPY_NO_EXPORT  void PyDataMem_FREE \
-     593             :        (void *);
-     594             : NPY_NO_EXPORT  void * PyDataMem_RENEW \
-     595             :        (void *, size_t);
-     596             : NPY_NO_EXPORT  PyDataMem_EventHookFunc * PyDataMem_SetEventHook \
-     597             :        (PyDataMem_EventHookFunc *, void *, void **);
-     598             : extern NPY_NO_EXPORT NPY_CASTING NPY_DEFAULT_ASSIGN_CASTING;
-     599             : 
-     600             : NPY_NO_EXPORT  void PyArray_MapIterSwapAxes \
-     601             :        (PyArrayMapIterObject *, PyArrayObject **, int);
-     602             : NPY_NO_EXPORT  PyObject * PyArray_MapIterArray \
-     603             :        (PyArrayObject *, PyObject *);
-     604             : NPY_NO_EXPORT  void PyArray_MapIterNext \
-     605             :        (PyArrayMapIterObject *);
-     606             : NPY_NO_EXPORT  int PyArray_Partition \
-     607             :        (PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND);
-     608             : NPY_NO_EXPORT  PyObject * PyArray_ArgPartition \
-     609             :        (PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND);
-     610             : NPY_NO_EXPORT  int PyArray_SelectkindConverter \
-     611             :        (PyObject *, NPY_SELECTKIND *);
-     612             : NPY_NO_EXPORT  void * PyDataMem_NEW_ZEROED \
-     613             :        (size_t, size_t);
-     614             : NPY_NO_EXPORT  int PyArray_CheckAnyScalarExact \
-     615             :        (PyObject *);
-     616             : NPY_NO_EXPORT  PyObject * PyArray_MapIterArrayCopyIfOverlap \
-     617             :        (PyArrayObject *, PyObject *, int, PyArrayObject *);
-     618             : NPY_NO_EXPORT  int PyArray_ResolveWritebackIfCopy \
-     619             :        (PyArrayObject *);
-     620             : NPY_NO_EXPORT  int PyArray_SetWritebackIfCopyBase \
-     621             :        (PyArrayObject *, PyArrayObject *);
-     622             : NPY_NO_EXPORT  PyObject * PyDataMem_SetHandler \
-     623             :        (PyObject *);
-     624             : NPY_NO_EXPORT  PyObject * PyDataMem_GetHandler \
-     625             :        (void);
-     626             : extern NPY_NO_EXPORT PyObject* PyDataMem_DefaultHandler;
-     627             : 
-     628             : 
-     629             : #else
-     630             : 
-     631             : #if defined(PY_ARRAY_UNIQUE_SYMBOL)
-     632             : #define PyArray_API PY_ARRAY_UNIQUE_SYMBOL
-     633             : #endif
-     634             : 
-     635             : #if defined(NO_IMPORT) || defined(NO_IMPORT_ARRAY)
-     636             : extern void **PyArray_API;
-     637             : #else
-     638             : #if defined(PY_ARRAY_UNIQUE_SYMBOL)
-     639             : void **PyArray_API;
-     640             : #else
-     641             : static void **PyArray_API=NULL;
-     642             : #endif
-     643             : #endif
-     644             : 
-     645             : #define PyArray_GetNDArrayCVersion \
-     646             :         (*(unsigned int (*)(void)) \
-     647             :     PyArray_API[0])
-     648             : #define PyBigArray_Type (*(PyTypeObject *)PyArray_API[1])
-     649             : #define PyArray_Type (*(PyTypeObject *)PyArray_API[2])
-     650             : #define PyArrayDescr_Type (*(PyTypeObject *)PyArray_API[3])
-     651             : #define PyArrayFlags_Type (*(PyTypeObject *)PyArray_API[4])
-     652             : #define PyArrayIter_Type (*(PyTypeObject *)PyArray_API[5])
-     653             : #define PyArrayMultiIter_Type (*(PyTypeObject *)PyArray_API[6])
-     654             : #define NPY_NUMUSERTYPES (*(int *)PyArray_API[7])
-     655             : #define PyBoolArrType_Type (*(PyTypeObject *)PyArray_API[8])
-     656             : #define _PyArrayScalar_BoolValues ((PyBoolScalarObject *)PyArray_API[9])
-     657             : #define PyGenericArrType_Type (*(PyTypeObject *)PyArray_API[10])
-     658             : #define PyNumberArrType_Type (*(PyTypeObject *)PyArray_API[11])
-     659             : #define PyIntegerArrType_Type (*(PyTypeObject *)PyArray_API[12])
-     660             : #define PySignedIntegerArrType_Type (*(PyTypeObject *)PyArray_API[13])
-     661             : #define PyUnsignedIntegerArrType_Type (*(PyTypeObject *)PyArray_API[14])
-     662             : #define PyInexactArrType_Type (*(PyTypeObject *)PyArray_API[15])
-     663             : #define PyFloatingArrType_Type (*(PyTypeObject *)PyArray_API[16])
-     664             : #define PyComplexFloatingArrType_Type (*(PyTypeObject *)PyArray_API[17])
-     665             : #define PyFlexibleArrType_Type (*(PyTypeObject *)PyArray_API[18])
-     666             : #define PyCharacterArrType_Type (*(PyTypeObject *)PyArray_API[19])
-     667             : #define PyByteArrType_Type (*(PyTypeObject *)PyArray_API[20])
-     668             : #define PyShortArrType_Type (*(PyTypeObject *)PyArray_API[21])
-     669             : #define PyIntArrType_Type (*(PyTypeObject *)PyArray_API[22])
-     670             : #define PyLongArrType_Type (*(PyTypeObject *)PyArray_API[23])
-     671             : #define PyLongLongArrType_Type (*(PyTypeObject *)PyArray_API[24])
-     672             : #define PyUByteArrType_Type (*(PyTypeObject *)PyArray_API[25])
-     673             : #define PyUShortArrType_Type (*(PyTypeObject *)PyArray_API[26])
-     674             : #define PyUIntArrType_Type (*(PyTypeObject *)PyArray_API[27])
-     675             : #define PyULongArrType_Type (*(PyTypeObject *)PyArray_API[28])
-     676             : #define PyULongLongArrType_Type (*(PyTypeObject *)PyArray_API[29])
-     677             : #define PyFloatArrType_Type (*(PyTypeObject *)PyArray_API[30])
-     678             : #define PyDoubleArrType_Type (*(PyTypeObject *)PyArray_API[31])
-     679             : #define PyLongDoubleArrType_Type (*(PyTypeObject *)PyArray_API[32])
-     680             : #define PyCFloatArrType_Type (*(PyTypeObject *)PyArray_API[33])
-     681             : #define PyCDoubleArrType_Type (*(PyTypeObject *)PyArray_API[34])
-     682             : #define PyCLongDoubleArrType_Type (*(PyTypeObject *)PyArray_API[35])
-     683             : #define PyObjectArrType_Type (*(PyTypeObject *)PyArray_API[36])
-     684             : #define PyStringArrType_Type (*(PyTypeObject *)PyArray_API[37])
-     685             : #define PyUnicodeArrType_Type (*(PyTypeObject *)PyArray_API[38])
-     686             : #define PyVoidArrType_Type (*(PyTypeObject *)PyArray_API[39])
-     687             : #define PyArray_SetNumericOps \
-     688             :         (*(int (*)(PyObject *)) \
-     689             :     PyArray_API[40])
-     690             : #define PyArray_GetNumericOps \
-     691             :         (*(PyObject * (*)(void)) \
-     692             :     PyArray_API[41])
-     693             : #define PyArray_INCREF \
-     694             :         (*(int (*)(PyArrayObject *)) \
-     695             :     PyArray_API[42])
-     696             : #define PyArray_XDECREF \
-     697             :         (*(int (*)(PyArrayObject *)) \
-     698             :     PyArray_API[43])
-     699             : #define PyArray_SetStringFunction \
-     700             :         (*(void (*)(PyObject *, int)) \
-     701             :     PyArray_API[44])
-     702             : #define PyArray_DescrFromType \
-     703             :         (*(PyArray_Descr * (*)(int)) \
-     704             :     PyArray_API[45])
-     705             : #define PyArray_TypeObjectFromType \
-     706             :         (*(PyObject * (*)(int)) \
-     707             :     PyArray_API[46])
-     708             : #define PyArray_Zero \
-     709             :         (*(char * (*)(PyArrayObject *)) \
-     710             :     PyArray_API[47])
-     711             : #define PyArray_One \
-     712             :         (*(char * (*)(PyArrayObject *)) \
-     713             :     PyArray_API[48])
-     714             : #define PyArray_CastToType \
-     715             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, int)) \
-     716             :     PyArray_API[49])
-     717             : #define PyArray_CastTo \
-     718             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
-     719             :     PyArray_API[50])
-     720             : #define PyArray_CastAnyTo \
-     721             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
-     722             :     PyArray_API[51])
-     723             : #define PyArray_CanCastSafely \
-     724             :         (*(int (*)(int, int)) \
-     725             :     PyArray_API[52])
-     726             : #define PyArray_CanCastTo \
-     727             :         (*(npy_bool (*)(PyArray_Descr *, PyArray_Descr *)) \
-     728             :     PyArray_API[53])
-     729             : #define PyArray_ObjectType \
-     730             :         (*(int (*)(PyObject *, int)) \
-     731             :     PyArray_API[54])
-     732             : #define PyArray_DescrFromObject \
-     733             :         (*(PyArray_Descr * (*)(PyObject *, PyArray_Descr *)) \
-     734             :     PyArray_API[55])
-     735             : #define PyArray_ConvertToCommonType \
-     736             :         (*(PyArrayObject ** (*)(PyObject *, int *)) \
-     737             :     PyArray_API[56])
-     738             : #define PyArray_DescrFromScalar \
-     739             :         (*(PyArray_Descr * (*)(PyObject *)) \
-     740             :     PyArray_API[57])
-     741             : #define PyArray_DescrFromTypeObject \
-     742             :         (*(PyArray_Descr * (*)(PyObject *)) \
-     743             :     PyArray_API[58])
-     744             : #define PyArray_Size \
-     745             :         (*(npy_intp (*)(PyObject *)) \
-     746             :     PyArray_API[59])
-     747             : #define PyArray_Scalar \
-     748             :         (*(PyObject * (*)(void *, PyArray_Descr *, PyObject *)) \
-     749             :     PyArray_API[60])
-     750             : #define PyArray_FromScalar \
-     751             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *)) \
-     752             :     PyArray_API[61])
-     753             : #define PyArray_ScalarAsCtype \
-     754             :         (*(void (*)(PyObject *, void *)) \
-     755             :     PyArray_API[62])
-     756             : #define PyArray_CastScalarToCtype \
-     757             :         (*(int (*)(PyObject *, void *, PyArray_Descr *)) \
-     758             :     PyArray_API[63])
-     759             : #define PyArray_CastScalarDirect \
-     760             :         (*(int (*)(PyObject *, PyArray_Descr *, void *, int)) \
-     761             :     PyArray_API[64])
-     762             : #define PyArray_ScalarFromObject \
-     763             :         (*(PyObject * (*)(PyObject *)) \
-     764             :     PyArray_API[65])
-     765             : #define PyArray_GetCastFunc \
-     766             :         (*(PyArray_VectorUnaryFunc * (*)(PyArray_Descr *, int)) \
-     767             :     PyArray_API[66])
-     768             : #define PyArray_FromDims \
-     769             :         (*(PyObject * (*)(int NPY_UNUSED(nd), int *NPY_UNUSED(d), int NPY_UNUSED(type))) \
-     770             :     PyArray_API[67])
-     771             : #define PyArray_FromDimsAndDataAndDescr \
-     772             :         (*(PyObject * (*)(int NPY_UNUSED(nd), int *NPY_UNUSED(d), PyArray_Descr *, char *NPY_UNUSED(data))) \
-     773             :     PyArray_API[68])
-     774             : #define PyArray_FromAny \
-     775             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, int, int, int, PyObject *)) \
-     776             :     PyArray_API[69])
-     777             : #define PyArray_EnsureArray \
-     778             :         (*(PyObject * (*)(PyObject *)) \
-     779             :     PyArray_API[70])
-     780             : #define PyArray_EnsureAnyArray \
-     781             :         (*(PyObject * (*)(PyObject *)) \
-     782             :     PyArray_API[71])
-     783             : #define PyArray_FromFile \
-     784             :         (*(PyObject * (*)(FILE *, PyArray_Descr *, npy_intp, char *)) \
-     785             :     PyArray_API[72])
-     786             : #define PyArray_FromString \
-     787             :         (*(PyObject * (*)(char *, npy_intp, PyArray_Descr *, npy_intp, char *)) \
-     788             :     PyArray_API[73])
-     789             : #define PyArray_FromBuffer \
-     790             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, npy_intp, npy_intp)) \
-     791             :     PyArray_API[74])
-     792             : #define PyArray_FromIter \
-     793             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, npy_intp)) \
-     794             :     PyArray_API[75])
-     795             : #define PyArray_Return \
-     796             :         (*(PyObject * (*)(PyArrayObject *)) \
-     797             :     PyArray_API[76])
-     798             : #define PyArray_GetField \
-     799             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, int)) \
-     800             :     PyArray_API[77])
-     801             : #define PyArray_SetField \
-     802             :         (*(int (*)(PyArrayObject *, PyArray_Descr *, int, PyObject *)) \
-     803             :     PyArray_API[78])
-     804             : #define PyArray_Byteswap \
-     805             :         (*(PyObject * (*)(PyArrayObject *, npy_bool)) \
-     806             :     PyArray_API[79])
-     807             : #define PyArray_Resize \
-     808             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Dims *, int, NPY_ORDER NPY_UNUSED(order))) \
-     809             :     PyArray_API[80])
-     810             : #define PyArray_MoveInto \
-     811             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
-     812             :     PyArray_API[81])
-     813             : #define PyArray_CopyInto \
-     814             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
-     815             :     PyArray_API[82])
-     816             : #define PyArray_CopyAnyInto \
-     817             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
-     818             :     PyArray_API[83])
-     819             : #define PyArray_CopyObject \
-     820             :         (*(int (*)(PyArrayObject *, PyObject *)) \
-     821             :     PyArray_API[84])
-     822             : #define PyArray_NewCopy \
-     823             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
-     824             :     PyArray_API[85])
-     825             : #define PyArray_ToList \
-     826             :         (*(PyObject * (*)(PyArrayObject *)) \
-     827             :     PyArray_API[86])
-     828             : #define PyArray_ToString \
-     829             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
-     830             :     PyArray_API[87])
-     831             : #define PyArray_ToFile \
-     832             :         (*(int (*)(PyArrayObject *, FILE *, char *, char *)) \
-     833             :     PyArray_API[88])
-     834             : #define PyArray_Dump \
-     835             :         (*(int (*)(PyObject *, PyObject *, int)) \
-     836             :     PyArray_API[89])
-     837             : #define PyArray_Dumps \
-     838             :         (*(PyObject * (*)(PyObject *, int)) \
-     839             :     PyArray_API[90])
-     840             : #define PyArray_ValidType \
-     841             :         (*(int (*)(int)) \
-     842             :     PyArray_API[91])
-     843             : #define PyArray_UpdateFlags \
-     844             :         (*(void (*)(PyArrayObject *, int)) \
-     845             :     PyArray_API[92])
-     846             : #define PyArray_New \
-     847             :         (*(PyObject * (*)(PyTypeObject *, int, npy_intp const *, int, npy_intp const *, void *, int, int, PyObject *)) \
-     848             :     PyArray_API[93])
-     849             : #define PyArray_NewFromDescr \
-     850             :         (*(PyObject * (*)(PyTypeObject *, PyArray_Descr *, int, npy_intp const *, npy_intp const *, void *, int, PyObject *)) \
-     851             :     PyArray_API[94])
-     852             : #define PyArray_DescrNew \
-     853             :         (*(PyArray_Descr * (*)(PyArray_Descr *)) \
-     854             :     PyArray_API[95])
-     855             : #define PyArray_DescrNewFromType \
-     856             :         (*(PyArray_Descr * (*)(int)) \
-     857             :     PyArray_API[96])
-     858             : #define PyArray_GetPriority \
-     859             :         (*(double (*)(PyObject *, double)) \
-     860             :     PyArray_API[97])
-     861             : #define PyArray_IterNew \
-     862             :         (*(PyObject * (*)(PyObject *)) \
-     863             :     PyArray_API[98])
-     864             : #define PyArray_MultiIterNew \
-     865             :         (*(PyObject* (*)(int, ...)) \
-     866             :     PyArray_API[99])
-     867             : #define PyArray_PyIntAsInt \
-     868             :         (*(int (*)(PyObject *)) \
-     869             :     PyArray_API[100])
-     870             : #define PyArray_PyIntAsIntp \
-     871             :         (*(npy_intp (*)(PyObject *)) \
-     872             :     PyArray_API[101])
-     873             : #define PyArray_Broadcast \
-     874             :         (*(int (*)(PyArrayMultiIterObject *)) \
-     875             :     PyArray_API[102])
-     876             : #define PyArray_FillObjectArray \
-     877             :         (*(void (*)(PyArrayObject *, PyObject *)) \
-     878             :     PyArray_API[103])
-     879             : #define PyArray_FillWithScalar \
-     880             :         (*(int (*)(PyArrayObject *, PyObject *)) \
-     881             :     PyArray_API[104])
-     882             : #define PyArray_CheckStrides \
-     883             :         (*(npy_bool (*)(int, int, npy_intp, npy_intp, npy_intp const *, npy_intp const *)) \
-     884             :     PyArray_API[105])
-     885             : #define PyArray_DescrNewByteorder \
-     886             :         (*(PyArray_Descr * (*)(PyArray_Descr *, char)) \
-     887             :     PyArray_API[106])
-     888             : #define PyArray_IterAllButAxis \
-     889             :         (*(PyObject * (*)(PyObject *, int *)) \
-     890             :     PyArray_API[107])
-     891             : #define PyArray_CheckFromAny \
-     892             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, int, int, int, PyObject *)) \
-     893             :     PyArray_API[108])
-     894             : #define PyArray_FromArray \
-     895             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, int)) \
-     896             :     PyArray_API[109])
-     897             : #define PyArray_FromInterface \
-     898             :         (*(PyObject * (*)(PyObject *)) \
-     899             :     PyArray_API[110])
-     900             : #define PyArray_FromStructInterface \
-     901             :         (*(PyObject * (*)(PyObject *)) \
-     902             :     PyArray_API[111])
-     903             : #define PyArray_FromArrayAttr \
-     904             :         (*(PyObject * (*)(PyObject *, PyArray_Descr *, PyObject *)) \
-     905             :     PyArray_API[112])
-     906             : #define PyArray_ScalarKind \
-     907             :         (*(NPY_SCALARKIND (*)(int, PyArrayObject **)) \
-     908             :     PyArray_API[113])
-     909             : #define PyArray_CanCoerceScalar \
-     910             :         (*(int (*)(int, int, NPY_SCALARKIND)) \
-     911             :     PyArray_API[114])
-     912             : #define PyArray_NewFlagsObject \
-     913             :         (*(PyObject * (*)(PyObject *)) \
-     914             :     PyArray_API[115])
-     915             : #define PyArray_CanCastScalar \
-     916             :         (*(npy_bool (*)(PyTypeObject *, PyTypeObject *)) \
-     917             :     PyArray_API[116])
-     918             : #define PyArray_CompareUCS4 \
-     919             :         (*(int (*)(npy_ucs4 const *, npy_ucs4 const *, size_t)) \
-     920             :     PyArray_API[117])
-     921             : #define PyArray_RemoveSmallest \
-     922             :         (*(int (*)(PyArrayMultiIterObject *)) \
-     923             :     PyArray_API[118])
-     924             : #define PyArray_ElementStrides \
-     925             :         (*(int (*)(PyObject *)) \
-     926             :     PyArray_API[119])
-     927             : #define PyArray_Item_INCREF \
-     928             :         (*(void (*)(char *, PyArray_Descr *)) \
-     929             :     PyArray_API[120])
-     930             : #define PyArray_Item_XDECREF \
-     931             :         (*(void (*)(char *, PyArray_Descr *)) \
-     932             :     PyArray_API[121])
-     933             : #define PyArray_FieldNames \
-     934             :         (*(PyObject * (*)(PyObject *)) \
-     935             :     PyArray_API[122])
-     936             : #define PyArray_Transpose \
-     937             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Dims *)) \
-     938             :     PyArray_API[123])
-     939             : #define PyArray_TakeFrom \
-     940             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int, PyArrayObject *, NPY_CLIPMODE)) \
-     941             :     PyArray_API[124])
-     942             : #define PyArray_PutTo \
-     943             :         (*(PyObject * (*)(PyArrayObject *, PyObject*, PyObject *, NPY_CLIPMODE)) \
-     944             :     PyArray_API[125])
-     945             : #define PyArray_PutMask \
-     946             :         (*(PyObject * (*)(PyArrayObject *, PyObject*, PyObject*)) \
-     947             :     PyArray_API[126])
-     948             : #define PyArray_Repeat \
-     949             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int)) \
-     950             :     PyArray_API[127])
-     951             : #define PyArray_Choose \
-     952             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, PyArrayObject *, NPY_CLIPMODE)) \
-     953             :     PyArray_API[128])
-     954             : #define PyArray_Sort \
-     955             :         (*(int (*)(PyArrayObject *, int, NPY_SORTKIND)) \
-     956             :     PyArray_API[129])
-     957             : #define PyArray_ArgSort \
-     958             :         (*(PyObject * (*)(PyArrayObject *, int, NPY_SORTKIND)) \
-     959             :     PyArray_API[130])
-     960             : #define PyArray_SearchSorted \
-     961             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, NPY_SEARCHSIDE, PyObject *)) \
-     962             :     PyArray_API[131])
-     963             : #define PyArray_ArgMax \
-     964             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-     965             :     PyArray_API[132])
-     966             : #define PyArray_ArgMin \
-     967             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-     968             :     PyArray_API[133])
-     969             : #define PyArray_Reshape \
-     970             :         (*(PyObject * (*)(PyArrayObject *, PyObject *)) \
-     971             :     PyArray_API[134])
-     972             : #define PyArray_Newshape \
-     973             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Dims *, NPY_ORDER)) \
-     974             :     PyArray_API[135])
-     975             : #define PyArray_Squeeze \
-     976             :         (*(PyObject * (*)(PyArrayObject *)) \
-     977             :     PyArray_API[136])
-     978             : #define PyArray_View \
-     979             :         (*(PyObject * (*)(PyArrayObject *, PyArray_Descr *, PyTypeObject *)) \
-     980             :     PyArray_API[137])
-     981             : #define PyArray_SwapAxes \
-     982             :         (*(PyObject * (*)(PyArrayObject *, int, int)) \
-     983             :     PyArray_API[138])
-     984             : #define PyArray_Max \
-     985             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-     986             :     PyArray_API[139])
-     987             : #define PyArray_Min \
-     988             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-     989             :     PyArray_API[140])
-     990             : #define PyArray_Ptp \
-     991             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-     992             :     PyArray_API[141])
-     993             : #define PyArray_Mean \
-     994             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
-     995             :     PyArray_API[142])
-     996             : #define PyArray_Trace \
-     997             :         (*(PyObject * (*)(PyArrayObject *, int, int, int, int, PyArrayObject *)) \
-     998             :     PyArray_API[143])
-     999             : #define PyArray_Diagonal \
-    1000             :         (*(PyObject * (*)(PyArrayObject *, int, int, int)) \
-    1001             :     PyArray_API[144])
-    1002             : #define PyArray_Clip \
-    1003             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, PyObject *, PyArrayObject *)) \
-    1004             :     PyArray_API[145])
-    1005             : #define PyArray_Conjugate \
-    1006             :         (*(PyObject * (*)(PyArrayObject *, PyArrayObject *)) \
-    1007             :     PyArray_API[146])
-    1008             : #define PyArray_Nonzero \
-    1009             :         (*(PyObject * (*)(PyArrayObject *)) \
-    1010             :     PyArray_API[147])
-    1011             : #define PyArray_Std \
-    1012             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *, int)) \
-    1013             :     PyArray_API[148])
-    1014             : #define PyArray_Sum \
-    1015             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
-    1016             :     PyArray_API[149])
-    1017             : #define PyArray_CumSum \
-    1018             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
-    1019             :     PyArray_API[150])
-    1020             : #define PyArray_Prod \
-    1021             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
-    1022             :     PyArray_API[151])
-    1023             : #define PyArray_CumProd \
-    1024             :         (*(PyObject * (*)(PyArrayObject *, int, int, PyArrayObject *)) \
-    1025             :     PyArray_API[152])
-    1026             : #define PyArray_All \
-    1027             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-    1028             :     PyArray_API[153])
-    1029             : #define PyArray_Any \
-    1030             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-    1031             :     PyArray_API[154])
-    1032             : #define PyArray_Compress \
-    1033             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int, PyArrayObject *)) \
-    1034             :     PyArray_API[155])
-    1035             : #define PyArray_Flatten \
-    1036             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
-    1037             :     PyArray_API[156])
-    1038             : #define PyArray_Ravel \
-    1039             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER)) \
-    1040             :     PyArray_API[157])
-    1041             : #define PyArray_MultiplyList \
-    1042             :         (*(npy_intp (*)(npy_intp const *, int)) \
-    1043             :     PyArray_API[158])
-    1044             : #define PyArray_MultiplyIntList \
-    1045             :         (*(int (*)(int const *, int)) \
-    1046             :     PyArray_API[159])
-    1047             : #define PyArray_GetPtr \
-    1048             :         (*(void * (*)(PyArrayObject *, npy_intp const*)) \
-    1049             :     PyArray_API[160])
-    1050             : #define PyArray_CompareLists \
-    1051             :         (*(int (*)(npy_intp const *, npy_intp const *, int)) \
-    1052             :     PyArray_API[161])
-    1053             : #define PyArray_AsCArray \
-    1054             :         (*(int (*)(PyObject **, void *, npy_intp *, int, PyArray_Descr*)) \
-    1055             :     PyArray_API[162])
-    1056             : #define PyArray_As1D \
-    1057             :         (*(int (*)(PyObject **NPY_UNUSED(op), char **NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int NPY_UNUSED(typecode))) \
-    1058             :     PyArray_API[163])
-    1059             : #define PyArray_As2D \
-    1060             :         (*(int (*)(PyObject **NPY_UNUSED(op), char ***NPY_UNUSED(ptr), int *NPY_UNUSED(d1), int *NPY_UNUSED(d2), int NPY_UNUSED(typecode))) \
-    1061             :     PyArray_API[164])
-    1062             : #define PyArray_Free \
-    1063             :         (*(int (*)(PyObject *, void *)) \
-    1064             :     PyArray_API[165])
-    1065             : #define PyArray_Converter \
-    1066             :         (*(int (*)(PyObject *, PyObject **)) \
-    1067             :     PyArray_API[166])
-    1068             : #define PyArray_IntpFromSequence \
-    1069             :         (*(int (*)(PyObject *, npy_intp *, int)) \
-    1070             :     PyArray_API[167])
-    1071             : #define PyArray_Concatenate \
-    1072             :         (*(PyObject * (*)(PyObject *, int)) \
-    1073             :     PyArray_API[168])
-    1074             : #define PyArray_InnerProduct \
-    1075             :         (*(PyObject * (*)(PyObject *, PyObject *)) \
-    1076             :     PyArray_API[169])
-    1077             : #define PyArray_MatrixProduct \
-    1078             :         (*(PyObject * (*)(PyObject *, PyObject *)) \
-    1079             :     PyArray_API[170])
-    1080             : #define PyArray_CopyAndTranspose \
-    1081             :         (*(PyObject * (*)(PyObject *)) \
-    1082             :     PyArray_API[171])
-    1083             : #define PyArray_Correlate \
-    1084             :         (*(PyObject * (*)(PyObject *, PyObject *, int)) \
-    1085             :     PyArray_API[172])
-    1086             : #define PyArray_TypestrConvert \
-    1087             :         (*(int (*)(int, int)) \
-    1088             :     PyArray_API[173])
-    1089             : #define PyArray_DescrConverter \
-    1090             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
-    1091             :     PyArray_API[174])
-    1092             : #define PyArray_DescrConverter2 \
-    1093             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
-    1094             :     PyArray_API[175])
-    1095             : #define PyArray_IntpConverter \
-    1096             :         (*(int (*)(PyObject *, PyArray_Dims *)) \
-    1097             :     PyArray_API[176])
-    1098             : #define PyArray_BufferConverter \
-    1099             :         (*(int (*)(PyObject *, PyArray_Chunk *)) \
-    1100             :     PyArray_API[177])
-    1101             : #define PyArray_AxisConverter \
-    1102             :         (*(int (*)(PyObject *, int *)) \
-    1103             :     PyArray_API[178])
-    1104             : #define PyArray_BoolConverter \
-    1105             :         (*(int (*)(PyObject *, npy_bool *)) \
-    1106             :     PyArray_API[179])
-    1107             : #define PyArray_ByteorderConverter \
-    1108             :         (*(int (*)(PyObject *, char *)) \
-    1109             :     PyArray_API[180])
-    1110             : #define PyArray_OrderConverter \
-    1111             :         (*(int (*)(PyObject *, NPY_ORDER *)) \
-    1112             :     PyArray_API[181])
-    1113             : #define PyArray_EquivTypes \
-    1114             :         (*(unsigned char (*)(PyArray_Descr *, PyArray_Descr *)) \
-    1115             :     PyArray_API[182])
-    1116             : #define PyArray_Zeros \
-    1117             :         (*(PyObject * (*)(int, npy_intp const *, PyArray_Descr *, int)) \
-    1118             :     PyArray_API[183])
-    1119             : #define PyArray_Empty \
-    1120             :         (*(PyObject * (*)(int, npy_intp const *, PyArray_Descr *, int)) \
-    1121             :     PyArray_API[184])
-    1122             : #define PyArray_Where \
-    1123             :         (*(PyObject * (*)(PyObject *, PyObject *, PyObject *)) \
-    1124             :     PyArray_API[185])
-    1125             : #define PyArray_Arange \
-    1126             :         (*(PyObject * (*)(double, double, double, int)) \
-    1127             :     PyArray_API[186])
-    1128             : #define PyArray_ArangeObj \
-    1129             :         (*(PyObject * (*)(PyObject *, PyObject *, PyObject *, PyArray_Descr *)) \
-    1130             :     PyArray_API[187])
-    1131             : #define PyArray_SortkindConverter \
-    1132             :         (*(int (*)(PyObject *, NPY_SORTKIND *)) \
-    1133             :     PyArray_API[188])
-    1134             : #define PyArray_LexSort \
-    1135             :         (*(PyObject * (*)(PyObject *, int)) \
-    1136             :     PyArray_API[189])
-    1137             : #define PyArray_Round \
-    1138             :         (*(PyObject * (*)(PyArrayObject *, int, PyArrayObject *)) \
-    1139             :     PyArray_API[190])
-    1140             : #define PyArray_EquivTypenums \
-    1141             :         (*(unsigned char (*)(int, int)) \
-    1142             :     PyArray_API[191])
-    1143             : #define PyArray_RegisterDataType \
-    1144             :         (*(int (*)(PyArray_Descr *)) \
-    1145             :     PyArray_API[192])
-    1146             : #define PyArray_RegisterCastFunc \
-    1147             :         (*(int (*)(PyArray_Descr *, int, PyArray_VectorUnaryFunc *)) \
-    1148             :     PyArray_API[193])
-    1149             : #define PyArray_RegisterCanCast \
-    1150             :         (*(int (*)(PyArray_Descr *, int, NPY_SCALARKIND)) \
-    1151             :     PyArray_API[194])
-    1152             : #define PyArray_InitArrFuncs \
-    1153             :         (*(void (*)(PyArray_ArrFuncs *)) \
-    1154             :     PyArray_API[195])
-    1155             : #define PyArray_IntTupleFromIntp \
-    1156             :         (*(PyObject * (*)(int, npy_intp const *)) \
-    1157             :     PyArray_API[196])
-    1158             : #define PyArray_TypeNumFromName \
-    1159             :         (*(int (*)(char const *)) \
-    1160             :     PyArray_API[197])
-    1161             : #define PyArray_ClipmodeConverter \
-    1162             :         (*(int (*)(PyObject *, NPY_CLIPMODE *)) \
-    1163             :     PyArray_API[198])
-    1164             : #define PyArray_OutputConverter \
-    1165             :         (*(int (*)(PyObject *, PyArrayObject **)) \
-    1166             :     PyArray_API[199])
-    1167             : #define PyArray_BroadcastToShape \
-    1168             :         (*(PyObject * (*)(PyObject *, npy_intp *, int)) \
-    1169             :     PyArray_API[200])
-    1170             : #define _PyArray_SigintHandler \
-    1171             :         (*(void (*)(int)) \
-    1172             :     PyArray_API[201])
-    1173             : #define _PyArray_GetSigintBuf \
-    1174             :         (*(void* (*)(void)) \
-    1175             :     PyArray_API[202])
-    1176             : #define PyArray_DescrAlignConverter \
-    1177             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
-    1178             :     PyArray_API[203])
-    1179             : #define PyArray_DescrAlignConverter2 \
-    1180             :         (*(int (*)(PyObject *, PyArray_Descr **)) \
-    1181             :     PyArray_API[204])
-    1182             : #define PyArray_SearchsideConverter \
-    1183             :         (*(int (*)(PyObject *, void *)) \
-    1184             :     PyArray_API[205])
-    1185             : #define PyArray_CheckAxis \
-    1186             :         (*(PyObject * (*)(PyArrayObject *, int *, int)) \
-    1187             :     PyArray_API[206])
-    1188             : #define PyArray_OverflowMultiplyList \
-    1189             :         (*(npy_intp (*)(npy_intp const *, int)) \
-    1190             :     PyArray_API[207])
-    1191             : #define PyArray_CompareString \
-    1192             :         (*(int (*)(const char *, const char *, size_t)) \
-    1193             :     PyArray_API[208])
-    1194             : #define PyArray_MultiIterFromObjects \
-    1195             :         (*(PyObject* (*)(PyObject **, int, int, ...)) \
-    1196             :     PyArray_API[209])
-    1197             : #define PyArray_GetEndianness \
-    1198             :         (*(int (*)(void)) \
-    1199             :     PyArray_API[210])
-    1200             : #define PyArray_GetNDArrayCFeatureVersion \
-    1201             :         (*(unsigned int (*)(void)) \
-    1202             :     PyArray_API[211])
-    1203             : #define PyArray_Correlate2 \
-    1204             :         (*(PyObject * (*)(PyObject *, PyObject *, int)) \
-    1205             :     PyArray_API[212])
-    1206             : #define PyArray_NeighborhoodIterNew \
-    1207             :         (*(PyObject* (*)(PyArrayIterObject *, const npy_intp *, int, PyArrayObject*)) \
-    1208             :     PyArray_API[213])
-    1209             : #define PyTimeIntegerArrType_Type (*(PyTypeObject *)PyArray_API[214])
-    1210             : #define PyDatetimeArrType_Type (*(PyTypeObject *)PyArray_API[215])
-    1211             : #define PyTimedeltaArrType_Type (*(PyTypeObject *)PyArray_API[216])
-    1212             : #define PyHalfArrType_Type (*(PyTypeObject *)PyArray_API[217])
-    1213             : #define NpyIter_Type (*(PyTypeObject *)PyArray_API[218])
-    1214             : #define PyArray_SetDatetimeParseFunction \
-    1215             :         (*(void (*)(PyObject *NPY_UNUSED(op))) \
-    1216             :     PyArray_API[219])
-    1217             : #define PyArray_DatetimeToDatetimeStruct \
-    1218             :         (*(void (*)(npy_datetime NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *)) \
-    1219             :     PyArray_API[220])
-    1220             : #define PyArray_TimedeltaToTimedeltaStruct \
-    1221             :         (*(void (*)(npy_timedelta NPY_UNUSED(val), NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *)) \
-    1222             :     PyArray_API[221])
-    1223             : #define PyArray_DatetimeStructToDatetime \
-    1224             :         (*(npy_datetime (*)(NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_datetimestruct *NPY_UNUSED(d))) \
-    1225             :     PyArray_API[222])
-    1226             : #define PyArray_TimedeltaStructToTimedelta \
-    1227             :         (*(npy_datetime (*)(NPY_DATETIMEUNIT NPY_UNUSED(fr), npy_timedeltastruct *NPY_UNUSED(d))) \
-    1228             :     PyArray_API[223])
-    1229             : #define NpyIter_New \
-    1230             :         (*(NpyIter * (*)(PyArrayObject *, npy_uint32, NPY_ORDER, NPY_CASTING, PyArray_Descr*)) \
-    1231             :     PyArray_API[224])
-    1232             : #define NpyIter_MultiNew \
-    1233             :         (*(NpyIter * (*)(int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **)) \
-    1234             :     PyArray_API[225])
-    1235             : #define NpyIter_AdvancedNew \
-    1236             :         (*(NpyIter * (*)(int, PyArrayObject **, npy_uint32, NPY_ORDER, NPY_CASTING, npy_uint32 *, PyArray_Descr **, int, int **, npy_intp *, npy_intp)) \
-    1237             :     PyArray_API[226])
-    1238             : #define NpyIter_Copy \
-    1239             :         (*(NpyIter * (*)(NpyIter *)) \
-    1240             :     PyArray_API[227])
-    1241             : #define NpyIter_Deallocate \
-    1242             :         (*(int (*)(NpyIter *)) \
-    1243             :     PyArray_API[228])
-    1244             : #define NpyIter_HasDelayedBufAlloc \
-    1245             :         (*(npy_bool (*)(NpyIter *)) \
-    1246             :     PyArray_API[229])
-    1247             : #define NpyIter_HasExternalLoop \
-    1248             :         (*(npy_bool (*)(NpyIter *)) \
-    1249             :     PyArray_API[230])
-    1250             : #define NpyIter_EnableExternalLoop \
-    1251             :         (*(int (*)(NpyIter *)) \
-    1252             :     PyArray_API[231])
-    1253             : #define NpyIter_GetInnerStrideArray \
-    1254             :         (*(npy_intp * (*)(NpyIter *)) \
-    1255             :     PyArray_API[232])
-    1256             : #define NpyIter_GetInnerLoopSizePtr \
-    1257             :         (*(npy_intp * (*)(NpyIter *)) \
-    1258             :     PyArray_API[233])
-    1259             : #define NpyIter_Reset \
-    1260             :         (*(int (*)(NpyIter *, char **)) \
-    1261             :     PyArray_API[234])
-    1262             : #define NpyIter_ResetBasePointers \
-    1263             :         (*(int (*)(NpyIter *, char **, char **)) \
-    1264             :     PyArray_API[235])
-    1265             : #define NpyIter_ResetToIterIndexRange \
-    1266             :         (*(int (*)(NpyIter *, npy_intp, npy_intp, char **)) \
-    1267             :     PyArray_API[236])
-    1268             : #define NpyIter_GetNDim \
-    1269             :         (*(int (*)(NpyIter *)) \
-    1270             :     PyArray_API[237])
-    1271             : #define NpyIter_GetNOp \
-    1272             :         (*(int (*)(NpyIter *)) \
-    1273             :     PyArray_API[238])
-    1274             : #define NpyIter_GetIterNext \
-    1275             :         (*(NpyIter_IterNextFunc * (*)(NpyIter *, char **)) \
-    1276             :     PyArray_API[239])
-    1277             : #define NpyIter_GetIterSize \
-    1278             :         (*(npy_intp (*)(NpyIter *)) \
-    1279             :     PyArray_API[240])
-    1280             : #define NpyIter_GetIterIndexRange \
-    1281             :         (*(void (*)(NpyIter *, npy_intp *, npy_intp *)) \
-    1282             :     PyArray_API[241])
-    1283             : #define NpyIter_GetIterIndex \
-    1284             :         (*(npy_intp (*)(NpyIter *)) \
-    1285             :     PyArray_API[242])
-    1286             : #define NpyIter_GotoIterIndex \
-    1287             :         (*(int (*)(NpyIter *, npy_intp)) \
-    1288             :     PyArray_API[243])
-    1289             : #define NpyIter_HasMultiIndex \
-    1290             :         (*(npy_bool (*)(NpyIter *)) \
-    1291             :     PyArray_API[244])
-    1292             : #define NpyIter_GetShape \
-    1293             :         (*(int (*)(NpyIter *, npy_intp *)) \
-    1294             :     PyArray_API[245])
-    1295             : #define NpyIter_GetGetMultiIndex \
-    1296             :         (*(NpyIter_GetMultiIndexFunc * (*)(NpyIter *, char **)) \
-    1297             :     PyArray_API[246])
-    1298             : #define NpyIter_GotoMultiIndex \
-    1299             :         (*(int (*)(NpyIter *, npy_intp const *)) \
-    1300             :     PyArray_API[247])
-    1301             : #define NpyIter_RemoveMultiIndex \
-    1302             :         (*(int (*)(NpyIter *)) \
-    1303             :     PyArray_API[248])
-    1304             : #define NpyIter_HasIndex \
-    1305             :         (*(npy_bool (*)(NpyIter *)) \
-    1306             :     PyArray_API[249])
-    1307             : #define NpyIter_IsBuffered \
-    1308             :         (*(npy_bool (*)(NpyIter *)) \
-    1309             :     PyArray_API[250])
-    1310             : #define NpyIter_IsGrowInner \
-    1311             :         (*(npy_bool (*)(NpyIter *)) \
-    1312             :     PyArray_API[251])
-    1313             : #define NpyIter_GetBufferSize \
-    1314             :         (*(npy_intp (*)(NpyIter *)) \
-    1315             :     PyArray_API[252])
-    1316             : #define NpyIter_GetIndexPtr \
-    1317             :         (*(npy_intp * (*)(NpyIter *)) \
-    1318             :     PyArray_API[253])
-    1319             : #define NpyIter_GotoIndex \
-    1320             :         (*(int (*)(NpyIter *, npy_intp)) \
-    1321             :     PyArray_API[254])
-    1322             : #define NpyIter_GetDataPtrArray \
-    1323             :         (*(char ** (*)(NpyIter *)) \
-    1324             :     PyArray_API[255])
-    1325             : #define NpyIter_GetDescrArray \
-    1326             :         (*(PyArray_Descr ** (*)(NpyIter *)) \
-    1327             :     PyArray_API[256])
-    1328             : #define NpyIter_GetOperandArray \
-    1329             :         (*(PyArrayObject ** (*)(NpyIter *)) \
-    1330             :     PyArray_API[257])
-    1331             : #define NpyIter_GetIterView \
-    1332             :         (*(PyArrayObject * (*)(NpyIter *, npy_intp)) \
-    1333             :     PyArray_API[258])
-    1334             : #define NpyIter_GetReadFlags \
-    1335             :         (*(void (*)(NpyIter *, char *)) \
-    1336             :     PyArray_API[259])
-    1337             : #define NpyIter_GetWriteFlags \
-    1338             :         (*(void (*)(NpyIter *, char *)) \
-    1339             :     PyArray_API[260])
-    1340             : #define NpyIter_DebugPrint \
-    1341             :         (*(void (*)(NpyIter *)) \
-    1342             :     PyArray_API[261])
-    1343             : #define NpyIter_IterationNeedsAPI \
-    1344             :         (*(npy_bool (*)(NpyIter *)) \
-    1345             :     PyArray_API[262])
-    1346             : #define NpyIter_GetInnerFixedStrideArray \
-    1347             :         (*(void (*)(NpyIter *, npy_intp *)) \
-    1348             :     PyArray_API[263])
-    1349             : #define NpyIter_RemoveAxis \
-    1350             :         (*(int (*)(NpyIter *, int)) \
-    1351             :     PyArray_API[264])
-    1352             : #define NpyIter_GetAxisStrideArray \
-    1353             :         (*(npy_intp * (*)(NpyIter *, int)) \
-    1354             :     PyArray_API[265])
-    1355             : #define NpyIter_RequiresBuffering \
-    1356             :         (*(npy_bool (*)(NpyIter *)) \
-    1357             :     PyArray_API[266])
-    1358             : #define NpyIter_GetInitialDataPtrArray \
-    1359             :         (*(char ** (*)(NpyIter *)) \
-    1360             :     PyArray_API[267])
-    1361             : #define NpyIter_CreateCompatibleStrides \
-    1362             :         (*(int (*)(NpyIter *, npy_intp, npy_intp *)) \
-    1363             :     PyArray_API[268])
-    1364             : #define PyArray_CastingConverter \
-    1365             :         (*(int (*)(PyObject *, NPY_CASTING *)) \
-    1366             :     PyArray_API[269])
-    1367             : #define PyArray_CountNonzero \
-    1368             :         (*(npy_intp (*)(PyArrayObject *)) \
-    1369             :     PyArray_API[270])
-    1370             : #define PyArray_PromoteTypes \
-    1371             :         (*(PyArray_Descr * (*)(PyArray_Descr *, PyArray_Descr *)) \
-    1372             :     PyArray_API[271])
-    1373             : #define PyArray_MinScalarType \
-    1374             :         (*(PyArray_Descr * (*)(PyArrayObject *)) \
-    1375             :     PyArray_API[272])
-    1376             : #define PyArray_ResultType \
-    1377             :         (*(PyArray_Descr * (*)(npy_intp, PyArrayObject *arrs[], npy_intp, PyArray_Descr *descrs[])) \
-    1378             :     PyArray_API[273])
-    1379             : #define PyArray_CanCastArrayTo \
-    1380             :         (*(npy_bool (*)(PyArrayObject *, PyArray_Descr *, NPY_CASTING)) \
-    1381             :     PyArray_API[274])
-    1382             : #define PyArray_CanCastTypeTo \
-    1383             :         (*(npy_bool (*)(PyArray_Descr *, PyArray_Descr *, NPY_CASTING)) \
-    1384             :     PyArray_API[275])
-    1385             : #define PyArray_EinsteinSum \
-    1386             :         (*(PyArrayObject * (*)(char *, npy_intp, PyArrayObject **, PyArray_Descr *, NPY_ORDER, NPY_CASTING, PyArrayObject *)) \
-    1387             :     PyArray_API[276])
-    1388             : #define PyArray_NewLikeArray \
-    1389             :         (*(PyObject * (*)(PyArrayObject *, NPY_ORDER, PyArray_Descr *, int)) \
-    1390             :     PyArray_API[277])
-    1391             : #define PyArray_GetArrayParamsFromObject \
-    1392             :         (*(int (*)(PyObject *NPY_UNUSED(op), PyArray_Descr *NPY_UNUSED(requested_dtype), npy_bool NPY_UNUSED(writeable), PyArray_Descr **NPY_UNUSED(out_dtype), int *NPY_UNUSED(out_ndim), npy_intp *NPY_UNUSED(out_dims), PyArrayObject **NPY_UNUSED(out_arr), PyObject *NPY_UNUSED(context))) \
-    1393             :     PyArray_API[278])
-    1394             : #define PyArray_ConvertClipmodeSequence \
-    1395             :         (*(int (*)(PyObject *, NPY_CLIPMODE *, int)) \
-    1396             :     PyArray_API[279])
-    1397             : #define PyArray_MatrixProduct2 \
-    1398             :         (*(PyObject * (*)(PyObject *, PyObject *, PyArrayObject*)) \
-    1399             :     PyArray_API[280])
-    1400             : #define NpyIter_IsFirstVisit \
-    1401             :         (*(npy_bool (*)(NpyIter *, int)) \
-    1402             :     PyArray_API[281])
-    1403             : #define PyArray_SetBaseObject \
-    1404             :         (*(int (*)(PyArrayObject *, PyObject *)) \
-    1405             :     PyArray_API[282])
-    1406             : #define PyArray_CreateSortedStridePerm \
-    1407             :         (*(void (*)(int, npy_intp const *, npy_stride_sort_item *)) \
-    1408             :     PyArray_API[283])
-    1409             : #define PyArray_RemoveAxesInPlace \
-    1410             :         (*(void (*)(PyArrayObject *, const npy_bool *)) \
-    1411             :     PyArray_API[284])
-    1412             : #define PyArray_DebugPrint \
-    1413             :         (*(void (*)(PyArrayObject *)) \
-    1414             :     PyArray_API[285])
-    1415             : #define PyArray_FailUnlessWriteable \
-    1416             :         (*(int (*)(PyArrayObject *, const char *)) \
-    1417             :     PyArray_API[286])
-    1418             : #define PyArray_SetUpdateIfCopyBase \
-    1419             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
-    1420             :     PyArray_API[287])
-    1421             : #define PyDataMem_NEW \
-    1422             :         (*(void * (*)(size_t)) \
-    1423             :     PyArray_API[288])
-    1424             : #define PyDataMem_FREE \
-    1425             :         (*(void (*)(void *)) \
-    1426             :     PyArray_API[289])
-    1427             : #define PyDataMem_RENEW \
-    1428             :         (*(void * (*)(void *, size_t)) \
-    1429             :     PyArray_API[290])
-    1430             : #define PyDataMem_SetEventHook \
-    1431             :         (*(PyDataMem_EventHookFunc * (*)(PyDataMem_EventHookFunc *, void *, void **)) \
-    1432             :     PyArray_API[291])
-    1433             : #define NPY_DEFAULT_ASSIGN_CASTING (*(NPY_CASTING *)PyArray_API[292])
-    1434             : #define PyArray_MapIterSwapAxes \
-    1435             :         (*(void (*)(PyArrayMapIterObject *, PyArrayObject **, int)) \
-    1436             :     PyArray_API[293])
-    1437             : #define PyArray_MapIterArray \
-    1438             :         (*(PyObject * (*)(PyArrayObject *, PyObject *)) \
-    1439             :     PyArray_API[294])
-    1440             : #define PyArray_MapIterNext \
-    1441             :         (*(void (*)(PyArrayMapIterObject *)) \
-    1442             :     PyArray_API[295])
-    1443             : #define PyArray_Partition \
-    1444             :         (*(int (*)(PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND)) \
-    1445             :     PyArray_API[296])
-    1446             : #define PyArray_ArgPartition \
-    1447             :         (*(PyObject * (*)(PyArrayObject *, PyArrayObject *, int, NPY_SELECTKIND)) \
-    1448             :     PyArray_API[297])
-    1449             : #define PyArray_SelectkindConverter \
-    1450             :         (*(int (*)(PyObject *, NPY_SELECTKIND *)) \
-    1451             :     PyArray_API[298])
-    1452             : #define PyDataMem_NEW_ZEROED \
-    1453             :         (*(void * (*)(size_t, size_t)) \
-    1454             :     PyArray_API[299])
-    1455             : #define PyArray_CheckAnyScalarExact \
-    1456             :         (*(int (*)(PyObject *)) \
-    1457             :     PyArray_API[300])
-    1458             : #define PyArray_MapIterArrayCopyIfOverlap \
-    1459             :         (*(PyObject * (*)(PyArrayObject *, PyObject *, int, PyArrayObject *)) \
-    1460             :     PyArray_API[301])
-    1461             : #define PyArray_ResolveWritebackIfCopy \
-    1462             :         (*(int (*)(PyArrayObject *)) \
-    1463             :     PyArray_API[302])
-    1464             : #define PyArray_SetWritebackIfCopyBase \
-    1465             :         (*(int (*)(PyArrayObject *, PyArrayObject *)) \
-    1466             :     PyArray_API[303])
-    1467             : 
-    1468             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
-    1469             : #define PyDataMem_SetHandler \
-    1470             :         (*(PyObject * (*)(PyObject *)) \
-    1471             :     PyArray_API[304])
-    1472             : #endif
-    1473             : 
-    1474             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
-    1475             : #define PyDataMem_GetHandler \
-    1476             :         (*(PyObject * (*)(void)) \
-    1477             :     PyArray_API[305])
-    1478             : #endif
-    1479             : #define PyDataMem_DefaultHandler (*(PyObject* *)PyArray_API[306])
-    1480             : 
-    1481             : #if !defined(NO_IMPORT_ARRAY) && !defined(NO_IMPORT)
-    1482             : static int
-    1483           4 : _import_array(void)
-    1484             : {
-    1485             :   int st;
-    1486           4 :   PyObject *numpy = PyImport_ImportModule("numpy.core._multiarray_umath");
-    1487             :   PyObject *c_api = NULL;
-    1488             : 
-    1489           4 :   if (numpy == NULL) {
-    1490             :       return -1;
-    1491             :   }
-    1492           4 :   c_api = PyObject_GetAttrString(numpy, "_ARRAY_API");
-    1493             :   Py_DECREF(numpy);
-    1494           4 :   if (c_api == NULL) {
-    1495             :       return -1;
-    1496             :   }
-    1497             : 
-    1498           4 :   if (!PyCapsule_CheckExact(c_api)) {
-    1499           0 :       PyErr_SetString(PyExc_RuntimeError, "_ARRAY_API is not PyCapsule object");
-    1500             :       Py_DECREF(c_api);
-    1501           0 :       return -1;
-    1502             :   }
-    1503           4 :   PyArray_API = (void **)PyCapsule_GetPointer(c_api, NULL);
-    1504             :   Py_DECREF(c_api);
-    1505           4 :   if (PyArray_API == NULL) {
-    1506           0 :       PyErr_SetString(PyExc_RuntimeError, "_ARRAY_API is NULL pointer");
-    1507           0 :       return -1;
-    1508             :   }
-    1509             : 
-    1510             :   /* Perform runtime check of C API version */
-    1511           4 :   if (NPY_VERSION != PyArray_GetNDArrayCVersion()) {
-    1512           0 :       PyErr_Format(PyExc_RuntimeError, "module compiled against "\
-    1513             :              "ABI version 0x%x but this version of numpy is 0x%x", \
-    1514           0 :              (int) NPY_VERSION, (int) PyArray_GetNDArrayCVersion());
-    1515           0 :       return -1;
-    1516             :   }
-    1517           4 :   if (NPY_FEATURE_VERSION > PyArray_GetNDArrayCFeatureVersion()) {
-    1518           0 :       PyErr_Format(PyExc_RuntimeError, "module compiled against "\
-    1519             :              "API version 0x%x but this version of numpy is 0x%x . "\
-    1520             :              "Check the section C-API incompatibility at the "\
-    1521             :              "Troubleshooting ImportError section at "\
-    1522             :              "https://numpy.org/devdocs/user/troubleshooting-importerror.html"\
-    1523             :              "#c-api-incompatibility "\
-    1524             :               "for indications on how to solve this problem .", \
-    1525           0 :              (int) NPY_FEATURE_VERSION, (int) PyArray_GetNDArrayCFeatureVersion());
-    1526           0 :       return -1;
-    1527             :   }
-    1528             : 
-    1529             :   /*
-    1530             :    * Perform runtime check of endianness and check it matches the one set by
-    1531             :    * the headers (npy_endian.h) as a safeguard
-    1532             :    */
-    1533           4 :   st = PyArray_GetEndianness();
-    1534           4 :   if (st == NPY_CPU_UNKNOWN_ENDIAN) {
-    1535           0 :       PyErr_SetString(PyExc_RuntimeError,
-    1536             :                       "FATAL: module compiled as unknown endian");
-    1537           0 :       return -1;
-    1538             :   }
-    1539             : #if NPY_BYTE_ORDER == NPY_BIG_ENDIAN
-    1540             :   if (st != NPY_CPU_BIG) {
-    1541             :       PyErr_SetString(PyExc_RuntimeError,
-    1542             :                       "FATAL: module compiled as big endian, but "
-    1543             :                       "detected different endianness at runtime");
-    1544             :       return -1;
-    1545             :   }
-    1546             : #elif NPY_BYTE_ORDER == NPY_LITTLE_ENDIAN
-    1547           4 :   if (st != NPY_CPU_LITTLE) {
-    1548           0 :       PyErr_SetString(PyExc_RuntimeError,
-    1549             :                       "FATAL: module compiled as little endian, but "
-    1550             :                       "detected different endianness at runtime");
-    1551           0 :       return -1;
-    1552             :   }
-    1553             : #endif
-    1554             : 
-    1555             :   return 0;
-    1556             : }
-    1557             : 
-    1558             : #define import_array() {if (_import_array() < 0) {PyErr_Print(); PyErr_SetString(PyExc_ImportError, "numpy.core.multiarray failed to import"); return NULL; } }
-    1559             : 
-    1560             : #define import_array1(ret) {if (_import_array() < 0) {PyErr_Print(); PyErr_SetString(PyExc_ImportError, "numpy.core.multiarray failed to import"); return ret; } }
-    1561             : 
-    1562             : #define import_array2(msg, ret) {if (_import_array() < 0) {PyErr_Print(); PyErr_SetString(PyExc_ImportError, msg); return ret; } }
-    1563             : 
-    1564             : #endif
-    1565             : 
-    1566             : #endif
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html deleted file mode 100644 index 1e4f8aa99..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __ufunc_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81650.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_import_umath4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html deleted file mode 100644 index 093ab6873..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __ufunc_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81650.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_import_umath4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html deleted file mode 100644 index da3452463..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h.gcov.html +++ /dev/null @@ -1,390 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/__ufunc_api.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - __ufunc_api.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81650.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : 
-       2             : #ifdef _UMATHMODULE
-       3             : 
-       4             : extern NPY_NO_EXPORT PyTypeObject PyUFunc_Type;
-       5             : 
-       6             : extern NPY_NO_EXPORT PyTypeObject PyUFunc_Type;
-       7             : 
-       8             : NPY_NO_EXPORT  PyObject * PyUFunc_FromFuncAndData \
-       9             :        (PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int);
-      10             : NPY_NO_EXPORT  int PyUFunc_RegisterLoopForType \
-      11             :        (PyUFuncObject *, int, PyUFuncGenericFunction, const int *, void *);
-      12             : NPY_NO_EXPORT  int PyUFunc_GenericFunction \
-      13             :        (PyUFuncObject *NPY_UNUSED(ufunc), PyObject *NPY_UNUSED(args), PyObject *NPY_UNUSED(kwds), PyArrayObject **NPY_UNUSED(op));
-      14             : NPY_NO_EXPORT  void PyUFunc_f_f_As_d_d \
-      15             :        (char **, npy_intp const *, npy_intp const *, void *);
-      16             : NPY_NO_EXPORT  void PyUFunc_d_d \
-      17             :        (char **, npy_intp const *, npy_intp const *, void *);
-      18             : NPY_NO_EXPORT  void PyUFunc_f_f \
-      19             :        (char **, npy_intp const *, npy_intp const *, void *);
-      20             : NPY_NO_EXPORT  void PyUFunc_g_g \
-      21             :        (char **, npy_intp const *, npy_intp const *, void *);
-      22             : NPY_NO_EXPORT  void PyUFunc_F_F_As_D_D \
-      23             :        (char **, npy_intp const *, npy_intp const *, void *);
-      24             : NPY_NO_EXPORT  void PyUFunc_F_F \
-      25             :        (char **, npy_intp const *, npy_intp const *, void *);
-      26             : NPY_NO_EXPORT  void PyUFunc_D_D \
-      27             :        (char **, npy_intp const *, npy_intp const *, void *);
-      28             : NPY_NO_EXPORT  void PyUFunc_G_G \
-      29             :        (char **, npy_intp const *, npy_intp const *, void *);
-      30             : NPY_NO_EXPORT  void PyUFunc_O_O \
-      31             :        (char **, npy_intp const *, npy_intp const *, void *);
-      32             : NPY_NO_EXPORT  void PyUFunc_ff_f_As_dd_d \
-      33             :        (char **, npy_intp const *, npy_intp const *, void *);
-      34             : NPY_NO_EXPORT  void PyUFunc_ff_f \
-      35             :        (char **, npy_intp const *, npy_intp const *, void *);
-      36             : NPY_NO_EXPORT  void PyUFunc_dd_d \
-      37             :        (char **, npy_intp const *, npy_intp const *, void *);
-      38             : NPY_NO_EXPORT  void PyUFunc_gg_g \
-      39             :        (char **, npy_intp const *, npy_intp const *, void *);
-      40             : NPY_NO_EXPORT  void PyUFunc_FF_F_As_DD_D \
-      41             :        (char **, npy_intp const *, npy_intp const *, void *);
-      42             : NPY_NO_EXPORT  void PyUFunc_DD_D \
-      43             :        (char **, npy_intp const *, npy_intp const *, void *);
-      44             : NPY_NO_EXPORT  void PyUFunc_FF_F \
-      45             :        (char **, npy_intp const *, npy_intp const *, void *);
-      46             : NPY_NO_EXPORT  void PyUFunc_GG_G \
-      47             :        (char **, npy_intp const *, npy_intp const *, void *);
-      48             : NPY_NO_EXPORT  void PyUFunc_OO_O \
-      49             :        (char **, npy_intp const *, npy_intp const *, void *);
-      50             : NPY_NO_EXPORT  void PyUFunc_O_O_method \
-      51             :        (char **, npy_intp const *, npy_intp const *, void *);
-      52             : NPY_NO_EXPORT  void PyUFunc_OO_O_method \
-      53             :        (char **, npy_intp const *, npy_intp const *, void *);
-      54             : NPY_NO_EXPORT  void PyUFunc_On_Om \
-      55             :        (char **, npy_intp const *, npy_intp const *, void *);
-      56             : NPY_NO_EXPORT  int PyUFunc_GetPyValues \
-      57             :        (char *, int *, int *, PyObject **);
-      58             : NPY_NO_EXPORT  int PyUFunc_checkfperr \
-      59             :        (int, PyObject *, int *);
-      60             : NPY_NO_EXPORT  void PyUFunc_clearfperr \
-      61             :        (void);
-      62             : NPY_NO_EXPORT  int PyUFunc_getfperr \
-      63             :        (void);
-      64             : NPY_NO_EXPORT  int PyUFunc_handlefperr \
-      65             :        (int, PyObject *, int, int *);
-      66             : NPY_NO_EXPORT  int PyUFunc_ReplaceLoopBySignature \
-      67             :        (PyUFuncObject *, PyUFuncGenericFunction, const int *, PyUFuncGenericFunction *);
-      68             : NPY_NO_EXPORT  PyObject * PyUFunc_FromFuncAndDataAndSignature \
-      69             :        (PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int, const char *);
-      70             : NPY_NO_EXPORT  int PyUFunc_SetUsesArraysAsData \
-      71             :        (void **NPY_UNUSED(data), size_t NPY_UNUSED(i));
-      72             : NPY_NO_EXPORT  void PyUFunc_e_e \
-      73             :        (char **, npy_intp const *, npy_intp const *, void *);
-      74             : NPY_NO_EXPORT  void PyUFunc_e_e_As_f_f \
-      75             :        (char **, npy_intp const *, npy_intp const *, void *);
-      76             : NPY_NO_EXPORT  void PyUFunc_e_e_As_d_d \
-      77             :        (char **, npy_intp const *, npy_intp const *, void *);
-      78             : NPY_NO_EXPORT  void PyUFunc_ee_e \
-      79             :        (char **, npy_intp const *, npy_intp const *, void *);
-      80             : NPY_NO_EXPORT  void PyUFunc_ee_e_As_ff_f \
-      81             :        (char **, npy_intp const *, npy_intp const *, void *);
-      82             : NPY_NO_EXPORT  void PyUFunc_ee_e_As_dd_d \
-      83             :        (char **, npy_intp const *, npy_intp const *, void *);
-      84             : NPY_NO_EXPORT  int PyUFunc_DefaultTypeResolver \
-      85             :        (PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyObject *, PyArray_Descr **);
-      86             : NPY_NO_EXPORT  int PyUFunc_ValidateCasting \
-      87             :        (PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyArray_Descr **);
-      88             : NPY_NO_EXPORT  int PyUFunc_RegisterLoopForDescr \
-      89             :        (PyUFuncObject *, PyArray_Descr *, PyUFuncGenericFunction, PyArray_Descr **, void *);
-      90             : NPY_NO_EXPORT  PyObject * PyUFunc_FromFuncAndDataAndSignatureAndIdentity \
-      91             :        (PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, const int, const char *, PyObject *);
-      92             : 
-      93             : #else
-      94             : 
-      95             : #if defined(PY_UFUNC_UNIQUE_SYMBOL)
-      96             : #define PyUFunc_API PY_UFUNC_UNIQUE_SYMBOL
-      97             : #endif
-      98             : 
-      99             : #if defined(NO_IMPORT) || defined(NO_IMPORT_UFUNC)
-     100             : extern void **PyUFunc_API;
-     101             : #else
-     102             : #if defined(PY_UFUNC_UNIQUE_SYMBOL)
-     103             : void **PyUFunc_API;
-     104             : #else
-     105             : static void **PyUFunc_API=NULL;
-     106             : #endif
-     107             : #endif
-     108             : 
-     109             : #define PyUFunc_Type (*(PyTypeObject *)PyUFunc_API[0])
-     110             : #define PyUFunc_FromFuncAndData \
-     111             :         (*(PyObject * (*)(PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int)) \
-     112             :     PyUFunc_API[1])
-     113             : #define PyUFunc_RegisterLoopForType \
-     114             :         (*(int (*)(PyUFuncObject *, int, PyUFuncGenericFunction, const int *, void *)) \
-     115             :     PyUFunc_API[2])
-     116             : #define PyUFunc_GenericFunction \
-     117             :         (*(int (*)(PyUFuncObject *NPY_UNUSED(ufunc), PyObject *NPY_UNUSED(args), PyObject *NPY_UNUSED(kwds), PyArrayObject **NPY_UNUSED(op))) \
-     118             :     PyUFunc_API[3])
-     119             : #define PyUFunc_f_f_As_d_d \
-     120             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     121             :     PyUFunc_API[4])
-     122             : #define PyUFunc_d_d \
-     123             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     124             :     PyUFunc_API[5])
-     125             : #define PyUFunc_f_f \
-     126             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     127             :     PyUFunc_API[6])
-     128             : #define PyUFunc_g_g \
-     129             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     130             :     PyUFunc_API[7])
-     131             : #define PyUFunc_F_F_As_D_D \
-     132             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     133             :     PyUFunc_API[8])
-     134             : #define PyUFunc_F_F \
-     135             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     136             :     PyUFunc_API[9])
-     137             : #define PyUFunc_D_D \
-     138             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     139             :     PyUFunc_API[10])
-     140             : #define PyUFunc_G_G \
-     141             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     142             :     PyUFunc_API[11])
-     143             : #define PyUFunc_O_O \
-     144             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     145             :     PyUFunc_API[12])
-     146             : #define PyUFunc_ff_f_As_dd_d \
-     147             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     148             :     PyUFunc_API[13])
-     149             : #define PyUFunc_ff_f \
-     150             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     151             :     PyUFunc_API[14])
-     152             : #define PyUFunc_dd_d \
-     153             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     154             :     PyUFunc_API[15])
-     155             : #define PyUFunc_gg_g \
-     156             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     157             :     PyUFunc_API[16])
-     158             : #define PyUFunc_FF_F_As_DD_D \
-     159             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     160             :     PyUFunc_API[17])
-     161             : #define PyUFunc_DD_D \
-     162             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     163             :     PyUFunc_API[18])
-     164             : #define PyUFunc_FF_F \
-     165             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     166             :     PyUFunc_API[19])
-     167             : #define PyUFunc_GG_G \
-     168             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     169             :     PyUFunc_API[20])
-     170             : #define PyUFunc_OO_O \
-     171             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     172             :     PyUFunc_API[21])
-     173             : #define PyUFunc_O_O_method \
-     174             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     175             :     PyUFunc_API[22])
-     176             : #define PyUFunc_OO_O_method \
-     177             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     178             :     PyUFunc_API[23])
-     179             : #define PyUFunc_On_Om \
-     180             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     181             :     PyUFunc_API[24])
-     182             : #define PyUFunc_GetPyValues \
-     183             :         (*(int (*)(char *, int *, int *, PyObject **)) \
-     184             :     PyUFunc_API[25])
-     185             : #define PyUFunc_checkfperr \
-     186             :         (*(int (*)(int, PyObject *, int *)) \
-     187             :     PyUFunc_API[26])
-     188             : #define PyUFunc_clearfperr \
-     189             :         (*(void (*)(void)) \
-     190             :     PyUFunc_API[27])
-     191             : #define PyUFunc_getfperr \
-     192             :         (*(int (*)(void)) \
-     193             :     PyUFunc_API[28])
-     194             : #define PyUFunc_handlefperr \
-     195             :         (*(int (*)(int, PyObject *, int, int *)) \
-     196             :     PyUFunc_API[29])
-     197             : #define PyUFunc_ReplaceLoopBySignature \
-     198             :         (*(int (*)(PyUFuncObject *, PyUFuncGenericFunction, const int *, PyUFuncGenericFunction *)) \
-     199             :     PyUFunc_API[30])
-     200             : #define PyUFunc_FromFuncAndDataAndSignature \
-     201             :         (*(PyObject * (*)(PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, int, const char *)) \
-     202             :     PyUFunc_API[31])
-     203             : #define PyUFunc_SetUsesArraysAsData \
-     204             :         (*(int (*)(void **NPY_UNUSED(data), size_t NPY_UNUSED(i))) \
-     205             :     PyUFunc_API[32])
-     206             : #define PyUFunc_e_e \
-     207             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     208             :     PyUFunc_API[33])
-     209             : #define PyUFunc_e_e_As_f_f \
-     210             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     211             :     PyUFunc_API[34])
-     212             : #define PyUFunc_e_e_As_d_d \
-     213             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     214             :     PyUFunc_API[35])
-     215             : #define PyUFunc_ee_e \
-     216             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     217             :     PyUFunc_API[36])
-     218             : #define PyUFunc_ee_e_As_ff_f \
-     219             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     220             :     PyUFunc_API[37])
-     221             : #define PyUFunc_ee_e_As_dd_d \
-     222             :         (*(void (*)(char **, npy_intp const *, npy_intp const *, void *)) \
-     223             :     PyUFunc_API[38])
-     224             : #define PyUFunc_DefaultTypeResolver \
-     225             :         (*(int (*)(PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyObject *, PyArray_Descr **)) \
-     226             :     PyUFunc_API[39])
-     227             : #define PyUFunc_ValidateCasting \
-     228             :         (*(int (*)(PyUFuncObject *, NPY_CASTING, PyArrayObject **, PyArray_Descr **)) \
-     229             :     PyUFunc_API[40])
-     230             : #define PyUFunc_RegisterLoopForDescr \
-     231             :         (*(int (*)(PyUFuncObject *, PyArray_Descr *, PyUFuncGenericFunction, PyArray_Descr **, void *)) \
-     232             :     PyUFunc_API[41])
-     233             : 
-     234             : #if NPY_FEATURE_VERSION >= NPY_1_16_API_VERSION
-     235             : #define PyUFunc_FromFuncAndDataAndSignatureAndIdentity \
-     236             :         (*(PyObject * (*)(PyUFuncGenericFunction *, void **, char *, int, int, int, int, const char *, const char *, const int, const char *, PyObject *)) \
-     237             :     PyUFunc_API[42])
-     238             : #endif
-     239             : 
-     240             : static inline int
-     241           4 : _import_umath(void)
-     242             : {
-     243           4 :   PyObject *numpy = PyImport_ImportModule("numpy.core._multiarray_umath");
-     244             :   PyObject *c_api = NULL;
-     245             : 
-     246           4 :   if (numpy == NULL) {
-     247           0 :       PyErr_SetString(PyExc_ImportError,
-     248             :                       "numpy.core._multiarray_umath failed to import");
-     249           0 :       return -1;
-     250             :   }
-     251           4 :   c_api = PyObject_GetAttrString(numpy, "_UFUNC_API");
-     252             :   Py_DECREF(numpy);
-     253           4 :   if (c_api == NULL) {
-     254           0 :       PyErr_SetString(PyExc_AttributeError, "_UFUNC_API not found");
-     255           0 :       return -1;
-     256             :   }
-     257             : 
-     258           4 :   if (!PyCapsule_CheckExact(c_api)) {
-     259           0 :       PyErr_SetString(PyExc_RuntimeError, "_UFUNC_API is not PyCapsule object");
-     260             :       Py_DECREF(c_api);
-     261           0 :       return -1;
-     262             :   }
-     263           4 :   PyUFunc_API = (void **)PyCapsule_GetPointer(c_api, NULL);
-     264             :   Py_DECREF(c_api);
-     265           4 :   if (PyUFunc_API == NULL) {
-     266           0 :       PyErr_SetString(PyExc_RuntimeError, "_UFUNC_API is NULL pointer");
-     267           0 :       return -1;
-     268             :   }
-     269             :   return 0;
-     270             : }
-     271             : 
-     272             : #define import_umath() \
-     273             :     do {\
-     274             :         UFUNC_NOFPE\
-     275             :         if (_import_umath() < 0) {\
-     276             :             PyErr_Print();\
-     277             :             PyErr_SetString(PyExc_ImportError,\
-     278             :                     "numpy.core.umath failed to import");\
-     279             :             return NULL;\
-     280             :         }\
-     281             :     } while(0)
-     282             : 
-     283             : #define import_umath1(ret) \
-     284             :     do {\
-     285             :         UFUNC_NOFPE\
-     286             :         if (_import_umath() < 0) {\
-     287             :             PyErr_Print();\
-     288             :             PyErr_SetString(PyExc_ImportError,\
-     289             :                     "numpy.core.umath failed to import");\
-     290             :             return ret;\
-     291             :         }\
-     292             :     } while(0)
-     293             : 
-     294             : #define import_umath2(ret, msg) \
-     295             :     do {\
-     296             :         UFUNC_NOFPE\
-     297             :         if (_import_umath() < 0) {\
-     298             :             PyErr_Print();\
-     299             :             PyErr_SetString(PyExc_ImportError, msg);\
-     300             :             return ret;\
-     301             :         }\
-     302             :     } while(0)
-     303             : 
-     304             : #define import_ufunc() \
-     305             :     do {\
-     306             :         UFUNC_NOFPE\
-     307             :         if (_import_umath() < 0) {\
-     308             :             PyErr_Print();\
-     309             :             PyErr_SetString(PyExc_ImportError,\
-     310             :                     "numpy.core.umath failed to import");\
-     311             :         }\
-     312             :     } while(0)
-     313             : 
-     314             : #endif
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html deleted file mode 100644 index 2686fc849..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-f.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpyHitTotalCoverage
Test:coverage.info.cleanedLines:214843.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ndarraytypes.h -
0.0%
-
0.0 %0 / 5-0 / 0
__ufunc_api.h -
50.0%50.0%
-
50.0 %8 / 16100.0 %1 / 1
__multiarray_api.h -
48.1%48.1%
-
48.1 %13 / 27100.0 %1 / 1
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html deleted file mode 100644 index 80f238d04..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index-sort-l.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpyHitTotalCoverage
Test:coverage.info.cleanedLines:214843.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ndarraytypes.h -
0.0%
-
0.0 %0 / 5-0 / 0
__multiarray_api.h -
48.1%48.1%
-
48.1 %13 / 27100.0 %1 / 1
__ufunc_api.h -
50.0%50.0%
-
50.0 %8 / 16100.0 %1 / 1
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html deleted file mode 100644 index 124271195..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/index.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpyHitTotalCoverage
Test:coverage.info.cleanedLines:214843.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
__multiarray_api.h -
48.1%48.1%
-
48.1 %13 / 27100.0 %1 / 1
__ufunc_api.h -
50.0%50.0%
-
50.0 %8 / 16100.0 %1 / 1
ndarraytypes.h -
0.0%
-
0.0 %0 / 5-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html deleted file mode 100644 index 84a09fcbb..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - ndarraytypes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html deleted file mode 100644 index ebd0e1b6a..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - ndarraytypes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html b/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html deleted file mode 100644 index c960b1d11..000000000 --- a/doc/coverageReport/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h.gcov.html +++ /dev/null @@ -1,2021 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - /home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy/ndarraytypes.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy - ndarraytypes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef NUMPY_CORE_INCLUDE_NUMPY_NDARRAYTYPES_H_
-       2             : #define NUMPY_CORE_INCLUDE_NUMPY_NDARRAYTYPES_H_
-       3             : 
-       4             : #include "npy_common.h"
-       5             : #include "npy_endian.h"
-       6             : #include "npy_cpu.h"
-       7             : #include "utils.h"
-       8             : 
-       9             : #define NPY_NO_EXPORT NPY_VISIBILITY_HIDDEN
-      10             : 
-      11             : /* Only use thread if configured in config and python supports it */
-      12             : #if defined WITH_THREAD && !NPY_NO_SMP
-      13             :         #define NPY_ALLOW_THREADS 1
-      14             : #else
-      15             :         #define NPY_ALLOW_THREADS 0
-      16             : #endif
-      17             : 
-      18             : #ifndef __has_extension
-      19             : #define __has_extension(x) 0
-      20             : #endif
-      21             : 
-      22             : #if !defined(_NPY_NO_DEPRECATIONS) && \
-      23             :     ((defined(__GNUC__)&& __GNUC__ >= 6) || \
-      24             :      __has_extension(attribute_deprecated_with_message))
-      25             : #define NPY_ATTR_DEPRECATE(text) __attribute__ ((deprecated (text)))
-      26             : #else
-      27             : #define NPY_ATTR_DEPRECATE(text)
-      28             : #endif
-      29             : 
-      30             : /*
-      31             :  * There are several places in the code where an array of dimensions
-      32             :  * is allocated statically.  This is the size of that static
-      33             :  * allocation.
-      34             :  *
-      35             :  * The array creation itself could have arbitrary dimensions but all
-      36             :  * the places where static allocation is used would need to be changed
-      37             :  * to dynamic (including inside of several structures)
-      38             :  */
-      39             : 
-      40             : #define NPY_MAXDIMS 32
-      41             : #define NPY_MAXARGS 32
-      42             : 
-      43             : /* Used for Converter Functions "O&" code in ParseTuple */
-      44             : #define NPY_FAIL 0
-      45             : #define NPY_SUCCEED 1
-      46             : 
-      47             : 
-      48             : enum NPY_TYPES {    NPY_BOOL=0,
-      49             :                     NPY_BYTE, NPY_UBYTE,
-      50             :                     NPY_SHORT, NPY_USHORT,
-      51             :                     NPY_INT, NPY_UINT,
-      52             :                     NPY_LONG, NPY_ULONG,
-      53             :                     NPY_LONGLONG, NPY_ULONGLONG,
-      54             :                     NPY_FLOAT, NPY_DOUBLE, NPY_LONGDOUBLE,
-      55             :                     NPY_CFLOAT, NPY_CDOUBLE, NPY_CLONGDOUBLE,
-      56             :                     NPY_OBJECT=17,
-      57             :                     NPY_STRING, NPY_UNICODE,
-      58             :                     NPY_VOID,
-      59             :                     /*
-      60             :                      * New 1.6 types appended, may be integrated
-      61             :                      * into the above in 2.0.
-      62             :                      */
-      63             :                     NPY_DATETIME, NPY_TIMEDELTA, NPY_HALF,
-      64             : 
-      65             :                     NPY_NTYPES,
-      66             :                     NPY_NOTYPE,
-      67             :                     NPY_CHAR NPY_ATTR_DEPRECATE("Use NPY_STRING"),
-      68             :                     NPY_USERDEF=256,  /* leave room for characters */
-      69             : 
-      70             :                     /* The number of types not including the new 1.6 types */
-      71             :                     NPY_NTYPES_ABI_COMPATIBLE=21
-      72             : };
-      73             : #if defined(_MSC_VER) && !defined(__clang__)
-      74             : #pragma deprecated(NPY_CHAR)
-      75             : #endif
-      76             : 
-      77             : /* basetype array priority */
-      78             : #define NPY_PRIORITY 0.0
-      79             : 
-      80             : /* default subtype priority */
-      81             : #define NPY_SUBTYPE_PRIORITY 1.0
-      82             : 
-      83             : /* default scalar priority */
-      84             : #define NPY_SCALAR_PRIORITY -1000000.0
-      85             : 
-      86             : /* How many floating point types are there (excluding half) */
-      87             : #define NPY_NUM_FLOATTYPE 3
-      88             : 
-      89             : /*
-      90             :  * These characters correspond to the array type and the struct
-      91             :  * module
-      92             :  */
-      93             : 
-      94             : enum NPY_TYPECHAR {
-      95             :         NPY_BOOLLTR = '?',
-      96             :         NPY_BYTELTR = 'b',
-      97             :         NPY_UBYTELTR = 'B',
-      98             :         NPY_SHORTLTR = 'h',
-      99             :         NPY_USHORTLTR = 'H',
-     100             :         NPY_INTLTR = 'i',
-     101             :         NPY_UINTLTR = 'I',
-     102             :         NPY_LONGLTR = 'l',
-     103             :         NPY_ULONGLTR = 'L',
-     104             :         NPY_LONGLONGLTR = 'q',
-     105             :         NPY_ULONGLONGLTR = 'Q',
-     106             :         NPY_HALFLTR = 'e',
-     107             :         NPY_FLOATLTR = 'f',
-     108             :         NPY_DOUBLELTR = 'd',
-     109             :         NPY_LONGDOUBLELTR = 'g',
-     110             :         NPY_CFLOATLTR = 'F',
-     111             :         NPY_CDOUBLELTR = 'D',
-     112             :         NPY_CLONGDOUBLELTR = 'G',
-     113             :         NPY_OBJECTLTR = 'O',
-     114             :         NPY_STRINGLTR = 'S',
-     115             :         NPY_STRINGLTR2 = 'a',
-     116             :         NPY_UNICODELTR = 'U',
-     117             :         NPY_VOIDLTR = 'V',
-     118             :         NPY_DATETIMELTR = 'M',
-     119             :         NPY_TIMEDELTALTR = 'm',
-     120             :         NPY_CHARLTR = 'c',
-     121             : 
-     122             :         /*
-     123             :          * No Descriptor, just a define -- this let's
-     124             :          * Python users specify an array of integers
-     125             :          * large enough to hold a pointer on the
-     126             :          * platform
-     127             :          */
-     128             :         NPY_INTPLTR = 'p',
-     129             :         NPY_UINTPLTR = 'P',
-     130             : 
-     131             :         /*
-     132             :          * These are for dtype 'kinds', not dtype 'typecodes'
-     133             :          * as the above are for.
-     134             :          */
-     135             :         NPY_GENBOOLLTR ='b',
-     136             :         NPY_SIGNEDLTR = 'i',
-     137             :         NPY_UNSIGNEDLTR = 'u',
-     138             :         NPY_FLOATINGLTR = 'f',
-     139             :         NPY_COMPLEXLTR = 'c'
-     140             : };
-     141             : 
-     142             : /*
-     143             :  * Changing this may break Numpy API compatibility
-     144             :  * due to changing offsets in PyArray_ArrFuncs, so be
-     145             :  * careful. Here we have reused the mergesort slot for
-     146             :  * any kind of stable sort, the actual implementation will
-     147             :  * depend on the data type.
-     148             :  */
-     149             : typedef enum {
-     150             :         NPY_QUICKSORT=0,
-     151             :         NPY_HEAPSORT=1,
-     152             :         NPY_MERGESORT=2,
-     153             :         NPY_STABLESORT=2,
-     154             : } NPY_SORTKIND;
-     155             : #define NPY_NSORTS (NPY_STABLESORT + 1)
-     156             : 
-     157             : 
-     158             : typedef enum {
-     159             :         NPY_INTROSELECT=0
-     160             : } NPY_SELECTKIND;
-     161             : #define NPY_NSELECTS (NPY_INTROSELECT + 1)
-     162             : 
-     163             : 
-     164             : typedef enum {
-     165             :         NPY_SEARCHLEFT=0,
-     166             :         NPY_SEARCHRIGHT=1
-     167             : } NPY_SEARCHSIDE;
-     168             : #define NPY_NSEARCHSIDES (NPY_SEARCHRIGHT + 1)
-     169             : 
-     170             : 
-     171             : typedef enum {
-     172             :         NPY_NOSCALAR=-1,
-     173             :         NPY_BOOL_SCALAR,
-     174             :         NPY_INTPOS_SCALAR,
-     175             :         NPY_INTNEG_SCALAR,
-     176             :         NPY_FLOAT_SCALAR,
-     177             :         NPY_COMPLEX_SCALAR,
-     178             :         NPY_OBJECT_SCALAR
-     179             : } NPY_SCALARKIND;
-     180             : #define NPY_NSCALARKINDS (NPY_OBJECT_SCALAR + 1)
-     181             : 
-     182             : /* For specifying array memory layout or iteration order */
-     183             : typedef enum {
-     184             :         /* Fortran order if inputs are all Fortran, C otherwise */
-     185             :         NPY_ANYORDER=-1,
-     186             :         /* C order */
-     187             :         NPY_CORDER=0,
-     188             :         /* Fortran order */
-     189             :         NPY_FORTRANORDER=1,
-     190             :         /* An order as close to the inputs as possible */
-     191             :         NPY_KEEPORDER=2
-     192             : } NPY_ORDER;
-     193             : 
-     194             : /* For specifying allowed casting in operations which support it */
-     195             : typedef enum {
-     196             :         _NPY_ERROR_OCCURRED_IN_CAST = -1,
-     197             :         /* Only allow identical types */
-     198             :         NPY_NO_CASTING=0,
-     199             :         /* Allow identical and byte swapped types */
-     200             :         NPY_EQUIV_CASTING=1,
-     201             :         /* Only allow safe casts */
-     202             :         NPY_SAFE_CASTING=2,
-     203             :         /* Allow safe casts or casts within the same kind */
-     204             :         NPY_SAME_KIND_CASTING=3,
-     205             :         /* Allow any casts */
-     206             :         NPY_UNSAFE_CASTING=4,
-     207             : } NPY_CASTING;
-     208             : 
-     209             : typedef enum {
-     210             :         NPY_CLIP=0,
-     211             :         NPY_WRAP=1,
-     212             :         NPY_RAISE=2
-     213             : } NPY_CLIPMODE;
-     214             : 
-     215             : typedef enum {
-     216             :         NPY_VALID=0,
-     217             :         NPY_SAME=1,
-     218             :         NPY_FULL=2
-     219             : } NPY_CORRELATEMODE;
-     220             : 
-     221             : /* The special not-a-time (NaT) value */
-     222             : #define NPY_DATETIME_NAT NPY_MIN_INT64
-     223             : 
-     224             : /*
-     225             :  * Upper bound on the length of a DATETIME ISO 8601 string
-     226             :  *   YEAR: 21 (64-bit year)
-     227             :  *   MONTH: 3
-     228             :  *   DAY: 3
-     229             :  *   HOURS: 3
-     230             :  *   MINUTES: 3
-     231             :  *   SECONDS: 3
-     232             :  *   ATTOSECONDS: 1 + 3*6
-     233             :  *   TIMEZONE: 5
-     234             :  *   NULL TERMINATOR: 1
-     235             :  */
-     236             : #define NPY_DATETIME_MAX_ISO8601_STRLEN (21 + 3*5 + 1 + 3*6 + 6 + 1)
-     237             : 
-     238             : /* The FR in the unit names stands for frequency */
-     239             : typedef enum {
-     240             :         /* Force signed enum type, must be -1 for code compatibility */
-     241             :         NPY_FR_ERROR = -1,      /* error or undetermined */
-     242             : 
-     243             :         /* Start of valid units */
-     244             :         NPY_FR_Y = 0,           /* Years */
-     245             :         NPY_FR_M = 1,           /* Months */
-     246             :         NPY_FR_W = 2,           /* Weeks */
-     247             :         /* Gap where 1.6 NPY_FR_B (value 3) was */
-     248             :         NPY_FR_D = 4,           /* Days */
-     249             :         NPY_FR_h = 5,           /* hours */
-     250             :         NPY_FR_m = 6,           /* minutes */
-     251             :         NPY_FR_s = 7,           /* seconds */
-     252             :         NPY_FR_ms = 8,          /* milliseconds */
-     253             :         NPY_FR_us = 9,          /* microseconds */
-     254             :         NPY_FR_ns = 10,         /* nanoseconds */
-     255             :         NPY_FR_ps = 11,         /* picoseconds */
-     256             :         NPY_FR_fs = 12,         /* femtoseconds */
-     257             :         NPY_FR_as = 13,         /* attoseconds */
-     258             :         NPY_FR_GENERIC = 14     /* unbound units, can convert to anything */
-     259             : } NPY_DATETIMEUNIT;
-     260             : 
-     261             : /*
-     262             :  * NOTE: With the NPY_FR_B gap for 1.6 ABI compatibility, NPY_DATETIME_NUMUNITS
-     263             :  * is technically one more than the actual number of units.
-     264             :  */
-     265             : #define NPY_DATETIME_NUMUNITS (NPY_FR_GENERIC + 1)
-     266             : #define NPY_DATETIME_DEFAULTUNIT NPY_FR_GENERIC
-     267             : 
-     268             : /*
-     269             :  * Business day conventions for mapping invalid business
-     270             :  * days to valid business days.
-     271             :  */
-     272             : typedef enum {
-     273             :     /* Go forward in time to the following business day. */
-     274             :     NPY_BUSDAY_FORWARD,
-     275             :     NPY_BUSDAY_FOLLOWING = NPY_BUSDAY_FORWARD,
-     276             :     /* Go backward in time to the preceding business day. */
-     277             :     NPY_BUSDAY_BACKWARD,
-     278             :     NPY_BUSDAY_PRECEDING = NPY_BUSDAY_BACKWARD,
-     279             :     /*
-     280             :      * Go forward in time to the following business day, unless it
-     281             :      * crosses a month boundary, in which case go backward
-     282             :      */
-     283             :     NPY_BUSDAY_MODIFIEDFOLLOWING,
-     284             :     /*
-     285             :      * Go backward in time to the preceding business day, unless it
-     286             :      * crosses a month boundary, in which case go forward.
-     287             :      */
-     288             :     NPY_BUSDAY_MODIFIEDPRECEDING,
-     289             :     /* Produce a NaT for non-business days. */
-     290             :     NPY_BUSDAY_NAT,
-     291             :     /* Raise an exception for non-business days. */
-     292             :     NPY_BUSDAY_RAISE
-     293             : } NPY_BUSDAY_ROLL;
-     294             : 
-     295             : /************************************************************
-     296             :  * NumPy Auxiliary Data for inner loops, sort functions, etc.
-     297             :  ************************************************************/
-     298             : 
-     299             : /*
-     300             :  * When creating an auxiliary data struct, this should always appear
-     301             :  * as the first member, like this:
-     302             :  *
-     303             :  * typedef struct {
-     304             :  *     NpyAuxData base;
-     305             :  *     double constant;
-     306             :  * } constant_multiplier_aux_data;
-     307             :  */
-     308             : typedef struct NpyAuxData_tag NpyAuxData;
-     309             : 
-     310             : /* Function pointers for freeing or cloning auxiliary data */
-     311             : typedef void (NpyAuxData_FreeFunc) (NpyAuxData *);
-     312             : typedef NpyAuxData *(NpyAuxData_CloneFunc) (NpyAuxData *);
-     313             : 
-     314             : struct NpyAuxData_tag {
-     315             :     NpyAuxData_FreeFunc *free;
-     316             :     NpyAuxData_CloneFunc *clone;
-     317             :     /* To allow for a bit of expansion without breaking the ABI */
-     318             :     void *reserved[2];
-     319             : };
-     320             : 
-     321             : /* Macros to use for freeing and cloning auxiliary data */
-     322             : #define NPY_AUXDATA_FREE(auxdata) \
-     323             :     do { \
-     324             :         if ((auxdata) != NULL) { \
-     325             :             (auxdata)->free(auxdata); \
-     326             :         } \
-     327             :     } while(0)
-     328             : #define NPY_AUXDATA_CLONE(auxdata) \
-     329             :     ((auxdata)->clone(auxdata))
-     330             : 
-     331             : #define NPY_ERR(str) fprintf(stderr, #str); fflush(stderr);
-     332             : #define NPY_ERR2(str) fprintf(stderr, str); fflush(stderr);
-     333             : 
-     334             : /*
-     335             : * Macros to define how array, and dimension/strides data is
-     336             : * allocated. These should be made private
-     337             : */
-     338             : 
-     339             : #define NPY_USE_PYMEM 1
-     340             : 
-     341             : 
-     342             : #if NPY_USE_PYMEM == 1
-     343             : /* use the Raw versions which are safe to call with the GIL released */
-     344             : #define PyArray_malloc PyMem_RawMalloc
-     345             : #define PyArray_free PyMem_RawFree
-     346             : #define PyArray_realloc PyMem_RawRealloc
-     347             : #else
-     348             : #define PyArray_malloc malloc
-     349             : #define PyArray_free free
-     350             : #define PyArray_realloc realloc
-     351             : #endif
-     352             : 
-     353             : /* Dimensions and strides */
-     354             : #define PyDimMem_NEW(size)                                         \
-     355             :     ((npy_intp *)PyArray_malloc(size*sizeof(npy_intp)))
-     356             : 
-     357             : #define PyDimMem_FREE(ptr) PyArray_free(ptr)
-     358             : 
-     359             : #define PyDimMem_RENEW(ptr,size)                                   \
-     360             :         ((npy_intp *)PyArray_realloc(ptr,size*sizeof(npy_intp)))
-     361             : 
-     362             : /* forward declaration */
-     363             : struct _PyArray_Descr;
-     364             : 
-     365             : /* These must deal with unaligned and swapped data if necessary */
-     366             : typedef PyObject * (PyArray_GetItemFunc) (void *, void *);
-     367             : typedef int (PyArray_SetItemFunc)(PyObject *, void *, void *);
-     368             : 
-     369             : typedef void (PyArray_CopySwapNFunc)(void *, npy_intp, void *, npy_intp,
-     370             :                                      npy_intp, int, void *);
-     371             : 
-     372             : typedef void (PyArray_CopySwapFunc)(void *, void *, int, void *);
-     373             : typedef npy_bool (PyArray_NonzeroFunc)(void *, void *);
-     374             : 
-     375             : 
-     376             : /*
-     377             :  * These assume aligned and notswapped data -- a buffer will be used
-     378             :  * before or contiguous data will be obtained
-     379             :  */
-     380             : 
-     381             : typedef int (PyArray_CompareFunc)(const void *, const void *, void *);
-     382             : typedef int (PyArray_ArgFunc)(void*, npy_intp, npy_intp*, void *);
-     383             : 
-     384             : typedef void (PyArray_DotFunc)(void *, npy_intp, void *, npy_intp, void *,
-     385             :                                npy_intp, void *);
-     386             : 
-     387             : typedef void (PyArray_VectorUnaryFunc)(void *, void *, npy_intp, void *,
-     388             :                                        void *);
-     389             : 
-     390             : /*
-     391             :  * XXX the ignore argument should be removed next time the API version
-     392             :  * is bumped. It used to be the separator.
-     393             :  */
-     394             : typedef int (PyArray_ScanFunc)(FILE *fp, void *dptr,
-     395             :                                char *ignore, struct _PyArray_Descr *);
-     396             : typedef int (PyArray_FromStrFunc)(char *s, void *dptr, char **endptr,
-     397             :                                   struct _PyArray_Descr *);
-     398             : 
-     399             : typedef int (PyArray_FillFunc)(void *, npy_intp, void *);
-     400             : 
-     401             : typedef int (PyArray_SortFunc)(void *, npy_intp, void *);
-     402             : typedef int (PyArray_ArgSortFunc)(void *, npy_intp *, npy_intp, void *);
-     403             : typedef int (PyArray_PartitionFunc)(void *, npy_intp, npy_intp,
-     404             :                                     npy_intp *, npy_intp *,
-     405             :                                     void *);
-     406             : typedef int (PyArray_ArgPartitionFunc)(void *, npy_intp *, npy_intp, npy_intp,
-     407             :                                        npy_intp *, npy_intp *,
-     408             :                                        void *);
-     409             : 
-     410             : typedef int (PyArray_FillWithScalarFunc)(void *, npy_intp, void *, void *);
-     411             : 
-     412             : typedef int (PyArray_ScalarKindFunc)(void *);
-     413             : 
-     414             : typedef void (PyArray_FastClipFunc)(void *in, npy_intp n_in, void *min,
-     415             :                                     void *max, void *out);
-     416             : typedef void (PyArray_FastPutmaskFunc)(void *in, void *mask, npy_intp n_in,
-     417             :                                        void *values, npy_intp nv);
-     418             : typedef int  (PyArray_FastTakeFunc)(void *dest, void *src, npy_intp *indarray,
-     419             :                                        npy_intp nindarray, npy_intp n_outer,
-     420             :                                        npy_intp m_middle, npy_intp nelem,
-     421             :                                        NPY_CLIPMODE clipmode);
-     422             : 
-     423             : typedef struct {
-     424             :         npy_intp *ptr;
-     425             :         int len;
-     426             : } PyArray_Dims;
-     427             : 
-     428             : typedef struct {
-     429             :         /*
-     430             :          * Functions to cast to most other standard types
-     431             :          * Can have some NULL entries. The types
-     432             :          * DATETIME, TIMEDELTA, and HALF go into the castdict
-     433             :          * even though they are built-in.
-     434             :          */
-     435             :         PyArray_VectorUnaryFunc *cast[NPY_NTYPES_ABI_COMPATIBLE];
-     436             : 
-     437             :         /* The next four functions *cannot* be NULL */
-     438             : 
-     439             :         /*
-     440             :          * Functions to get and set items with standard Python types
-     441             :          * -- not array scalars
-     442             :          */
-     443             :         PyArray_GetItemFunc *getitem;
-     444             :         PyArray_SetItemFunc *setitem;
-     445             : 
-     446             :         /*
-     447             :          * Copy and/or swap data.  Memory areas may not overlap
-     448             :          * Use memmove first if they might
-     449             :          */
-     450             :         PyArray_CopySwapNFunc *copyswapn;
-     451             :         PyArray_CopySwapFunc *copyswap;
-     452             : 
-     453             :         /*
-     454             :          * Function to compare items
-     455             :          * Can be NULL
-     456             :          */
-     457             :         PyArray_CompareFunc *compare;
-     458             : 
-     459             :         /*
-     460             :          * Function to select largest
-     461             :          * Can be NULL
-     462             :          */
-     463             :         PyArray_ArgFunc *argmax;
-     464             : 
-     465             :         /*
-     466             :          * Function to compute dot product
-     467             :          * Can be NULL
-     468             :          */
-     469             :         PyArray_DotFunc *dotfunc;
-     470             : 
-     471             :         /*
-     472             :          * Function to scan an ASCII file and
-     473             :          * place a single value plus possible separator
-     474             :          * Can be NULL
-     475             :          */
-     476             :         PyArray_ScanFunc *scanfunc;
-     477             : 
-     478             :         /*
-     479             :          * Function to read a single value from a string
-     480             :          * and adjust the pointer; Can be NULL
-     481             :          */
-     482             :         PyArray_FromStrFunc *fromstr;
-     483             : 
-     484             :         /*
-     485             :          * Function to determine if data is zero or not
-     486             :          * If NULL a default version is
-     487             :          * used at Registration time.
-     488             :          */
-     489             :         PyArray_NonzeroFunc *nonzero;
-     490             : 
-     491             :         /*
-     492             :          * Used for arange. Should return 0 on success
-     493             :          * and -1 on failure.
-     494             :          * Can be NULL.
-     495             :          */
-     496             :         PyArray_FillFunc *fill;
-     497             : 
-     498             :         /*
-     499             :          * Function to fill arrays with scalar values
-     500             :          * Can be NULL
-     501             :          */
-     502             :         PyArray_FillWithScalarFunc *fillwithscalar;
-     503             : 
-     504             :         /*
-     505             :          * Sorting functions
-     506             :          * Can be NULL
-     507             :          */
-     508             :         PyArray_SortFunc *sort[NPY_NSORTS];
-     509             :         PyArray_ArgSortFunc *argsort[NPY_NSORTS];
-     510             : 
-     511             :         /*
-     512             :          * Dictionary of additional casting functions
-     513             :          * PyArray_VectorUnaryFuncs
-     514             :          * which can be populated to support casting
-     515             :          * to other registered types. Can be NULL
-     516             :          */
-     517             :         PyObject *castdict;
-     518             : 
-     519             :         /*
-     520             :          * Functions useful for generalizing
-     521             :          * the casting rules.
-     522             :          * Can be NULL;
-     523             :          */
-     524             :         PyArray_ScalarKindFunc *scalarkind;
-     525             :         int **cancastscalarkindto;
-     526             :         int *cancastto;
-     527             : 
-     528             :         PyArray_FastClipFunc *fastclip;
-     529             :         PyArray_FastPutmaskFunc *fastputmask;
-     530             :         PyArray_FastTakeFunc *fasttake;
-     531             : 
-     532             :         /*
-     533             :          * Function to select smallest
-     534             :          * Can be NULL
-     535             :          */
-     536             :         PyArray_ArgFunc *argmin;
-     537             : 
-     538             : } PyArray_ArrFuncs;
-     539             : 
-     540             : /* The item must be reference counted when it is inserted or extracted. */
-     541             : #define NPY_ITEM_REFCOUNT   0x01
-     542             : /* Same as needing REFCOUNT */
-     543             : #define NPY_ITEM_HASOBJECT  0x01
-     544             : /* Convert to list for pickling */
-     545             : #define NPY_LIST_PICKLE     0x02
-     546             : /* The item is a POINTER  */
-     547             : #define NPY_ITEM_IS_POINTER 0x04
-     548             : /* memory needs to be initialized for this data-type */
-     549             : #define NPY_NEEDS_INIT      0x08
-     550             : /* operations need Python C-API so don't give-up thread. */
-     551             : #define NPY_NEEDS_PYAPI     0x10
-     552             : /* Use f.getitem when extracting elements of this data-type */
-     553             : #define NPY_USE_GETITEM     0x20
-     554             : /* Use f.setitem when setting creating 0-d array from this data-type.*/
-     555             : #define NPY_USE_SETITEM     0x40
-     556             : /* A sticky flag specifically for structured arrays */
-     557             : #define NPY_ALIGNED_STRUCT  0x80
-     558             : 
-     559             : /*
-     560             :  *These are inherited for global data-type if any data-types in the
-     561             :  * field have them
-     562             :  */
-     563             : #define NPY_FROM_FIELDS    (NPY_NEEDS_INIT | NPY_LIST_PICKLE | \
-     564             :                             NPY_ITEM_REFCOUNT | NPY_NEEDS_PYAPI)
-     565             : 
-     566             : #define NPY_OBJECT_DTYPE_FLAGS (NPY_LIST_PICKLE | NPY_USE_GETITEM | \
-     567             :                                 NPY_ITEM_IS_POINTER | NPY_ITEM_REFCOUNT | \
-     568             :                                 NPY_NEEDS_INIT | NPY_NEEDS_PYAPI)
-     569             : 
-     570             : #define PyDataType_FLAGCHK(dtype, flag) \
-     571             :         (((dtype)->flags & (flag)) == (flag))
-     572             : 
-     573             : #define PyDataType_REFCHK(dtype) \
-     574             :         PyDataType_FLAGCHK(dtype, NPY_ITEM_REFCOUNT)
-     575             : 
-     576             : typedef struct _PyArray_Descr {
-     577             :         PyObject_HEAD
-     578             :         /*
-     579             :          * the type object representing an
-     580             :          * instance of this type -- should not
-     581             :          * be two type_numbers with the same type
-     582             :          * object.
-     583             :          */
-     584             :         PyTypeObject *typeobj;
-     585             :         /* kind for this type */
-     586             :         char kind;
-     587             :         /* unique-character representing this type */
-     588             :         char type;
-     589             :         /*
-     590             :          * '>' (big), '<' (little), '|'
-     591             :          * (not-applicable), or '=' (native).
-     592             :          */
-     593             :         char byteorder;
-     594             :         /* flags describing data type */
-     595             :         char flags;
-     596             :         /* number representing this type */
-     597             :         int type_num;
-     598             :         /* element size (itemsize) for this type */
-     599             :         int elsize;
-     600             :         /* alignment needed for this type */
-     601             :         int alignment;
-     602             :         /*
-     603             :          * Non-NULL if this type is
-     604             :          * is an array (C-contiguous)
-     605             :          * of some other type
-     606             :          */
-     607             :         struct _arr_descr *subarray;
-     608             :         /*
-     609             :          * The fields dictionary for this type
-     610             :          * For statically defined descr this
-     611             :          * is always Py_None
-     612             :          */
-     613             :         PyObject *fields;
-     614             :         /*
-     615             :          * An ordered tuple of field names or NULL
-     616             :          * if no fields are defined
-     617             :          */
-     618             :         PyObject *names;
-     619             :         /*
-     620             :          * a table of functions specific for each
-     621             :          * basic data descriptor
-     622             :          */
-     623             :         PyArray_ArrFuncs *f;
-     624             :         /* Metadata about this dtype */
-     625             :         PyObject *metadata;
-     626             :         /*
-     627             :          * Metadata specific to the C implementation
-     628             :          * of the particular dtype. This was added
-     629             :          * for NumPy 1.7.0.
-     630             :          */
-     631             :         NpyAuxData *c_metadata;
-     632             :         /* Cached hash value (-1 if not yet computed).
-     633             :          * This was added for NumPy 2.0.0.
-     634             :          */
-     635             :         npy_hash_t hash;
-     636             : } PyArray_Descr;
-     637             : 
-     638             : typedef struct _arr_descr {
-     639             :         PyArray_Descr *base;
-     640             :         PyObject *shape;       /* a tuple */
-     641             : } PyArray_ArrayDescr;
-     642             : 
-     643             : /*
-     644             :  * Memory handler structure for array data.
-     645             :  */
-     646             : /* The declaration of free differs from PyMemAllocatorEx */
-     647             : typedef struct {
-     648             :     void *ctx;
-     649             :     void* (*malloc) (void *ctx, size_t size);
-     650             :     void* (*calloc) (void *ctx, size_t nelem, size_t elsize);
-     651             :     void* (*realloc) (void *ctx, void *ptr, size_t new_size);
-     652             :     void (*free) (void *ctx, void *ptr, size_t size);
-     653             :     /*
-     654             :      * This is the end of the version=1 struct. Only add new fields after
-     655             :      * this line
-     656             :      */
-     657             : } PyDataMemAllocator;
-     658             : 
-     659             : typedef struct {
-     660             :     char name[127];  /* multiple of 64 to keep the struct aligned */
-     661             :     uint8_t version; /* currently 1 */
-     662             :     PyDataMemAllocator allocator;
-     663             : } PyDataMem_Handler;
-     664             : 
-     665             : 
-     666             : /*
-     667             :  * The main array object structure.
-     668             :  *
-     669             :  * It has been recommended to use the inline functions defined below
-     670             :  * (PyArray_DATA and friends) to access fields here for a number of
-     671             :  * releases. Direct access to the members themselves is deprecated.
-     672             :  * To ensure that your code does not use deprecated access,
-     673             :  * #define NPY_NO_DEPRECATED_API NPY_1_7_API_VERSION
-     674             :  * (or NPY_1_8_API_VERSION or higher as required).
-     675             :  */
-     676             : /* This struct will be moved to a private header in a future release */
-     677             : typedef struct tagPyArrayObject_fields {
-     678             :     PyObject_HEAD
-     679             :     /* Pointer to the raw data buffer */
-     680             :     char *data;
-     681             :     /* The number of dimensions, also called 'ndim' */
-     682             :     int nd;
-     683             :     /* The size in each dimension, also called 'shape' */
-     684             :     npy_intp *dimensions;
-     685             :     /*
-     686             :      * Number of bytes to jump to get to the
-     687             :      * next element in each dimension
-     688             :      */
-     689             :     npy_intp *strides;
-     690             :     /*
-     691             :      * This object is decref'd upon
-     692             :      * deletion of array. Except in the
-     693             :      * case of WRITEBACKIFCOPY which has
-     694             :      * special handling.
-     695             :      *
-     696             :      * For views it points to the original
-     697             :      * array, collapsed so no chains of
-     698             :      * views occur.
-     699             :      *
-     700             :      * For creation from buffer object it
-     701             :      * points to an object that should be
-     702             :      * decref'd on deletion
-     703             :      *
-     704             :      * For WRITEBACKIFCOPY flag this is an
-     705             :      * array to-be-updated upon calling
-     706             :      * PyArray_ResolveWritebackIfCopy
-     707             :      */
-     708             :     PyObject *base;
-     709             :     /* Pointer to type structure */
-     710             :     PyArray_Descr *descr;
-     711             :     /* Flags describing array -- see below */
-     712             :     int flags;
-     713             :     /* For weak references */
-     714             :     PyObject *weakreflist;
-     715             : #if NPY_FEATURE_VERSION >= NPY_1_20_API_VERSION
-     716             :     void *_buffer_info;  /* private buffer info, tagged to allow warning */
-     717             : #endif
-     718             :     /*
-     719             :      * For malloc/calloc/realloc/free per object
-     720             :      */
-     721             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
-     722             :     PyObject *mem_handler;
-     723             : #endif
-     724             : } PyArrayObject_fields;
-     725             : 
-     726             : /*
-     727             :  * To hide the implementation details, we only expose
-     728             :  * the Python struct HEAD.
-     729             :  */
-     730             : #if !defined(NPY_NO_DEPRECATED_API) || \
-     731             :     (NPY_NO_DEPRECATED_API < NPY_1_7_API_VERSION)
-     732             : /*
-     733             :  * Can't put this in npy_deprecated_api.h like the others.
-     734             :  * PyArrayObject field access is deprecated as of NumPy 1.7.
-     735             :  */
-     736             : typedef PyArrayObject_fields PyArrayObject;
-     737             : #else
-     738             : typedef struct tagPyArrayObject {
-     739             :         PyObject_HEAD
-     740             : } PyArrayObject;
-     741             : #endif
-     742             : 
-     743             : /*
-     744             :  * Removed 2020-Nov-25, NumPy 1.20
-     745             :  * #define NPY_SIZEOF_PYARRAYOBJECT (sizeof(PyArrayObject_fields))
-     746             :  *
-     747             :  * The above macro was removed as it gave a false sense of a stable ABI
-     748             :  * with respect to the structures size.  If you require a runtime constant,
-     749             :  * you can use `PyArray_Type.tp_basicsize` instead.  Otherwise, please
-     750             :  * see the PyArrayObject documentation or ask the NumPy developers for
-     751             :  * information on how to correctly replace the macro in a way that is
-     752             :  * compatible with multiple NumPy versions.
-     753             :  */
-     754             : 
-     755             : 
-     756             : /* Array Flags Object */
-     757             : typedef struct PyArrayFlagsObject {
-     758             :         PyObject_HEAD
-     759             :         PyObject *arr;
-     760             :         int flags;
-     761             : } PyArrayFlagsObject;
-     762             : 
-     763             : /* Mirrors buffer object to ptr */
-     764             : 
-     765             : typedef struct {
-     766             :         PyObject_HEAD
-     767             :         PyObject *base;
-     768             :         void *ptr;
-     769             :         npy_intp len;
-     770             :         int flags;
-     771             : } PyArray_Chunk;
-     772             : 
-     773             : typedef struct {
-     774             :     NPY_DATETIMEUNIT base;
-     775             :     int num;
-     776             : } PyArray_DatetimeMetaData;
-     777             : 
-     778             : typedef struct {
-     779             :     NpyAuxData base;
-     780             :     PyArray_DatetimeMetaData meta;
-     781             : } PyArray_DatetimeDTypeMetaData;
-     782             : 
-     783             : /*
-     784             :  * This structure contains an exploded view of a date-time value.
-     785             :  * NaT is represented by year == NPY_DATETIME_NAT.
-     786             :  */
-     787             : typedef struct {
-     788             :         npy_int64 year;
-     789             :         npy_int32 month, day, hour, min, sec, us, ps, as;
-     790             : } npy_datetimestruct;
-     791             : 
-     792             : /* This is not used internally. */
-     793             : typedef struct {
-     794             :         npy_int64 day;
-     795             :         npy_int32 sec, us, ps, as;
-     796             : } npy_timedeltastruct;
-     797             : 
-     798             : typedef int (PyArray_FinalizeFunc)(PyArrayObject *, PyObject *);
-     799             : 
-     800             : /*
-     801             :  * Means c-style contiguous (last index varies the fastest). The data
-     802             :  * elements right after each other.
-     803             :  *
-     804             :  * This flag may be requested in constructor functions.
-     805             :  * This flag may be tested for in PyArray_FLAGS(arr).
-     806             :  */
-     807             : #define NPY_ARRAY_C_CONTIGUOUS    0x0001
-     808             : 
-     809             : /*
-     810             :  * Set if array is a contiguous Fortran array: the first index varies
-     811             :  * the fastest in memory (strides array is reverse of C-contiguous
-     812             :  * array)
-     813             :  *
-     814             :  * This flag may be requested in constructor functions.
-     815             :  * This flag may be tested for in PyArray_FLAGS(arr).
-     816             :  */
-     817             : #define NPY_ARRAY_F_CONTIGUOUS    0x0002
-     818             : 
-     819             : /*
-     820             :  * Note: all 0-d arrays are C_CONTIGUOUS and F_CONTIGUOUS. If a
-     821             :  * 1-d array is C_CONTIGUOUS it is also F_CONTIGUOUS. Arrays with
-     822             :  * more then one dimension can be C_CONTIGUOUS and F_CONTIGUOUS
-     823             :  * at the same time if they have either zero or one element.
-     824             :  * A higher dimensional array always has the same contiguity flags as
-     825             :  * `array.squeeze()`; dimensions with `array.shape[dimension] == 1` are
-     826             :  * effectively ignored when checking for contiguity.
-     827             :  */
-     828             : 
-     829             : /*
-     830             :  * If set, the array owns the data: it will be free'd when the array
-     831             :  * is deleted.
-     832             :  *
-     833             :  * This flag may be tested for in PyArray_FLAGS(arr).
-     834             :  */
-     835             : #define NPY_ARRAY_OWNDATA         0x0004
-     836             : 
-     837             : /*
-     838             :  * An array never has the next four set; they're only used as parameter
-     839             :  * flags to the various FromAny functions
-     840             :  *
-     841             :  * This flag may be requested in constructor functions.
-     842             :  */
-     843             : 
-     844             : /* Cause a cast to occur regardless of whether or not it is safe. */
-     845             : #define NPY_ARRAY_FORCECAST       0x0010
-     846             : 
-     847             : /*
-     848             :  * Always copy the array. Returned arrays are always CONTIGUOUS,
-     849             :  * ALIGNED, and WRITEABLE. See also: NPY_ARRAY_ENSURENOCOPY = 0x4000.
-     850             :  *
-     851             :  * This flag may be requested in constructor functions.
-     852             :  */
-     853             : #define NPY_ARRAY_ENSURECOPY      0x0020
-     854             : 
-     855             : /*
-     856             :  * Make sure the returned array is a base-class ndarray
-     857             :  *
-     858             :  * This flag may be requested in constructor functions.
-     859             :  */
-     860             : #define NPY_ARRAY_ENSUREARRAY     0x0040
-     861             : 
-     862             : /*
-     863             :  * Make sure that the strides are in units of the element size Needed
-     864             :  * for some operations with record-arrays.
-     865             :  *
-     866             :  * This flag may be requested in constructor functions.
-     867             :  */
-     868             : #define NPY_ARRAY_ELEMENTSTRIDES  0x0080
-     869             : 
-     870             : /*
-     871             :  * Array data is aligned on the appropriate memory address for the type
-     872             :  * stored according to how the compiler would align things (e.g., an
-     873             :  * array of integers (4 bytes each) starts on a memory address that's
-     874             :  * a multiple of 4)
-     875             :  *
-     876             :  * This flag may be requested in constructor functions.
-     877             :  * This flag may be tested for in PyArray_FLAGS(arr).
-     878             :  */
-     879             : #define NPY_ARRAY_ALIGNED         0x0100
-     880             : 
-     881             : /*
-     882             :  * Array data has the native endianness
-     883             :  *
-     884             :  * This flag may be requested in constructor functions.
-     885             :  */
-     886             : #define NPY_ARRAY_NOTSWAPPED      0x0200
-     887             : 
-     888             : /*
-     889             :  * Array data is writeable
-     890             :  *
-     891             :  * This flag may be requested in constructor functions.
-     892             :  * This flag may be tested for in PyArray_FLAGS(arr).
-     893             :  */
-     894             : #define NPY_ARRAY_WRITEABLE       0x0400
-     895             : 
-     896             : /*
-     897             :  * If this flag is set, then base contains a pointer to an array of
-     898             :  * the same size that should be updated with the current contents of
-     899             :  * this array when PyArray_ResolveWritebackIfCopy is called.
-     900             :  *
-     901             :  * This flag may be requested in constructor functions.
-     902             :  * This flag may be tested for in PyArray_FLAGS(arr).
-     903             :  */
-     904             : #define NPY_ARRAY_WRITEBACKIFCOPY 0x2000
-     905             : 
-     906             : /*
-     907             :  * No copy may be made while converting from an object/array (result is a view)
-     908             :  *
-     909             :  * This flag may be requested in constructor functions.
-     910             :  */
-     911             : #define NPY_ARRAY_ENSURENOCOPY 0x4000
-     912             : 
-     913             : /*
-     914             :  * NOTE: there are also internal flags defined in multiarray/arrayobject.h,
-     915             :  * which start at bit 31 and work down.
-     916             :  */
-     917             : 
-     918             : #define NPY_ARRAY_BEHAVED      (NPY_ARRAY_ALIGNED | \
-     919             :                                 NPY_ARRAY_WRITEABLE)
-     920             : #define NPY_ARRAY_BEHAVED_NS   (NPY_ARRAY_ALIGNED | \
-     921             :                                 NPY_ARRAY_WRITEABLE | \
-     922             :                                 NPY_ARRAY_NOTSWAPPED)
-     923             : #define NPY_ARRAY_CARRAY       (NPY_ARRAY_C_CONTIGUOUS | \
-     924             :                                 NPY_ARRAY_BEHAVED)
-     925             : #define NPY_ARRAY_CARRAY_RO    (NPY_ARRAY_C_CONTIGUOUS | \
-     926             :                                 NPY_ARRAY_ALIGNED)
-     927             : #define NPY_ARRAY_FARRAY       (NPY_ARRAY_F_CONTIGUOUS | \
-     928             :                                 NPY_ARRAY_BEHAVED)
-     929             : #define NPY_ARRAY_FARRAY_RO    (NPY_ARRAY_F_CONTIGUOUS | \
-     930             :                                 NPY_ARRAY_ALIGNED)
-     931             : #define NPY_ARRAY_DEFAULT      (NPY_ARRAY_CARRAY)
-     932             : #define NPY_ARRAY_IN_ARRAY     (NPY_ARRAY_CARRAY_RO)
-     933             : #define NPY_ARRAY_OUT_ARRAY    (NPY_ARRAY_CARRAY)
-     934             : #define NPY_ARRAY_INOUT_ARRAY  (NPY_ARRAY_CARRAY)
-     935             : #define NPY_ARRAY_INOUT_ARRAY2 (NPY_ARRAY_CARRAY | \
-     936             :                                 NPY_ARRAY_WRITEBACKIFCOPY)
-     937             : #define NPY_ARRAY_IN_FARRAY    (NPY_ARRAY_FARRAY_RO)
-     938             : #define NPY_ARRAY_OUT_FARRAY   (NPY_ARRAY_FARRAY)
-     939             : #define NPY_ARRAY_INOUT_FARRAY (NPY_ARRAY_FARRAY)
-     940             : #define NPY_ARRAY_INOUT_FARRAY2 (NPY_ARRAY_FARRAY | \
-     941             :                                 NPY_ARRAY_WRITEBACKIFCOPY)
-     942             : 
-     943             : #define NPY_ARRAY_UPDATE_ALL   (NPY_ARRAY_C_CONTIGUOUS | \
-     944             :                                 NPY_ARRAY_F_CONTIGUOUS | \
-     945             :                                 NPY_ARRAY_ALIGNED)
-     946             : 
-     947             : /* This flag is for the array interface, not PyArrayObject */
-     948             : #define NPY_ARR_HAS_DESCR  0x0800
-     949             : 
-     950             : 
-     951             : 
-     952             : 
-     953             : /*
-     954             :  * Size of internal buffers used for alignment Make BUFSIZE a multiple
-     955             :  * of sizeof(npy_cdouble) -- usually 16 so that ufunc buffers are aligned
-     956             :  */
-     957             : #define NPY_MIN_BUFSIZE ((int)sizeof(npy_cdouble))
-     958             : #define NPY_MAX_BUFSIZE (((int)sizeof(npy_cdouble))*1000000)
-     959             : #define NPY_BUFSIZE 8192
-     960             : /* buffer stress test size: */
-     961             : /*#define NPY_BUFSIZE 17*/
-     962             : 
-     963             : #define PyArray_MAX(a,b) (((a)>(b))?(a):(b))
-     964             : #define PyArray_MIN(a,b) (((a)<(b))?(a):(b))
-     965             : #define PyArray_CLT(p,q) ((((p).real==(q).real) ? ((p).imag < (q).imag) : \
-     966             :                                ((p).real < (q).real)))
-     967             : #define PyArray_CGT(p,q) ((((p).real==(q).real) ? ((p).imag > (q).imag) : \
-     968             :                                ((p).real > (q).real)))
-     969             : #define PyArray_CLE(p,q) ((((p).real==(q).real) ? ((p).imag <= (q).imag) : \
-     970             :                                ((p).real <= (q).real)))
-     971             : #define PyArray_CGE(p,q) ((((p).real==(q).real) ? ((p).imag >= (q).imag) : \
-     972             :                                ((p).real >= (q).real)))
-     973             : #define PyArray_CEQ(p,q) (((p).real==(q).real) && ((p).imag == (q).imag))
-     974             : #define PyArray_CNE(p,q) (((p).real!=(q).real) || ((p).imag != (q).imag))
-     975             : 
-     976             : /*
-     977             :  * C API: consists of Macros and functions.  The MACROS are defined
-     978             :  * here.
-     979             :  */
-     980             : 
-     981             : 
-     982             : #define PyArray_ISCONTIGUOUS(m) PyArray_CHKFLAGS((m), NPY_ARRAY_C_CONTIGUOUS)
-     983             : #define PyArray_ISWRITEABLE(m) PyArray_CHKFLAGS((m), NPY_ARRAY_WRITEABLE)
-     984             : #define PyArray_ISALIGNED(m) PyArray_CHKFLAGS((m), NPY_ARRAY_ALIGNED)
-     985             : 
-     986             : #define PyArray_IS_C_CONTIGUOUS(m) PyArray_CHKFLAGS((m), NPY_ARRAY_C_CONTIGUOUS)
-     987             : #define PyArray_IS_F_CONTIGUOUS(m) PyArray_CHKFLAGS((m), NPY_ARRAY_F_CONTIGUOUS)
-     988             : 
-     989             : /* the variable is used in some places, so always define it */
-     990             : #define NPY_BEGIN_THREADS_DEF PyThreadState *_save=NULL;
-     991             : #if NPY_ALLOW_THREADS
-     992             : #define NPY_BEGIN_ALLOW_THREADS Py_BEGIN_ALLOW_THREADS
-     993             : #define NPY_END_ALLOW_THREADS Py_END_ALLOW_THREADS
-     994             : #define NPY_BEGIN_THREADS do {_save = PyEval_SaveThread();} while (0);
-     995             : #define NPY_END_THREADS   do { if (_save) \
-     996             :                 { PyEval_RestoreThread(_save); _save = NULL;} } while (0);
-     997             : #define NPY_BEGIN_THREADS_THRESHOLDED(loop_size) do { if ((loop_size) > 500) \
-     998             :                 { _save = PyEval_SaveThread();} } while (0);
-     999             : 
-    1000             : #define NPY_BEGIN_THREADS_DESCR(dtype) \
-    1001             :         do {if (!(PyDataType_FLAGCHK((dtype), NPY_NEEDS_PYAPI))) \
-    1002             :                 NPY_BEGIN_THREADS;} while (0);
-    1003             : 
-    1004             : #define NPY_END_THREADS_DESCR(dtype) \
-    1005             :         do {if (!(PyDataType_FLAGCHK((dtype), NPY_NEEDS_PYAPI))) \
-    1006             :                 NPY_END_THREADS; } while (0);
-    1007             : 
-    1008             : #define NPY_ALLOW_C_API_DEF  PyGILState_STATE __save__;
-    1009             : #define NPY_ALLOW_C_API      do {__save__ = PyGILState_Ensure();} while (0);
-    1010             : #define NPY_DISABLE_C_API    do {PyGILState_Release(__save__);} while (0);
-    1011             : #else
-    1012             : #define NPY_BEGIN_ALLOW_THREADS
-    1013             : #define NPY_END_ALLOW_THREADS
-    1014             : #define NPY_BEGIN_THREADS
-    1015             : #define NPY_END_THREADS
-    1016             : #define NPY_BEGIN_THREADS_THRESHOLDED(loop_size)
-    1017             : #define NPY_BEGIN_THREADS_DESCR(dtype)
-    1018             : #define NPY_END_THREADS_DESCR(dtype)
-    1019             : #define NPY_ALLOW_C_API_DEF
-    1020             : #define NPY_ALLOW_C_API
-    1021             : #define NPY_DISABLE_C_API
-    1022             : #endif
-    1023             : 
-    1024             : /**********************************
-    1025             :  * The nditer object, added in 1.6
-    1026             :  **********************************/
-    1027             : 
-    1028             : /* The actual structure of the iterator is an internal detail */
-    1029             : typedef struct NpyIter_InternalOnly NpyIter;
-    1030             : 
-    1031             : /* Iterator function pointers that may be specialized */
-    1032             : typedef int (NpyIter_IterNextFunc)(NpyIter *iter);
-    1033             : typedef void (NpyIter_GetMultiIndexFunc)(NpyIter *iter,
-    1034             :                                       npy_intp *outcoords);
-    1035             : 
-    1036             : /*** Global flags that may be passed to the iterator constructors ***/
-    1037             : 
-    1038             : /* Track an index representing C order */
-    1039             : #define NPY_ITER_C_INDEX                    0x00000001
-    1040             : /* Track an index representing Fortran order */
-    1041             : #define NPY_ITER_F_INDEX                    0x00000002
-    1042             : /* Track a multi-index */
-    1043             : #define NPY_ITER_MULTI_INDEX                0x00000004
-    1044             : /* User code external to the iterator does the 1-dimensional innermost loop */
-    1045             : #define NPY_ITER_EXTERNAL_LOOP              0x00000008
-    1046             : /* Convert all the operands to a common data type */
-    1047             : #define NPY_ITER_COMMON_DTYPE               0x00000010
-    1048             : /* Operands may hold references, requiring API access during iteration */
-    1049             : #define NPY_ITER_REFS_OK                    0x00000020
-    1050             : /* Zero-sized operands should be permitted, iteration checks IterSize for 0 */
-    1051             : #define NPY_ITER_ZEROSIZE_OK                0x00000040
-    1052             : /* Permits reductions (size-0 stride with dimension size > 1) */
-    1053             : #define NPY_ITER_REDUCE_OK                  0x00000080
-    1054             : /* Enables sub-range iteration */
-    1055             : #define NPY_ITER_RANGED                     0x00000100
-    1056             : /* Enables buffering */
-    1057             : #define NPY_ITER_BUFFERED                   0x00000200
-    1058             : /* When buffering is enabled, grows the inner loop if possible */
-    1059             : #define NPY_ITER_GROWINNER                  0x00000400
-    1060             : /* Delay allocation of buffers until first Reset* call */
-    1061             : #define NPY_ITER_DELAY_BUFALLOC             0x00000800
-    1062             : /* When NPY_KEEPORDER is specified, disable reversing negative-stride axes */
-    1063             : #define NPY_ITER_DONT_NEGATE_STRIDES        0x00001000
-    1064             : /*
-    1065             :  * If output operands overlap with other operands (based on heuristics that
-    1066             :  * has false positives but no false negatives), make temporary copies to
-    1067             :  * eliminate overlap.
-    1068             :  */
-    1069             : #define NPY_ITER_COPY_IF_OVERLAP            0x00002000
-    1070             : 
-    1071             : /*** Per-operand flags that may be passed to the iterator constructors ***/
-    1072             : 
-    1073             : /* The operand will be read from and written to */
-    1074             : #define NPY_ITER_READWRITE                  0x00010000
-    1075             : /* The operand will only be read from */
-    1076             : #define NPY_ITER_READONLY                   0x00020000
-    1077             : /* The operand will only be written to */
-    1078             : #define NPY_ITER_WRITEONLY                  0x00040000
-    1079             : /* The operand's data must be in native byte order */
-    1080             : #define NPY_ITER_NBO                        0x00080000
-    1081             : /* The operand's data must be aligned */
-    1082             : #define NPY_ITER_ALIGNED                    0x00100000
-    1083             : /* The operand's data must be contiguous (within the inner loop) */
-    1084             : #define NPY_ITER_CONTIG                     0x00200000
-    1085             : /* The operand may be copied to satisfy requirements */
-    1086             : #define NPY_ITER_COPY                       0x00400000
-    1087             : /* The operand may be copied with WRITEBACKIFCOPY to satisfy requirements */
-    1088             : #define NPY_ITER_UPDATEIFCOPY               0x00800000
-    1089             : /* Allocate the operand if it is NULL */
-    1090             : #define NPY_ITER_ALLOCATE                   0x01000000
-    1091             : /* If an operand is allocated, don't use any subtype */
-    1092             : #define NPY_ITER_NO_SUBTYPE                 0x02000000
-    1093             : /* This is a virtual array slot, operand is NULL but temporary data is there */
-    1094             : #define NPY_ITER_VIRTUAL                    0x04000000
-    1095             : /* Require that the dimension match the iterator dimensions exactly */
-    1096             : #define NPY_ITER_NO_BROADCAST               0x08000000
-    1097             : /* A mask is being used on this array, affects buffer -> array copy */
-    1098             : #define NPY_ITER_WRITEMASKED                0x10000000
-    1099             : /* This array is the mask for all WRITEMASKED operands */
-    1100             : #define NPY_ITER_ARRAYMASK                  0x20000000
-    1101             : /* Assume iterator order data access for COPY_IF_OVERLAP */
-    1102             : #define NPY_ITER_OVERLAP_ASSUME_ELEMENTWISE 0x40000000
-    1103             : 
-    1104             : #define NPY_ITER_GLOBAL_FLAGS               0x0000ffff
-    1105             : #define NPY_ITER_PER_OP_FLAGS               0xffff0000
-    1106             : 
-    1107             : 
-    1108             : /*****************************
-    1109             :  * Basic iterator object
-    1110             :  *****************************/
-    1111             : 
-    1112             : /* FWD declaration */
-    1113             : typedef struct PyArrayIterObject_tag PyArrayIterObject;
-    1114             : 
-    1115             : /*
-    1116             :  * type of the function which translates a set of coordinates to a
-    1117             :  * pointer to the data
-    1118             :  */
-    1119             : typedef char* (*npy_iter_get_dataptr_t)(
-    1120             :         PyArrayIterObject* iter, const npy_intp*);
-    1121             : 
-    1122             : struct PyArrayIterObject_tag {
-    1123             :         PyObject_HEAD
-    1124             :         int               nd_m1;            /* number of dimensions - 1 */
-    1125             :         npy_intp          index, size;
-    1126             :         npy_intp          coordinates[NPY_MAXDIMS];/* N-dimensional loop */
-    1127             :         npy_intp          dims_m1[NPY_MAXDIMS];    /* ao->dimensions - 1 */
-    1128             :         npy_intp          strides[NPY_MAXDIMS];    /* ao->strides or fake */
-    1129             :         npy_intp          backstrides[NPY_MAXDIMS];/* how far to jump back */
-    1130             :         npy_intp          factors[NPY_MAXDIMS];     /* shape factors */
-    1131             :         PyArrayObject     *ao;
-    1132             :         char              *dataptr;        /* pointer to current item*/
-    1133             :         npy_bool          contiguous;
-    1134             : 
-    1135             :         npy_intp          bounds[NPY_MAXDIMS][2];
-    1136             :         npy_intp          limits[NPY_MAXDIMS][2];
-    1137             :         npy_intp          limits_sizes[NPY_MAXDIMS];
-    1138             :         npy_iter_get_dataptr_t translate;
-    1139             : } ;
-    1140             : 
-    1141             : 
-    1142             : /* Iterator API */
-    1143             : #define PyArrayIter_Check(op) PyObject_TypeCheck((op), &PyArrayIter_Type)
-    1144             : 
-    1145             : #define _PyAIT(it) ((PyArrayIterObject *)(it))
-    1146             : #define PyArray_ITER_RESET(it) do { \
-    1147             :         _PyAIT(it)->index = 0; \
-    1148             :         _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao); \
-    1149             :         memset(_PyAIT(it)->coordinates, 0, \
-    1150             :                (_PyAIT(it)->nd_m1+1)*sizeof(npy_intp)); \
-    1151             : } while (0)
-    1152             : 
-    1153             : #define _PyArray_ITER_NEXT1(it) do { \
-    1154             :         (it)->dataptr += _PyAIT(it)->strides[0]; \
-    1155             :         (it)->coordinates[0]++; \
-    1156             : } while (0)
-    1157             : 
-    1158             : #define _PyArray_ITER_NEXT2(it) do { \
-    1159             :         if ((it)->coordinates[1] < (it)->dims_m1[1]) { \
-    1160             :                 (it)->coordinates[1]++; \
-    1161             :                 (it)->dataptr += (it)->strides[1]; \
-    1162             :         } \
-    1163             :         else { \
-    1164             :                 (it)->coordinates[1] = 0; \
-    1165             :                 (it)->coordinates[0]++; \
-    1166             :                 (it)->dataptr += (it)->strides[0] - \
-    1167             :                         (it)->backstrides[1]; \
-    1168             :         } \
-    1169             : } while (0)
-    1170             : 
-    1171             : #define PyArray_ITER_NEXT(it) do { \
-    1172             :         _PyAIT(it)->index++; \
-    1173             :         if (_PyAIT(it)->nd_m1 == 0) { \
-    1174             :                 _PyArray_ITER_NEXT1(_PyAIT(it)); \
-    1175             :         } \
-    1176             :         else if (_PyAIT(it)->contiguous) \
-    1177             :                 _PyAIT(it)->dataptr += PyArray_DESCR(_PyAIT(it)->ao)->elsize; \
-    1178             :         else if (_PyAIT(it)->nd_m1 == 1) { \
-    1179             :                 _PyArray_ITER_NEXT2(_PyAIT(it)); \
-    1180             :         } \
-    1181             :         else { \
-    1182             :                 int __npy_i; \
-    1183             :                 for (__npy_i=_PyAIT(it)->nd_m1; __npy_i >= 0; __npy_i--) { \
-    1184             :                         if (_PyAIT(it)->coordinates[__npy_i] < \
-    1185             :                             _PyAIT(it)->dims_m1[__npy_i]) { \
-    1186             :                                 _PyAIT(it)->coordinates[__npy_i]++; \
-    1187             :                                 _PyAIT(it)->dataptr += \
-    1188             :                                         _PyAIT(it)->strides[__npy_i]; \
-    1189             :                                 break; \
-    1190             :                         } \
-    1191             :                         else { \
-    1192             :                                 _PyAIT(it)->coordinates[__npy_i] = 0; \
-    1193             :                                 _PyAIT(it)->dataptr -= \
-    1194             :                                         _PyAIT(it)->backstrides[__npy_i]; \
-    1195             :                         } \
-    1196             :                 } \
-    1197             :         } \
-    1198             : } while (0)
-    1199             : 
-    1200             : #define PyArray_ITER_GOTO(it, destination) do { \
-    1201             :         int __npy_i; \
-    1202             :         _PyAIT(it)->index = 0; \
-    1203             :         _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao); \
-    1204             :         for (__npy_i = _PyAIT(it)->nd_m1; __npy_i>=0; __npy_i--) { \
-    1205             :                 if (destination[__npy_i] < 0) { \
-    1206             :                         destination[__npy_i] += \
-    1207             :                                 _PyAIT(it)->dims_m1[__npy_i]+1; \
-    1208             :                 } \
-    1209             :                 _PyAIT(it)->dataptr += destination[__npy_i] * \
-    1210             :                         _PyAIT(it)->strides[__npy_i]; \
-    1211             :                 _PyAIT(it)->coordinates[__npy_i] = \
-    1212             :                         destination[__npy_i]; \
-    1213             :                 _PyAIT(it)->index += destination[__npy_i] * \
-    1214             :                         ( __npy_i==_PyAIT(it)->nd_m1 ? 1 : \
-    1215             :                           _PyAIT(it)->dims_m1[__npy_i+1]+1) ; \
-    1216             :         } \
-    1217             : } while (0)
-    1218             : 
-    1219             : #define PyArray_ITER_GOTO1D(it, ind) do { \
-    1220             :         int __npy_i; \
-    1221             :         npy_intp __npy_ind = (npy_intp)(ind); \
-    1222             :         if (__npy_ind < 0) __npy_ind += _PyAIT(it)->size; \
-    1223             :         _PyAIT(it)->index = __npy_ind; \
-    1224             :         if (_PyAIT(it)->nd_m1 == 0) { \
-    1225             :                 _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao) + \
-    1226             :                         __npy_ind * _PyAIT(it)->strides[0]; \
-    1227             :         } \
-    1228             :         else if (_PyAIT(it)->contiguous) \
-    1229             :                 _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao) + \
-    1230             :                         __npy_ind * PyArray_DESCR(_PyAIT(it)->ao)->elsize; \
-    1231             :         else { \
-    1232             :                 _PyAIT(it)->dataptr = PyArray_BYTES(_PyAIT(it)->ao); \
-    1233             :                 for (__npy_i = 0; __npy_i<=_PyAIT(it)->nd_m1; \
-    1234             :                      __npy_i++) { \
-    1235             :                         _PyAIT(it)->coordinates[__npy_i] = \
-    1236             :                                 (__npy_ind / _PyAIT(it)->factors[__npy_i]); \
-    1237             :                         _PyAIT(it)->dataptr += \
-    1238             :                                 (__npy_ind / _PyAIT(it)->factors[__npy_i]) \
-    1239             :                                 * _PyAIT(it)->strides[__npy_i]; \
-    1240             :                         __npy_ind %= _PyAIT(it)->factors[__npy_i]; \
-    1241             :                 } \
-    1242             :         } \
-    1243             : } while (0)
-    1244             : 
-    1245             : #define PyArray_ITER_DATA(it) ((void *)(_PyAIT(it)->dataptr))
-    1246             : 
-    1247             : #define PyArray_ITER_NOTDONE(it) (_PyAIT(it)->index < _PyAIT(it)->size)
-    1248             : 
-    1249             : 
-    1250             : /*
-    1251             :  * Any object passed to PyArray_Broadcast must be binary compatible
-    1252             :  * with this structure.
-    1253             :  */
-    1254             : 
-    1255             : typedef struct {
-    1256             :         PyObject_HEAD
-    1257             :         int                  numiter;                 /* number of iters */
-    1258             :         npy_intp             size;                    /* broadcasted size */
-    1259             :         npy_intp             index;                   /* current index */
-    1260             :         int                  nd;                      /* number of dims */
-    1261             :         npy_intp             dimensions[NPY_MAXDIMS]; /* dimensions */
-    1262             :         PyArrayIterObject    *iters[NPY_MAXARGS];     /* iterators */
-    1263             : } PyArrayMultiIterObject;
-    1264             : 
-    1265             : #define _PyMIT(m) ((PyArrayMultiIterObject *)(m))
-    1266             : #define PyArray_MultiIter_RESET(multi) do {                                   \
-    1267             :         int __npy_mi;                                                         \
-    1268             :         _PyMIT(multi)->index = 0;                                             \
-    1269             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter;  __npy_mi++) {    \
-    1270             :                 PyArray_ITER_RESET(_PyMIT(multi)->iters[__npy_mi]);           \
-    1271             :         }                                                                     \
-    1272             : } while (0)
-    1273             : 
-    1274             : #define PyArray_MultiIter_NEXT(multi) do {                                    \
-    1275             :         int __npy_mi;                                                         \
-    1276             :         _PyMIT(multi)->index++;                                               \
-    1277             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter;   __npy_mi++) {   \
-    1278             :                 PyArray_ITER_NEXT(_PyMIT(multi)->iters[__npy_mi]);            \
-    1279             :         }                                                                     \
-    1280             : } while (0)
-    1281             : 
-    1282             : #define PyArray_MultiIter_GOTO(multi, dest) do {                            \
-    1283             :         int __npy_mi;                                                       \
-    1284             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter; __npy_mi++) {   \
-    1285             :                 PyArray_ITER_GOTO(_PyMIT(multi)->iters[__npy_mi], dest);    \
-    1286             :         }                                                                   \
-    1287             :         _PyMIT(multi)->index = _PyMIT(multi)->iters[0]->index;              \
-    1288             : } while (0)
-    1289             : 
-    1290             : #define PyArray_MultiIter_GOTO1D(multi, ind) do {                          \
-    1291             :         int __npy_mi;                                                      \
-    1292             :         for (__npy_mi=0; __npy_mi < _PyMIT(multi)->numiter; __npy_mi++) {  \
-    1293             :                 PyArray_ITER_GOTO1D(_PyMIT(multi)->iters[__npy_mi], ind);  \
-    1294             :         }                                                                  \
-    1295             :         _PyMIT(multi)->index = _PyMIT(multi)->iters[0]->index;             \
-    1296             : } while (0)
-    1297             : 
-    1298             : #define PyArray_MultiIter_DATA(multi, i)                \
-    1299             :         ((void *)(_PyMIT(multi)->iters[i]->dataptr))
-    1300             : 
-    1301             : #define PyArray_MultiIter_NEXTi(multi, i)               \
-    1302             :         PyArray_ITER_NEXT(_PyMIT(multi)->iters[i])
-    1303             : 
-    1304             : #define PyArray_MultiIter_NOTDONE(multi)                \
-    1305             :         (_PyMIT(multi)->index < _PyMIT(multi)->size)
-    1306             : 
-    1307             : /*
-    1308             :  * Store the information needed for fancy-indexing over an array. The
-    1309             :  * fields are slightly unordered to keep consec, dataptr and subspace
-    1310             :  * where they were originally.
-    1311             :  */
-    1312             : typedef struct {
-    1313             :         PyObject_HEAD
-    1314             :         /*
-    1315             :          * Multi-iterator portion --- needs to be present in this
-    1316             :          * order to work with PyArray_Broadcast
-    1317             :          */
-    1318             : 
-    1319             :         int                   numiter;                 /* number of index-array
-    1320             :                                                           iterators */
-    1321             :         npy_intp              size;                    /* size of broadcasted
-    1322             :                                                           result */
-    1323             :         npy_intp              index;                   /* current index */
-    1324             :         int                   nd;                      /* number of dims */
-    1325             :         npy_intp              dimensions[NPY_MAXDIMS]; /* dimensions */
-    1326             :         NpyIter               *outer;                  /* index objects
-    1327             :                                                           iterator */
-    1328             :         void                  *unused[NPY_MAXDIMS - 2];
-    1329             :         PyArrayObject         *array;
-    1330             :         /* Flat iterator for the indexed array. For compatibility solely. */
-    1331             :         PyArrayIterObject     *ait;
-    1332             : 
-    1333             :         /*
-    1334             :          * Subspace array. For binary compatibility (was an iterator,
-    1335             :          * but only the check for NULL should be used).
-    1336             :          */
-    1337             :         PyArrayObject         *subspace;
-    1338             : 
-    1339             :         /*
-    1340             :          * if subspace iteration, then this is the array of axes in
-    1341             :          * the underlying array represented by the index objects
-    1342             :          */
-    1343             :         int                   iteraxes[NPY_MAXDIMS];
-    1344             :         npy_intp              fancy_strides[NPY_MAXDIMS];
-    1345             : 
-    1346             :         /* pointer when all fancy indices are 0 */
-    1347             :         char                  *baseoffset;
-    1348             : 
-    1349             :         /*
-    1350             :          * after binding consec denotes at which axis the fancy axes
-    1351             :          * are inserted.
-    1352             :          */
-    1353             :         int                   consec;
-    1354             :         char                  *dataptr;
-    1355             : 
-    1356             :         int                   nd_fancy;
-    1357             :         npy_intp              fancy_dims[NPY_MAXDIMS];
-    1358             : 
-    1359             :         /*
-    1360             :          * Whether the iterator (any of the iterators) requires API.  This is
-    1361             :          * unused by NumPy itself; ArrayMethod flags are more precise.
-    1362             :          */
-    1363             :         int                   needs_api;
-    1364             : 
-    1365             :         /*
-    1366             :          * Extra op information.
-    1367             :          */
-    1368             :         PyArrayObject         *extra_op;
-    1369             :         PyArray_Descr         *extra_op_dtype;         /* desired dtype */
-    1370             :         npy_uint32            *extra_op_flags;         /* Iterator flags */
-    1371             : 
-    1372             :         NpyIter               *extra_op_iter;
-    1373             :         NpyIter_IterNextFunc  *extra_op_next;
-    1374             :         char                  **extra_op_ptrs;
-    1375             : 
-    1376             :         /*
-    1377             :          * Information about the iteration state.
-    1378             :          */
-    1379             :         NpyIter_IterNextFunc  *outer_next;
-    1380             :         char                  **outer_ptrs;
-    1381             :         npy_intp              *outer_strides;
-    1382             : 
-    1383             :         /*
-    1384             :          * Information about the subspace iterator.
-    1385             :          */
-    1386             :         NpyIter               *subspace_iter;
-    1387             :         NpyIter_IterNextFunc  *subspace_next;
-    1388             :         char                  **subspace_ptrs;
-    1389             :         npy_intp              *subspace_strides;
-    1390             : 
-    1391             :         /* Count for the external loop (which ever it is) for API iteration */
-    1392             :         npy_intp              iter_count;
-    1393             : 
-    1394             : } PyArrayMapIterObject;
-    1395             : 
-    1396             : enum {
-    1397             :     NPY_NEIGHBORHOOD_ITER_ZERO_PADDING,
-    1398             :     NPY_NEIGHBORHOOD_ITER_ONE_PADDING,
-    1399             :     NPY_NEIGHBORHOOD_ITER_CONSTANT_PADDING,
-    1400             :     NPY_NEIGHBORHOOD_ITER_CIRCULAR_PADDING,
-    1401             :     NPY_NEIGHBORHOOD_ITER_MIRROR_PADDING
-    1402             : };
-    1403             : 
-    1404             : typedef struct {
-    1405             :     PyObject_HEAD
-    1406             : 
-    1407             :     /*
-    1408             :      * PyArrayIterObject part: keep this in this exact order
-    1409             :      */
-    1410             :     int               nd_m1;            /* number of dimensions - 1 */
-    1411             :     npy_intp          index, size;
-    1412             :     npy_intp          coordinates[NPY_MAXDIMS];/* N-dimensional loop */
-    1413             :     npy_intp          dims_m1[NPY_MAXDIMS];    /* ao->dimensions - 1 */
-    1414             :     npy_intp          strides[NPY_MAXDIMS];    /* ao->strides or fake */
-    1415             :     npy_intp          backstrides[NPY_MAXDIMS];/* how far to jump back */
-    1416             :     npy_intp          factors[NPY_MAXDIMS];     /* shape factors */
-    1417             :     PyArrayObject     *ao;
-    1418             :     char              *dataptr;        /* pointer to current item*/
-    1419             :     npy_bool          contiguous;
-    1420             : 
-    1421             :     npy_intp          bounds[NPY_MAXDIMS][2];
-    1422             :     npy_intp          limits[NPY_MAXDIMS][2];
-    1423             :     npy_intp          limits_sizes[NPY_MAXDIMS];
-    1424             :     npy_iter_get_dataptr_t translate;
-    1425             : 
-    1426             :     /*
-    1427             :      * New members
-    1428             :      */
-    1429             :     npy_intp nd;
-    1430             : 
-    1431             :     /* Dimensions is the dimension of the array */
-    1432             :     npy_intp dimensions[NPY_MAXDIMS];
-    1433             : 
-    1434             :     /*
-    1435             :      * Neighborhood points coordinates are computed relatively to the
-    1436             :      * point pointed by _internal_iter
-    1437             :      */
-    1438             :     PyArrayIterObject* _internal_iter;
-    1439             :     /*
-    1440             :      * To keep a reference to the representation of the constant value
-    1441             :      * for constant padding
-    1442             :      */
-    1443             :     char* constant;
-    1444             : 
-    1445             :     int mode;
-    1446             : } PyArrayNeighborhoodIterObject;
-    1447             : 
-    1448             : /*
-    1449             :  * Neighborhood iterator API
-    1450             :  */
-    1451             : 
-    1452             : /* General: those work for any mode */
-    1453             : static inline int
-    1454             : PyArrayNeighborhoodIter_Reset(PyArrayNeighborhoodIterObject* iter);
-    1455             : static inline int
-    1456             : PyArrayNeighborhoodIter_Next(PyArrayNeighborhoodIterObject* iter);
-    1457             : #if 0
-    1458             : static inline int
-    1459             : PyArrayNeighborhoodIter_Next2D(PyArrayNeighborhoodIterObject* iter);
-    1460             : #endif
-    1461             : 
-    1462             : /*
-    1463             :  * Include inline implementations - functions defined there are not
-    1464             :  * considered public API
-    1465             :  */
-    1466             : #define NUMPY_CORE_INCLUDE_NUMPY__NEIGHBORHOOD_IMP_H_
-    1467             : #include "_neighborhood_iterator_imp.h"
-    1468             : #undef NUMPY_CORE_INCLUDE_NUMPY__NEIGHBORHOOD_IMP_H_
-    1469             : 
-    1470             : 
-    1471             : 
-    1472             : /* The default array type */
-    1473             : #define NPY_DEFAULT_TYPE NPY_DOUBLE
-    1474             : 
-    1475             : /*
-    1476             :  * All sorts of useful ways to look into a PyArrayObject. It is recommended
-    1477             :  * to use PyArrayObject * objects instead of always casting from PyObject *,
-    1478             :  * for improved type checking.
-    1479             :  *
-    1480             :  * In many cases here the macro versions of the accessors are deprecated,
-    1481             :  * but can't be immediately changed to inline functions because the
-    1482             :  * preexisting macros accept PyObject * and do automatic casts. Inline
-    1483             :  * functions accepting PyArrayObject * provides for some compile-time
-    1484             :  * checking of correctness when working with these objects in C.
-    1485             :  */
-    1486             : 
-    1487             : #define PyArray_ISONESEGMENT(m) (PyArray_CHKFLAGS(m, NPY_ARRAY_C_CONTIGUOUS) || \
-    1488             :                                  PyArray_CHKFLAGS(m, NPY_ARRAY_F_CONTIGUOUS))
-    1489             : 
-    1490             : #define PyArray_ISFORTRAN(m) (PyArray_CHKFLAGS(m, NPY_ARRAY_F_CONTIGUOUS) && \
-    1491             :                              (!PyArray_CHKFLAGS(m, NPY_ARRAY_C_CONTIGUOUS)))
-    1492             : 
-    1493             : #define PyArray_FORTRAN_IF(m) ((PyArray_CHKFLAGS(m, NPY_ARRAY_F_CONTIGUOUS) ? \
-    1494             :                                NPY_ARRAY_F_CONTIGUOUS : 0))
-    1495             : 
-    1496             : #if (defined(NPY_NO_DEPRECATED_API) && (NPY_1_7_API_VERSION <= NPY_NO_DEPRECATED_API))
-    1497             : /*
-    1498             :  * Changing access macros into functions, to allow for future hiding
-    1499             :  * of the internal memory layout. This later hiding will allow the 2.x series
-    1500             :  * to change the internal representation of arrays without affecting
-    1501             :  * ABI compatibility.
-    1502             :  */
-    1503             : 
-    1504             : static inline int
-    1505             : PyArray_NDIM(const PyArrayObject *arr)
-    1506             : {
-    1507             :     return ((PyArrayObject_fields *)arr)->nd;
-    1508             : }
-    1509             : 
-    1510             : static inline void *
-    1511             : PyArray_DATA(PyArrayObject *arr)
-    1512             : {
-    1513           0 :     return ((PyArrayObject_fields *)arr)->data;
-    1514             : }
-    1515             : 
-    1516             : static inline char *
-    1517             : PyArray_BYTES(PyArrayObject *arr)
-    1518             : {
-    1519             :     return ((PyArrayObject_fields *)arr)->data;
-    1520             : }
-    1521             : 
-    1522             : static inline npy_intp *
-    1523             : PyArray_DIMS(PyArrayObject *arr)
-    1524             : {
-    1525           0 :     return ((PyArrayObject_fields *)arr)->dimensions;
-    1526             : }
-    1527             : 
-    1528             : static inline npy_intp *
-    1529             : PyArray_STRIDES(PyArrayObject *arr)
-    1530             : {
-    1531             :     return ((PyArrayObject_fields *)arr)->strides;
-    1532             : }
-    1533             : 
-    1534             : static inline npy_intp
-    1535             : PyArray_DIM(const PyArrayObject *arr, int idim)
-    1536             : {
-    1537             :     return ((PyArrayObject_fields *)arr)->dimensions[idim];
-    1538             : }
-    1539             : 
-    1540             : static inline npy_intp
-    1541             : PyArray_STRIDE(const PyArrayObject *arr, int istride)
-    1542             : {
-    1543             :     return ((PyArrayObject_fields *)arr)->strides[istride];
-    1544             : }
-    1545             : 
-    1546             : static inline NPY_RETURNS_BORROWED_REF PyObject *
-    1547             : PyArray_BASE(PyArrayObject *arr)
-    1548             : {
-    1549             :     return ((PyArrayObject_fields *)arr)->base;
-    1550             : }
-    1551             : 
-    1552             : static inline NPY_RETURNS_BORROWED_REF PyArray_Descr *
-    1553             : PyArray_DESCR(PyArrayObject *arr)
-    1554             : {
-    1555             :     return ((PyArrayObject_fields *)arr)->descr;
-    1556             : }
-    1557             : 
-    1558             : static inline int
-    1559             : PyArray_FLAGS(const PyArrayObject *arr)
-    1560             : {
-    1561           0 :     return ((PyArrayObject_fields *)arr)->flags;
-    1562             : }
-    1563             : 
-    1564             : static inline npy_intp
-    1565             : PyArray_ITEMSIZE(const PyArrayObject *arr)
-    1566             : {
-    1567             :     return ((PyArrayObject_fields *)arr)->descr->elsize;
-    1568             : }
-    1569             : 
-    1570             : static inline int
-    1571             : PyArray_TYPE(const PyArrayObject *arr)
-    1572             : {
-    1573           0 :     return ((PyArrayObject_fields *)arr)->descr->type_num;
-    1574             : }
-    1575             : 
-    1576             : static inline int
-    1577             : PyArray_CHKFLAGS(const PyArrayObject *arr, int flags)
-    1578             : {
-    1579           0 :     return (PyArray_FLAGS(arr) & flags) == flags;
-    1580             : }
-    1581             : 
-    1582             : static inline PyObject *
-    1583             : PyArray_GETITEM(const PyArrayObject *arr, const char *itemptr)
-    1584             : {
-    1585             :     return ((PyArrayObject_fields *)arr)->descr->f->getitem(
-    1586             :                                         (void *)itemptr, (PyArrayObject *)arr);
-    1587             : }
-    1588             : 
-    1589             : /*
-    1590             :  * SETITEM should only be used if it is known that the value is a scalar
-    1591             :  * and of a type understood by the arrays dtype.
-    1592             :  * Use `PyArray_Pack` if the value may be of a different dtype.
-    1593             :  */
-    1594             : static inline int
-    1595             : PyArray_SETITEM(PyArrayObject *arr, char *itemptr, PyObject *v)
-    1596             : {
-    1597             :     return ((PyArrayObject_fields *)arr)->descr->f->setitem(v, itemptr, arr);
-    1598             : }
-    1599             : 
-    1600             : #else
-    1601             : 
-    1602             : /* These macros are deprecated as of NumPy 1.7. */
-    1603             : #define PyArray_NDIM(obj) (((PyArrayObject_fields *)(obj))->nd)
-    1604             : #define PyArray_BYTES(obj) (((PyArrayObject_fields *)(obj))->data)
-    1605             : #define PyArray_DATA(obj) ((void *)((PyArrayObject_fields *)(obj))->data)
-    1606             : #define PyArray_DIMS(obj) (((PyArrayObject_fields *)(obj))->dimensions)
-    1607             : #define PyArray_STRIDES(obj) (((PyArrayObject_fields *)(obj))->strides)
-    1608             : #define PyArray_DIM(obj,n) (PyArray_DIMS(obj)[n])
-    1609             : #define PyArray_STRIDE(obj,n) (PyArray_STRIDES(obj)[n])
-    1610             : #define PyArray_BASE(obj) (((PyArrayObject_fields *)(obj))->base)
-    1611             : #define PyArray_DESCR(obj) (((PyArrayObject_fields *)(obj))->descr)
-    1612             : #define PyArray_FLAGS(obj) (((PyArrayObject_fields *)(obj))->flags)
-    1613             : #define PyArray_CHKFLAGS(m, FLAGS) \
-    1614             :         ((((PyArrayObject_fields *)(m))->flags & (FLAGS)) == (FLAGS))
-    1615             : #define PyArray_ITEMSIZE(obj) \
-    1616             :                     (((PyArrayObject_fields *)(obj))->descr->elsize)
-    1617             : #define PyArray_TYPE(obj) \
-    1618             :                     (((PyArrayObject_fields *)(obj))->descr->type_num)
-    1619             : #define PyArray_GETITEM(obj,itemptr) \
-    1620             :         PyArray_DESCR(obj)->f->getitem((char *)(itemptr), \
-    1621             :                                      (PyArrayObject *)(obj))
-    1622             : 
-    1623             : #define PyArray_SETITEM(obj,itemptr,v) \
-    1624             :         PyArray_DESCR(obj)->f->setitem((PyObject *)(v), \
-    1625             :                                      (char *)(itemptr), \
-    1626             :                                      (PyArrayObject *)(obj))
-    1627             : #endif
-    1628             : 
-    1629             : static inline PyArray_Descr *
-    1630             : PyArray_DTYPE(PyArrayObject *arr)
-    1631             : {
-    1632             :     return ((PyArrayObject_fields *)arr)->descr;
-    1633             : }
-    1634             : 
-    1635             : static inline npy_intp *
-    1636             : PyArray_SHAPE(PyArrayObject *arr)
-    1637             : {
-    1638             :     return ((PyArrayObject_fields *)arr)->dimensions;
-    1639             : }
-    1640             : 
-    1641             : /*
-    1642             :  * Enables the specified array flags. Does no checking,
-    1643             :  * assumes you know what you're doing.
-    1644             :  */
-    1645             : static inline void
-    1646             : PyArray_ENABLEFLAGS(PyArrayObject *arr, int flags)
-    1647             : {
-    1648             :     ((PyArrayObject_fields *)arr)->flags |= flags;
-    1649             : }
-    1650             : 
-    1651             : /*
-    1652             :  * Clears the specified array flags. Does no checking,
-    1653             :  * assumes you know what you're doing.
-    1654             :  */
-    1655             : static inline void
-    1656             : PyArray_CLEARFLAGS(PyArrayObject *arr, int flags)
-    1657             : {
-    1658             :     ((PyArrayObject_fields *)arr)->flags &= ~flags;
-    1659             : }
-    1660             : 
-    1661             : #if NPY_FEATURE_VERSION >= NPY_1_22_API_VERSION
-    1662             :     static inline NPY_RETURNS_BORROWED_REF PyObject *
-    1663             :     PyArray_HANDLER(PyArrayObject *arr)
-    1664             :     {
-    1665             :         return ((PyArrayObject_fields *)arr)->mem_handler;
-    1666             :     }
-    1667             : #endif
-    1668             : 
-    1669             : #define PyTypeNum_ISBOOL(type) ((type) == NPY_BOOL)
-    1670             : 
-    1671             : #define PyTypeNum_ISUNSIGNED(type) (((type) == NPY_UBYTE) ||   \
-    1672             :                                  ((type) == NPY_USHORT) ||     \
-    1673             :                                  ((type) == NPY_UINT) ||       \
-    1674             :                                  ((type) == NPY_ULONG) ||      \
-    1675             :                                  ((type) == NPY_ULONGLONG))
-    1676             : 
-    1677             : #define PyTypeNum_ISSIGNED(type) (((type) == NPY_BYTE) ||      \
-    1678             :                                ((type) == NPY_SHORT) ||        \
-    1679             :                                ((type) == NPY_INT) ||          \
-    1680             :                                ((type) == NPY_LONG) ||         \
-    1681             :                                ((type) == NPY_LONGLONG))
-    1682             : 
-    1683             : #define PyTypeNum_ISINTEGER(type) (((type) >= NPY_BYTE) &&     \
-    1684             :                                 ((type) <= NPY_ULONGLONG))
-    1685             : 
-    1686             : #define PyTypeNum_ISFLOAT(type) ((((type) >= NPY_FLOAT) && \
-    1687             :                               ((type) <= NPY_LONGDOUBLE)) || \
-    1688             :                               ((type) == NPY_HALF))
-    1689             : 
-    1690             : #define PyTypeNum_ISNUMBER(type) (((type) <= NPY_CLONGDOUBLE) || \
-    1691             :                                   ((type) == NPY_HALF))
-    1692             : 
-    1693             : #define PyTypeNum_ISSTRING(type) (((type) == NPY_STRING) ||    \
-    1694             :                                   ((type) == NPY_UNICODE))
-    1695             : 
-    1696             : #define PyTypeNum_ISCOMPLEX(type) (((type) >= NPY_CFLOAT) &&   \
-    1697             :                                 ((type) <= NPY_CLONGDOUBLE))
-    1698             : 
-    1699             : #define PyTypeNum_ISPYTHON(type) (((type) == NPY_LONG) ||      \
-    1700             :                                   ((type) == NPY_DOUBLE) ||    \
-    1701             :                                   ((type) == NPY_CDOUBLE) ||   \
-    1702             :                                   ((type) == NPY_BOOL) ||      \
-    1703             :                                   ((type) == NPY_OBJECT ))
-    1704             : 
-    1705             : #define PyTypeNum_ISFLEXIBLE(type) (((type) >=NPY_STRING) &&  \
-    1706             :                                     ((type) <=NPY_VOID))
-    1707             : 
-    1708             : #define PyTypeNum_ISDATETIME(type) (((type) >=NPY_DATETIME) &&  \
-    1709             :                                     ((type) <=NPY_TIMEDELTA))
-    1710             : 
-    1711             : #define PyTypeNum_ISUSERDEF(type) (((type) >= NPY_USERDEF) && \
-    1712             :                                    ((type) < NPY_USERDEF+     \
-    1713             :                                     NPY_NUMUSERTYPES))
-    1714             : 
-    1715             : #define PyTypeNum_ISEXTENDED(type) (PyTypeNum_ISFLEXIBLE(type) ||  \
-    1716             :                                     PyTypeNum_ISUSERDEF(type))
-    1717             : 
-    1718             : #define PyTypeNum_ISOBJECT(type) ((type) == NPY_OBJECT)
-    1719             : 
-    1720             : 
-    1721             : #define PyDataType_ISBOOL(obj) PyTypeNum_ISBOOL(((PyArray_Descr*)(obj))->type_num)
-    1722             : #define PyDataType_ISUNSIGNED(obj) PyTypeNum_ISUNSIGNED(((PyArray_Descr*)(obj))->type_num)
-    1723             : #define PyDataType_ISSIGNED(obj) PyTypeNum_ISSIGNED(((PyArray_Descr*)(obj))->type_num)
-    1724             : #define PyDataType_ISINTEGER(obj) PyTypeNum_ISINTEGER(((PyArray_Descr*)(obj))->type_num )
-    1725             : #define PyDataType_ISFLOAT(obj) PyTypeNum_ISFLOAT(((PyArray_Descr*)(obj))->type_num)
-    1726             : #define PyDataType_ISNUMBER(obj) PyTypeNum_ISNUMBER(((PyArray_Descr*)(obj))->type_num)
-    1727             : #define PyDataType_ISSTRING(obj) PyTypeNum_ISSTRING(((PyArray_Descr*)(obj))->type_num)
-    1728             : #define PyDataType_ISCOMPLEX(obj) PyTypeNum_ISCOMPLEX(((PyArray_Descr*)(obj))->type_num)
-    1729             : #define PyDataType_ISPYTHON(obj) PyTypeNum_ISPYTHON(((PyArray_Descr*)(obj))->type_num)
-    1730             : #define PyDataType_ISFLEXIBLE(obj) PyTypeNum_ISFLEXIBLE(((PyArray_Descr*)(obj))->type_num)
-    1731             : #define PyDataType_ISDATETIME(obj) PyTypeNum_ISDATETIME(((PyArray_Descr*)(obj))->type_num)
-    1732             : #define PyDataType_ISUSERDEF(obj) PyTypeNum_ISUSERDEF(((PyArray_Descr*)(obj))->type_num)
-    1733             : #define PyDataType_ISEXTENDED(obj) PyTypeNum_ISEXTENDED(((PyArray_Descr*)(obj))->type_num)
-    1734             : #define PyDataType_ISOBJECT(obj) PyTypeNum_ISOBJECT(((PyArray_Descr*)(obj))->type_num)
-    1735             : #define PyDataType_HASFIELDS(obj) (((PyArray_Descr *)(obj))->names != NULL)
-    1736             : #define PyDataType_HASSUBARRAY(dtype) ((dtype)->subarray != NULL)
-    1737             : #define PyDataType_ISUNSIZED(dtype) ((dtype)->elsize == 0 && \
-    1738             :                                       !PyDataType_HASFIELDS(dtype))
-    1739             : #define PyDataType_MAKEUNSIZED(dtype) ((dtype)->elsize = 0)
-    1740             : 
-    1741             : #define PyArray_ISBOOL(obj) PyTypeNum_ISBOOL(PyArray_TYPE(obj))
-    1742             : #define PyArray_ISUNSIGNED(obj) PyTypeNum_ISUNSIGNED(PyArray_TYPE(obj))
-    1743             : #define PyArray_ISSIGNED(obj) PyTypeNum_ISSIGNED(PyArray_TYPE(obj))
-    1744             : #define PyArray_ISINTEGER(obj) PyTypeNum_ISINTEGER(PyArray_TYPE(obj))
-    1745             : #define PyArray_ISFLOAT(obj) PyTypeNum_ISFLOAT(PyArray_TYPE(obj))
-    1746             : #define PyArray_ISNUMBER(obj) PyTypeNum_ISNUMBER(PyArray_TYPE(obj))
-    1747             : #define PyArray_ISSTRING(obj) PyTypeNum_ISSTRING(PyArray_TYPE(obj))
-    1748             : #define PyArray_ISCOMPLEX(obj) PyTypeNum_ISCOMPLEX(PyArray_TYPE(obj))
-    1749             : #define PyArray_ISPYTHON(obj) PyTypeNum_ISPYTHON(PyArray_TYPE(obj))
-    1750             : #define PyArray_ISFLEXIBLE(obj) PyTypeNum_ISFLEXIBLE(PyArray_TYPE(obj))
-    1751             : #define PyArray_ISDATETIME(obj) PyTypeNum_ISDATETIME(PyArray_TYPE(obj))
-    1752             : #define PyArray_ISUSERDEF(obj) PyTypeNum_ISUSERDEF(PyArray_TYPE(obj))
-    1753             : #define PyArray_ISEXTENDED(obj) PyTypeNum_ISEXTENDED(PyArray_TYPE(obj))
-    1754             : #define PyArray_ISOBJECT(obj) PyTypeNum_ISOBJECT(PyArray_TYPE(obj))
-    1755             : #define PyArray_HASFIELDS(obj) PyDataType_HASFIELDS(PyArray_DESCR(obj))
-    1756             : 
-    1757             :     /*
-    1758             :      * FIXME: This should check for a flag on the data-type that
-    1759             :      * states whether or not it is variable length.  Because the
-    1760             :      * ISFLEXIBLE check is hard-coded to the built-in data-types.
-    1761             :      */
-    1762             : #define PyArray_ISVARIABLE(obj) PyTypeNum_ISFLEXIBLE(PyArray_TYPE(obj))
-    1763             : 
-    1764             : #define PyArray_SAFEALIGNEDCOPY(obj) (PyArray_ISALIGNED(obj) && !PyArray_ISVARIABLE(obj))
-    1765             : 
-    1766             : 
-    1767             : #define NPY_LITTLE '<'
-    1768             : #define NPY_BIG '>'
-    1769             : #define NPY_NATIVE '='
-    1770             : #define NPY_SWAP 's'
-    1771             : #define NPY_IGNORE '|'
-    1772             : 
-    1773             : #if NPY_BYTE_ORDER == NPY_BIG_ENDIAN
-    1774             : #define NPY_NATBYTE NPY_BIG
-    1775             : #define NPY_OPPBYTE NPY_LITTLE
-    1776             : #else
-    1777             : #define NPY_NATBYTE NPY_LITTLE
-    1778             : #define NPY_OPPBYTE NPY_BIG
-    1779             : #endif
-    1780             : 
-    1781             : #define PyArray_ISNBO(arg) ((arg) != NPY_OPPBYTE)
-    1782             : #define PyArray_IsNativeByteOrder PyArray_ISNBO
-    1783             : #define PyArray_ISNOTSWAPPED(m) PyArray_ISNBO(PyArray_DESCR(m)->byteorder)
-    1784             : #define PyArray_ISBYTESWAPPED(m) (!PyArray_ISNOTSWAPPED(m))
-    1785             : 
-    1786             : #define PyArray_FLAGSWAP(m, flags) (PyArray_CHKFLAGS(m, flags) &&       \
-    1787             :                                     PyArray_ISNOTSWAPPED(m))
-    1788             : 
-    1789             : #define PyArray_ISCARRAY(m) PyArray_FLAGSWAP(m, NPY_ARRAY_CARRAY)
-    1790             : #define PyArray_ISCARRAY_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_CARRAY_RO)
-    1791             : #define PyArray_ISFARRAY(m) PyArray_FLAGSWAP(m, NPY_ARRAY_FARRAY)
-    1792             : #define PyArray_ISFARRAY_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_FARRAY_RO)
-    1793             : #define PyArray_ISBEHAVED(m) PyArray_FLAGSWAP(m, NPY_ARRAY_BEHAVED)
-    1794             : #define PyArray_ISBEHAVED_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_ALIGNED)
-    1795             : 
-    1796             : 
-    1797             : #define PyDataType_ISNOTSWAPPED(d) PyArray_ISNBO(((PyArray_Descr *)(d))->byteorder)
-    1798             : #define PyDataType_ISBYTESWAPPED(d) (!PyDataType_ISNOTSWAPPED(d))
-    1799             : 
-    1800             : /************************************************************
-    1801             :  * A struct used by PyArray_CreateSortedStridePerm, new in 1.7.
-    1802             :  ************************************************************/
-    1803             : 
-    1804             : typedef struct {
-    1805             :     npy_intp perm, stride;
-    1806             : } npy_stride_sort_item;
-    1807             : 
-    1808             : /************************************************************
-    1809             :  * This is the form of the struct that's stored in the
-    1810             :  * PyCapsule returned by an array's __array_struct__ attribute. See
-    1811             :  * https://docs.scipy.org/doc/numpy/reference/arrays.interface.html for the full
-    1812             :  * documentation.
-    1813             :  ************************************************************/
-    1814             : typedef struct {
-    1815             :     int two;              /*
-    1816             :                            * contains the integer 2 as a sanity
-    1817             :                            * check
-    1818             :                            */
-    1819             : 
-    1820             :     int nd;               /* number of dimensions */
-    1821             : 
-    1822             :     char typekind;        /*
-    1823             :                            * kind in array --- character code of
-    1824             :                            * typestr
-    1825             :                            */
-    1826             : 
-    1827             :     int itemsize;         /* size of each element */
-    1828             : 
-    1829             :     int flags;            /*
-    1830             :                            * how should be data interpreted. Valid
-    1831             :                            * flags are CONTIGUOUS (1), F_CONTIGUOUS (2),
-    1832             :                            * ALIGNED (0x100), NOTSWAPPED (0x200), and
-    1833             :                            * WRITEABLE (0x400).  ARR_HAS_DESCR (0x800)
-    1834             :                            * states that arrdescr field is present in
-    1835             :                            * structure
-    1836             :                            */
-    1837             : 
-    1838             :     npy_intp *shape;       /*
-    1839             :                             * A length-nd array of shape
-    1840             :                             * information
-    1841             :                             */
-    1842             : 
-    1843             :     npy_intp *strides;    /* A length-nd array of stride information */
-    1844             : 
-    1845             :     void *data;           /* A pointer to the first element of the array */
-    1846             : 
-    1847             :     PyObject *descr;      /*
-    1848             :                            * A list of fields or NULL (ignored if flags
-    1849             :                            * does not have ARR_HAS_DESCR flag set)
-    1850             :                            */
-    1851             : } PyArrayInterface;
-    1852             : 
-    1853             : /*
-    1854             :  * This is a function for hooking into the PyDataMem_NEW/FREE/RENEW functions.
-    1855             :  * See the documentation for PyDataMem_SetEventHook.
-    1856             :  */
-    1857             : typedef void (PyDataMem_EventHookFunc)(void *inp, void *outp, size_t size,
-    1858             :                                        void *user_data);
-    1859             : 
-    1860             : 
-    1861             : /*
-    1862             :  * PyArray_DTypeMeta related definitions.
-    1863             :  *
-    1864             :  * As of now, this API is preliminary and will be extended as necessary.
-    1865             :  */
-    1866             : #if defined(NPY_INTERNAL_BUILD) && NPY_INTERNAL_BUILD
-    1867             :     /*
-    1868             :      * The Structures defined in this block are currently considered
-    1869             :      * private API and may change without warning!
-    1870             :      * Part of this (at least the size) is expected to be public API without
-    1871             :      * further modifications.
-    1872             :      */
-    1873             :     /* TODO: Make this definition public in the API, as soon as its settled */
-    1874             :     NPY_NO_EXPORT extern PyTypeObject PyArrayDTypeMeta_Type;
-    1875             : 
-    1876             :     /*
-    1877             :      * While NumPy DTypes would not need to be heap types the plan is to
-    1878             :      * make DTypes available in Python at which point they will be heap types.
-    1879             :      * Since we also wish to add fields to the DType class, this looks like
-    1880             :      * a typical instance definition, but with PyHeapTypeObject instead of
-    1881             :      * only the PyObject_HEAD.
-    1882             :      * This must only be exposed very extremely careful consideration, since
-    1883             :      * it is a fairly complex construct which may be better to allow
-    1884             :      * refactoring of.
-    1885             :      */
-    1886             :     typedef struct {
-    1887             :         PyHeapTypeObject super;
-    1888             : 
-    1889             :         /*
-    1890             :          * Most DTypes will have a singleton default instance, for the
-    1891             :          * parametric legacy DTypes (bytes, string, void, datetime) this
-    1892             :          * may be a pointer to the *prototype* instance?
-    1893             :          */
-    1894             :         PyArray_Descr *singleton;
-    1895             :         /* Copy of the legacy DTypes type number, usually invalid. */
-    1896             :         int type_num;
-    1897             : 
-    1898             :         /* The type object of the scalar instances (may be NULL?) */
-    1899             :         PyTypeObject *scalar_type;
-    1900             :         /*
-    1901             :          * DType flags to signal legacy, parametric, or
-    1902             :          * abstract.  But plenty of space for additional information/flags.
-    1903             :          */
-    1904             :         npy_uint64 flags;
-    1905             : 
-    1906             :         /*
-    1907             :          * Use indirection in order to allow a fixed size for this struct.
-    1908             :          * A stable ABI size makes creating a static DType less painful
-    1909             :          * while also ensuring flexibility for all opaque API (with one
-    1910             :          * indirection due the pointer lookup).
-    1911             :          */
-    1912             :         void *dt_slots;
-    1913             :         void *reserved[3];
-    1914             :     } PyArray_DTypeMeta;
-    1915             : 
-    1916             : #endif  /* NPY_INTERNAL_BUILD */
-    1917             : 
-    1918             : 
-    1919             : /*
-    1920             :  * Use the keyword NPY_DEPRECATED_INCLUDES to ensure that the header files
-    1921             :  * npy_*_*_deprecated_api.h are only included from here and nowhere else.
-    1922             :  */
-    1923             : #ifdef NPY_DEPRECATED_INCLUDES
-    1924             : #error "Do not use the reserved keyword NPY_DEPRECATED_INCLUDES."
-    1925             : #endif
-    1926             : #define NPY_DEPRECATED_INCLUDES
-    1927             : #if !defined(NPY_NO_DEPRECATED_API) || \
-    1928             :     (NPY_NO_DEPRECATED_API < NPY_1_7_API_VERSION)
-    1929             : #include "npy_1_7_deprecated_api.h"
-    1930             : #endif
-    1931             : /*
-    1932             :  * There is no file npy_1_8_deprecated_api.h since there are no additional
-    1933             :  * deprecated API features in NumPy 1.8.
-    1934             :  *
-    1935             :  * Note to maintainers: insert code like the following in future NumPy
-    1936             :  * versions.
-    1937             :  *
-    1938             :  * #if !defined(NPY_NO_DEPRECATED_API) || \
-    1939             :  *     (NPY_NO_DEPRECATED_API < NPY_1_9_API_VERSION)
-    1940             :  * #include "npy_1_9_deprecated_api.h"
-    1941             :  * #endif
-    1942             :  */
-    1943             : #undef NPY_DEPRECATED_INCLUDES
-    1944             : 
-    1945             : #endif  /* NUMPY_CORE_INCLUDE_NUMPY_NDARRAYTYPES_H_ */
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html b/doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html deleted file mode 100644 index c39d31005..000000000 --- a/doc/coverageReport/include/crpropa/AssocVector.h.func-sort-c.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/AssocVector.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - AssocVector.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2121100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_5
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEaSERKSE_30
_ZNK4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_41
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE6insertERKSC_1143
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEixERKS6_1143
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/AssocVector.h.func.html b/doc/coverageReport/include/crpropa/AssocVector.h.func.html deleted file mode 100644 index 206af8f4c..000000000 --- a/doc/coverageReport/include/crpropa/AssocVector.h.func.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/AssocVector.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - AssocVector.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2121100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_5
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE6insertERKSC_1143
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEaSERKSE_30
_ZN4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEEixERKS6_1143
_ZNK4Loki11AssocVectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEN7crpropa7VariantESt4lessIS6_ESaISt4pairIS6_S8_EEE4findERKS6_41
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/AssocVector.h.gcov.html b/doc/coverageReport/include/crpropa/AssocVector.h.gcov.html deleted file mode 100644 index 6e1f36ba8..000000000 --- a/doc/coverageReport/include/crpropa/AssocVector.h.gcov.html +++ /dev/null @@ -1,457 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/AssocVector.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - AssocVector.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2121100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : ////////////////////////////////////////////////////////////////////////////////
-       2             : // The Loki Library
-       3             : // Copyright (c) 2001 by Andrei Alexandrescu
-       4             : // This code accompanies the book:
-       5             : // Alexandrescu, Andrei. "Modern C++ Design: Generic Programming and Design
-       6             : //     Patterns Applied". Copyright (c) 2001. Addison-Wesley.
-       7             : //
-       8             : // Permission is hereby granted, free of charge, to any person obtaining a copy
-       9             : // of this software and associated documentation files (the "Software"), to deal
-      10             : // in the Software without restriction, including without limitation the rights
-      11             : // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-      12             : // copies of the Software, and to permit persons to whom the Software is
-      13             : // furnished to do so, subject to the following conditions:
-      14             : //
-      15             : // The above copyright notice and this permission notice shall be included in
-      16             : // all copies or substantial portions of the Software.
-      17             : //
-      18             : // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-      19             : // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-      20             : // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-      21             : // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-      22             : // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-      23             : // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-      24             : // SOFTWARE.
-      25             : ////////////////////////////////////////////////////////////////////////////////
-      26             : #ifndef LOKI_ASSOCVECTOR_INC_
-      27             : #define LOKI_ASSOCVECTOR_INC_
-      28             : 
-      29             : // $Id$
-      30             : 
-      31             : 
-      32             : #include <algorithm>
-      33             : #include <functional>
-      34             : #include <vector>
-      35             : #include <utility>
-      36             : #include <iterator>
-      37             : #include <map>
-      38             : 
-      39             : 
-      40             : namespace Loki
-      41             : {
-      42             : ////////////////////////////////////////////////////////////////////////////////
-      43             : // class template AssocVectorCompare
-      44             : // Used by AssocVector
-      45             : ////////////////////////////////////////////////////////////////////////////////
-      46             : 
-      47             :     namespace Private
-      48             :     {
-      49             :         template <class Value, class C>
-      50             :         class AssocVectorCompare : public C
-      51             :         {
-      52             :             typedef std::pair<typename C::first_argument_type, Value>
-      53             :                 Data;
-      54             :             typedef typename C::first_argument_type first_argument_type;
-      55             : 
-      56             :         public:
-      57             :             AssocVectorCompare()
-      58             :             {}
-      59             : 
-      60             :             AssocVectorCompare(const C& src) : C(src)
-      61             :             {}
-      62             : 
-      63             :             bool operator()(const first_argument_type& lhs,
-      64             :                 const first_argument_type& rhs) const
-      65             :             { return C::operator()(lhs, rhs); }
-      66             : 
-      67             :             bool operator()(const Data& lhs, const Data& rhs) const
-      68             :             { return operator()(lhs.first, rhs.first); }
-      69             : 
-      70             :             bool operator()(const Data& lhs,
-      71             :                 const first_argument_type& rhs) const
-      72          57 :             { return operator()(lhs.first, rhs); }
-      73             : 
-      74             :             bool operator()(const first_argument_type& lhs,
-      75             :                 const Data& rhs) const
-      76             :             { return operator()(lhs, rhs.first); }
-      77             :         };
-      78             :     }
-      79             : 
-      80             : ////////////////////////////////////////////////////////////////////////////////
-      81             : // class template AssocVector
-      82             : // An associative vector built as a syntactic drop-in replacement for std::map
-      83             : // BEWARE: AssocVector doesn't respect all map's guarantees, the most important
-      84             : //     being:
-      85             : // * iterators are invalidated by insert and erase operations
-      86             : // * the complexity of insert/erase is O(N) not O(log N)
-      87             : // * value_type is std::pair<K, V> not std::pair<const K, V>
-      88             : // * iterators are random
-      89             : ////////////////////////////////////////////////////////////////////////////////
-      90             : 
-      91             : 
-      92             :     template
-      93             :     <
-      94             :         class K,
-      95             :         class V,
-      96             :         class C = std::less<K>,
-      97             :         class A = std::allocator< std::pair<K, V> >
-      98             :     >
-      99          30 :     class AssocVector
-     100             :         : private std::vector< std::pair<K, V>, A >
-     101             :         , private Private::AssocVectorCompare<V, C>
-     102             :     {
-     103             :         typedef std::vector<std::pair<K, V>, A> Base;
-     104             :         typedef Private::AssocVectorCompare<V, C> MyCompare;
-     105             : 
-     106             :     public:
-     107             :         typedef K key_type;
-     108             :         typedef V mapped_type;
-     109             :         typedef typename Base::value_type value_type;
-     110             : 
-     111             :         typedef C key_compare;
-     112             :         typedef A allocator_type;
-     113             :         typedef typename A::reference reference;
-     114             :         typedef typename A::const_reference const_reference;
-     115             :         typedef typename Base::iterator iterator;
-     116             :         typedef typename Base::const_iterator const_iterator;
-     117             :         typedef typename Base::size_type size_type;
-     118             :         typedef typename Base::difference_type difference_type;
-     119             :         typedef typename A::pointer pointer;
-     120             :         typedef typename A::const_pointer const_pointer;
-     121             :         typedef typename Base::reverse_iterator reverse_iterator;
-     122             :         typedef typename Base::const_reverse_iterator const_reverse_iterator;
-     123             : 
-     124             :         class value_compare
-     125             :             : public std::binary_function<value_type, value_type, bool>
-     126             :             , private key_compare
-     127             :         {
-     128             :             friend class AssocVector;
-     129             : 
-     130             :         protected:
-     131             :             value_compare(key_compare pred) : key_compare(pred)
-     132             :             {}
-     133             : 
-     134             :         public:
-     135             :             bool operator()(const value_type& lhs, const value_type& rhs) const
-     136             :             { return key_compare::operator()(lhs.first, rhs.first); }
-     137             :         };
-     138             : 
-     139             :         // 23.3.1.1 construct/copy/destroy
-     140             : 
-     141             :         explicit AssocVector(const key_compare& comp = key_compare(),
-     142             :             const A& alloc = A())
-     143             :         : Base(alloc), MyCompare(comp)
-     144             :         {}
-     145             : 
-     146             :         template <class InputIterator>
-     147             :         AssocVector(InputIterator first, InputIterator last,
-     148             :             const key_compare& comp = key_compare(),
-     149             :             const A& alloc = A())
-     150             :         : Base( alloc ), MyCompare( comp )
-     151             :         {
-     152             :             typedef ::std::vector< ::std::pair< K, V >, A > BaseType;
-     153             :             typedef ::std::map< K, V, C, A > TempMap;
-     154             :             typedef ::std::back_insert_iterator< Base > MyInserter;
-     155             :             MyCompare & me = *this;
-     156             :             const A tempAlloc;
-     157             :             // Make a temporary map similar to this type to prevent any duplicate elements.
-     158             :             TempMap temp( first, last, me, tempAlloc );
-     159             :             Base::reserve( temp.size() );
-     160             :             BaseType & target = static_cast< BaseType & >( *this );
-     161             :             MyInserter myInserter = ::std::back_inserter( target );
-     162             :             ::std::copy( temp.begin(), temp.end(), myInserter );
-     163             :         }
-     164             : 
-     165          30 :         AssocVector& operator=(const AssocVector& rhs)
-     166             :         {
-     167          30 :             AssocVector(rhs).swap(*this);
-     168          30 :             return *this;
-     169             :         }
-     170             : 
-     171             :         // iterators:
-     172             :         // The following are here because MWCW gets 'using' wrong
-     173             :         iterator begin() { return Base::begin(); }
-     174             :         const_iterator begin() const { return Base::begin(); }
-     175             :         iterator end() { return Base::end(); }
-     176             :         const_iterator end() const { return Base::end(); }
-     177             :         reverse_iterator rbegin() { return Base::rbegin(); }
-     178             :         const_reverse_iterator rbegin() const { return Base::rbegin(); }
-     179             :         reverse_iterator rend() { return Base::rend(); }
-     180             :         const_reverse_iterator rend() const { return Base::rend(); }
-     181             : 
-     182             :         // capacity:
-     183             :         bool empty() const { return Base::empty(); }
-     184             :         size_type size() const { return Base::size(); }
-     185             :         size_type max_size() { return Base::max_size(); }
-     186             : 
-     187             :         // 23.3.1.2 element access:
-     188        1143 :         mapped_type& operator[](const key_type& key)
-     189        1143 :         { return insert(value_type(key, mapped_type())).first->second; }
-     190             : 
-     191             :         // modifiers:
-     192        1143 :         std::pair<iterator, bool> insert(const value_type& val)
-     193             :         {
-     194             :             bool found(true);
-     195        1143 :             iterator i(lower_bound(val.first));
-     196             : 
-     197          13 :             if (i == end() || this->operator()(val.first, i->first))
-     198             :             {
-     199        1134 :                 i = Base::insert(i, val);
-     200             :                 found = false;
-     201             :             }
-     202        1143 :             return std::make_pair(i, !found);
-     203             :         }
-     204             :         //Section [23.1.2], Table 69
-     205             :         //http://developer.apple.com/documentation/DeveloperTools/gcc-3.3/libstdc++/23_containers/howto.html#4
-     206             :         iterator insert(iterator pos, const value_type& val)
-     207             :         {
-     208             :             if( (pos == begin() || this->operator()(*(pos-1),val)) &&
-     209             :                 (pos == end()    || this->operator()(val, *pos)) )
-     210             :             {
-     211             :                 return Base::insert(pos, val);
-     212             :             }
-     213             :             return insert(val).first;
-     214             :         }
-     215             : 
-     216             :         template <class InputIterator>
-     217             :         void insert(InputIterator first, InputIterator last)
-     218             :         { for (; first != last; ++first) insert(*first); }
-     219             : 
-     220             :         void erase(iterator pos)
-     221           5 :         { Base::erase(pos); }
-     222             : 
-     223             :         size_type erase(const key_type& k)
-     224             :         {
-     225             :             iterator i(find(k));
-     226             :             if (i == end()) return 0;
-     227             :             erase(i);
-     228             :             return 1;
-     229             :         }
-     230             : 
-     231             :         void erase(iterator first, iterator last)
-     232             :         { Base::erase(first, last); }
-     233             : 
-     234             :         void swap(AssocVector& other)
-     235             :         {
-     236             :             Base::swap(other);
-     237             :             MyCompare& me = *this;
-     238             :             MyCompare& rhs = other;
-     239             :             std::swap(me, rhs);
-     240             :         }
-     241             : 
-     242             :         void clear()
-     243             :         { Base::clear(); }
-     244             : 
-     245             :         // observers:
-     246             :         key_compare key_comp() const
-     247             :         { return *this; }
-     248             : 
-     249             :         value_compare value_comp() const
-     250             :         {
-     251             :             const key_compare& comp = *this;
-     252             :             return value_compare(comp);
-     253             :         }
-     254             : 
-     255             :         // 23.3.1.3 map operations:
-     256           5 :         iterator find(const key_type& k)
-     257             :         {
-     258             :             iterator i(lower_bound(k));
-     259           5 :             if (i != end() && this->operator()(k, i->first))
-     260             :             {
-     261             :                 i = end();
-     262             :             }
-     263           5 :             return i;
-     264             :         }
-     265             : 
-     266          41 :         const_iterator find(const key_type& k) const
-     267             :         {
-     268             :             const_iterator i(lower_bound(k));
-     269          33 :             if (i != end() && this->operator()(k, i->first))
-     270             :             {
-     271             :                 i = end();
-     272             :             }
-     273          41 :             return i;
-     274             :         }
-     275             : 
-     276             :         size_type count(const key_type& k) const
-     277             :         { return find(k) != end(); }
-     278             : 
-     279             :         iterator lower_bound(const key_type& k)
-     280             :         {
-     281             :             MyCompare& me = *this;
-     282        1148 :             return std::lower_bound(begin(), end(), k, me);
-     283             :         }
-     284             : 
-     285             :         const_iterator lower_bound(const key_type& k) const
-     286             :         {
-     287             :             const MyCompare& me = *this;
-     288          41 :             return std::lower_bound(begin(), end(), k, me);
-     289             :         }
-     290             : 
-     291             :         iterator upper_bound(const key_type& k)
-     292             :         {
-     293             :             MyCompare& me = *this;
-     294             :             return std::upper_bound(begin(), end(), k, me);
-     295             :         }
-     296             : 
-     297             :         const_iterator upper_bound(const key_type& k) const
-     298             :         {
-     299             :             const MyCompare& me = *this;
-     300             :             return std::upper_bound(begin(), end(), k, me);
-     301             :         }
-     302             : 
-     303             :         std::pair<iterator, iterator> equal_range(const key_type& k)
-     304             :         {
-     305             :             MyCompare& me = *this;
-     306             :             return std::equal_range(begin(), end(), k, me);
-     307             :         }
-     308             : 
-     309             :         std::pair<const_iterator, const_iterator> equal_range(
-     310             :             const key_type& k) const
-     311             :         {
-     312             :             const MyCompare& me = *this;
-     313             :             return std::equal_range(begin(), end(), k, me);
-     314             :         }
-     315             : 
-     316             :         template <class K1, class V1, class C1, class A1>
-     317             :         friend bool operator==(const AssocVector<K1, V1, C1, A1>& lhs,
-     318             :                         const AssocVector<K1, V1, C1, A1>& rhs);
-     319             : 
-     320             :         bool operator<(const AssocVector& rhs) const
-     321             :         {
-     322             :             const Base& me = *this;
-     323             :             const Base& yo = rhs;
-     324             :             return me < yo;
-     325             :         }
-     326             : 
-     327             :         template <class K1, class V1, class C1, class A1>
-     328             :         friend bool operator!=(const AssocVector<K1, V1, C1, A1>& lhs,
-     329             :                                const AssocVector<K1, V1, C1, A1>& rhs);
-     330             : 
-     331             :         template <class K1, class V1, class C1, class A1>
-     332             :         friend bool operator>(const AssocVector<K1, V1, C1, A1>& lhs,
-     333             :                               const AssocVector<K1, V1, C1, A1>& rhs);
-     334             : 
-     335             :         template <class K1, class V1, class C1, class A1>
-     336             :         friend bool operator>=(const AssocVector<K1, V1, C1, A1>& lhs,
-     337             :                                const AssocVector<K1, V1, C1, A1>& rhs);
-     338             : 
-     339             :         template <class K1, class V1, class C1, class A1>
-     340             :         friend bool operator<=(const AssocVector<K1, V1, C1, A1>& lhs,
-     341             :                                const AssocVector<K1, V1, C1, A1>& rhs);
-     342             :     };
-     343             : 
-     344             :     template <class K, class V, class C, class A>
-     345             :     inline bool operator==(const AssocVector<K, V, C, A>& lhs,
-     346             :                            const AssocVector<K, V, C, A>& rhs)
-     347             :     {
-     348             :       const std::vector<std::pair<K, V>, A>& me = lhs;
-     349             :       return me == rhs;
-     350             :     }
-     351             : 
-     352             :     template <class K, class V, class C, class A>
-     353             :     inline bool operator!=(const AssocVector<K, V, C, A>& lhs,
-     354             :                            const AssocVector<K, V, C, A>& rhs)
-     355             :     { return !(lhs == rhs); }
-     356             : 
-     357             :     template <class K, class V, class C, class A>
-     358             :     inline bool operator>(const AssocVector<K, V, C, A>& lhs,
-     359             :                           const AssocVector<K, V, C, A>& rhs)
-     360             :     { return rhs < lhs; }
-     361             : 
-     362             :     template <class K, class V, class C, class A>
-     363             :     inline bool operator>=(const AssocVector<K, V, C, A>& lhs,
-     364             :                            const AssocVector<K, V, C, A>& rhs)
-     365             :     { return !(lhs < rhs); }
-     366             : 
-     367             :     template <class K, class V, class C, class A>
-     368             :     inline bool operator<=(const AssocVector<K, V, C, A>& lhs,
-     369             :                            const AssocVector<K, V, C, A>& rhs)
-     370             :     { return !(rhs < lhs); }
-     371             : 
-     372             : 
-     373             :     // specialized algorithms:
-     374             :     template <class K, class V, class C, class A>
-     375             :     void swap(AssocVector<K, V, C, A>& lhs, AssocVector<K, V, C, A>& rhs)
-     376             :     { lhs.swap(rhs); }
-     377             : 
-     378             : } // namespace Loki
-     379             : 
-     380             : #endif // end file guardian
-     381             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html deleted file mode 100644 index 311549a2e..000000000 --- a/doc/coverageReport/include/crpropa/Candidate.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Candidate.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Candidate.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Candidate.h.func.html b/doc/coverageReport/include/crpropa/Candidate.h.func.html deleted file mode 100644 index 2a4fbcad6..000000000 --- a/doc/coverageReport/include/crpropa/Candidate.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Candidate.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Candidate.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Candidate.h.gcov.html b/doc/coverageReport/include/crpropa/Candidate.h.gcov.html deleted file mode 100644 index 393563bad..000000000 --- a/doc/coverageReport/include/crpropa/Candidate.h.gcov.html +++ /dev/null @@ -1,258 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Candidate.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Candidate.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_CANDIDATE_H
-       2             : #define CRPROPA_CANDIDATE_H
-       3             : 
-       4             : #include "crpropa/ParticleState.h"
-       5             : #include "crpropa/Referenced.h"
-       6             : #include "crpropa/AssocVector.h"
-       7             : #include "crpropa/Variant.h"
-       8             : 
-       9             : #include <vector>
-      10             : #include <map>
-      11             : #include <sstream>
-      12             : #include <stdint.h>
-      13             : 
-      14             : namespace crpropa {
-      15             : /**
-      16             :  * \addtogroup Core
-      17             :  * @{
-      18             :  */
-      19             : 
-      20             : /**
-      21             :  @class Candidate Candidate.h include/crpropa/Candidate.h
-      22             :  @brief All information about the cosmic ray.
-      23             : 
-      24             :  The Candidate is a passive object, that holds the information about the state
-      25             :  of the cosmic ray and the simulation itself.
-      26             :  */
-      27             : class Candidate: public Referenced {
-      28             : public:
-      29             :         ParticleState source; /**< Particle state at the source */
-      30             :         ParticleState created; /**< Particle state of parent particle at the time of creation */
-      31             :         ParticleState current; /**< Current particle state */
-      32             :         ParticleState previous; /**< Particle state at the end of the previous step */
-      33             : 
-      34             :         std::vector<ref_ptr<Candidate> > secondaries; /**< Secondary particles from interactions */
-      35             : 
-      36             :         typedef Loki::AssocVector<std::string, Variant> PropertyMap;
-      37             :         PropertyMap properties; /**< Map of property names and their values. */
-      38             : 
-      39             :         /** Parent candidate. 0 if no parent (initial particle). Must not be a ref_ptr to prevent circular referencing. */
-      40             :         Candidate *parent;
-      41             : 
-      42             : private:
-      43             :         bool active; /**< Active status */
-      44             :         double weight; /**< Weight of the candidate */
-      45             :         double redshift; /**< Current simulation time-point in terms of redshift z */
-      46             :         double trajectoryLength; /**< Comoving distance [m] the candidate has traveled so far */
-      47             :         double currentStep; /**< Size of the currently performed step in [m] comoving units */
-      48             :         double nextStep; /**< Proposed size of the next propagation step in [m] comoving units */
-      49             :         std::string tagOrigin; /**< Name of interaction/source process which created this candidate*/
-      50             : 
-      51             :         static uint64_t nextSerialNumber;
-      52             :         uint64_t serialNumber;
-      53             : 
-      54             : public:
-      55             :         Candidate(
-      56             :                 int id = 0,
-      57             :                 double energy = 0,
-      58             :                 Vector3d position = Vector3d(0, 0, 0),
-      59             :                 Vector3d direction = Vector3d(-1, 0, 0),
-      60             :                 double z = 0,
-      61             :                 double weight = 1., 
-      62             :                 std::string tagOrigin = "PRIM"
-      63             :         );
-      64             : 
-      65             :         /**
-      66             :          Creates a candidate, initializing the Candidate::source, Candidate::created,
-      67             :          Candidate::previous and Candidate::current state with the argument.
-      68             :          */
-      69             :         Candidate(const ParticleState &state);
-      70             : 
-      71             :         bool isActive() const;
-      72             :         void setActive(bool b);
-      73             : 
-      74             :         void setTrajectoryLength(double length);
-      75             :         double getTrajectoryLength() const;
-      76             : 
-      77             :         void setRedshift(double z);
-      78             :         double getRedshift() const;
-      79             : 
-      80             :         /**
-      81             :          Sets weight of each candidate.
-      82             :          Weights are calculated for each tracked secondary.
-      83             :          */
-      84             :         void setWeight(double weight);
-      85             :     void updateWeight(double weight);
-      86             :         double getWeight() const;
-      87             : 
-      88             :         /**
-      89             :          Sets the current step and increases the trajectory length accordingly.
-      90             :          Only the propagation module should use this.
-      91             :          */
-      92             :         void setCurrentStep(double step);
-      93             :         double getCurrentStep() const;
-      94             : 
-      95             :         /**
-      96             :          Sets the proposed next step.
-      97             :          Only the propagation module should use this.
-      98             :          */
-      99             :         void setNextStep(double step);
-     100             :         double getNextStep() const;
-     101             : 
-     102             :         /**
-     103             :          Sets the tagOrigin of the candidate. Can be used to trace back the interactions
-     104             :          */
-     105             :         void setTagOrigin(std::string tagOrigin);
-     106             :         std::string getTagOrigin() const;
-     107             : 
-     108             :         /**
-     109             :          Make a bid for the next step size: the lowest wins.
-     110             :          */
-     111             :         void limitNextStep(double step);
-     112             : 
-     113             :         void setProperty(const std::string &name, const Variant &value);
-     114             :         const Variant &getProperty(const std::string &name) const;
-     115             :         bool removeProperty(const std::string &name);
-     116             :         bool hasProperty(const std::string &name) const;
-     117             : 
-     118             :         /**
-     119             :          Add a new candidate to the list of secondaries.
-     120             :          @param c Candidate
-     121             : 
-     122             :          Adds a new candidate to the list of secondaries of this candidate.
-     123             :          The secondaries Candidate::source and Candidate::previous state are set to the _source_ and _previous_ state of its parent.
-     124             :          The secondaries Candidate::created and Candidate::current state are set to the _current_ state of its parent, except for the secondaries current energy and particle id.
-     125             :          Trajectory length and redshift are copied from the parent.
-     126             :          */
-     127             :         void addSecondary(Candidate *c);
-     128           4 :         inline void addSecondary(ref_ptr<Candidate> c) { addSecondary(c.get()); };
-     129             :         /**
-     130             :          Add a new candidate to the list of secondaries.
-     131             :          @param id                      particle ID of the secondary
-     132             :          @param energy          energy of the secondary
-     133             :          @param w                       weight of the secondary
-     134             :          @param tagOrigin       tag of the secondary
-     135             :          */
-     136             :         void addSecondary(int id, double energy, double w = 1., std::string tagOrigin = "SEC");
-     137             :         /**
-     138             :          Add a new candidate to the list of secondaries.
-     139             :          @param id                      particle ID of the secondary
-     140             :          @param energy          energy of the secondary
-     141             :          @param position        start position of the secondary
-     142             :          @param w                       weight of the secondary
-     143             :          @param tagOrigin       tag of the secondary
-     144             :          */
-     145             :         void addSecondary(int id, double energy, Vector3d position, double w = 1., std::string tagOrigin = "SEC");
-     146             :         void clearSecondaries();
-     147             : 
-     148             :         std::string getDescription() const;
-     149             : 
-     150             :         /** Unique (inside process) serial number (id) of candidate */
-     151             :         uint64_t getSerialNumber() const;
-     152             :         void setSerialNumber(const uint64_t snr);
-     153             : 
-     154             :         /** Serial number of candidate at source*/
-     155             :         uint64_t getSourceSerialNumber() const;
-     156             : 
-     157             :         /** Serial number of candidate at creation */
-     158             :         uint64_t getCreatedSerialNumber() const;
-     159             : 
-     160             :         /** Set the next serial number to use */
-     161             :         static void setNextSerialNumber(uint64_t snr);
-     162             : 
-     163             :         /** Get the next serial number that will be assigned */
-     164             :         static uint64_t getNextSerialNumber();
-     165             : 
-     166             :         /**
-     167             :          Create an exact clone of candidate
-     168             :          @param recursive       recursively clone and add the secondaries
-     169             :          */
-     170             :         ref_ptr<Candidate> clone(bool recursive = false) const;
-     171             : 
-     172             :         /**
-     173             :          Copy the source particle state to the current state
-     174             :          and activate it if inactive, e.g. restart it
-     175             :         */
-     176             :         void restart();
-     177             : };
-     178             : 
-     179             : /** @}*/
-     180             : } // namespace crpropa
-     181             : 
-     182             : #endif // CRPROPA_CANDIDATE_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Common.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Common.h.func-sort-c.html deleted file mode 100644 index b6011ea62..000000000 --- a/doc/coverageReport/include/crpropa/Common.h.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Common.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Common.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1010100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8gaussIntIZNS_20common_gaussInt_Test8TestBodyEvEUldE0_EEdOT_dd1
_ZN7crpropa8gaussIntIZNKS_19PhotoPionProduction7probEpsEdbddEUldE_EEdOT_dd10660
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Common.h.func.html b/doc/coverageReport/include/crpropa/Common.h.func.html deleted file mode 100644 index 480121887..000000000 --- a/doc/coverageReport/include/crpropa/Common.h.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Common.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Common.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1010100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8gaussIntIZNKS_19PhotoPionProduction7probEpsEdbddEUldE_EEdOT_dd10660
_ZN7crpropa8gaussIntIZNS_20common_gaussInt_Test8TestBodyEvEUldE0_EEdOT_dd1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Common.h.gcov.html b/doc/coverageReport/include/crpropa/Common.h.gcov.html deleted file mode 100644 index 13a42780e..000000000 --- a/doc/coverageReport/include/crpropa/Common.h.gcov.html +++ /dev/null @@ -1,163 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Common.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Common.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1010100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_COMMON_H
-       2             : #define CRPROPA_COMMON_H
-       3             : 
-       4             : #include <string>
-       5             : #include <vector>
-       6             : /**
-       7             :  @file
-       8             :  @brief Common helper functions
-       9             :  */
-      10             : 
-      11             : namespace crpropa {
-      12             : /**
-      13             :  * \addtogroup Core
-      14             :  * @{
-      15             :  */
-      16             : 
-      17             : // Returns the full path to a CRPropa data file
-      18             : std::string getDataPath(std::string filename);
-      19             : 
-      20             : // Returns the install prefix
-      21             : std::string getInstallPrefix();
-      22             : 
-      23             : // Returns a certain digit from a given integer
-      24             : inline int digit(const int& value, const int& d) {
-      25        1249 :         return (value % (d * 10)) / d;
-      26             : }
-      27             : 
-      28             : // Return value xclip which is the closest to x, so that lower <= xclip <= upper
-      29             : template <typename T>
-      30             : T clip(const T& x, const T& lower, const T& upper) {
-      31      499341 :         return std::max(lower, std::min(x, upper));
-      32             : }
-      33             : 
-      34             : // Perform linear interpolation on a set of n tabulated data points X[0 .. n-1] -> Y[0 .. n-1]
-      35             : // Returns Y[0] if x < X[0] and Y[n-1] if x > X[n-1]
-      36             : double interpolate(double x, const std::vector<double>& X,
-      37             :                 const std::vector<double>& Y);
-      38             : 
-      39             : 
-      40             : // Perform bilinear interpolation on a set of (n,m) tabulated data points X[0 .. n-1], Y[0 .. m-1] -> Z[0.. n-1*m-1]
-      41             : // Returns 0 if x < X[0] or x > X[n-1] or y < Y[0] or y > Y[m-1]
-      42             : double interpolate2d(double x, double y, const std::vector<double>& X,
-      43             :                 const std::vector<double>& Y, const std::vector<double>& Z);
-      44             : 
-      45             : // Perform linear interpolation on equidistant tabulated data
-      46             : // Returns Y[0] if x < lo and Y[n-1] if x > hi
-      47             : double interpolateEquidistant(double x, double lo, double hi,
-      48             :                 const std::vector<double>& Y);
-      49             : 
-      50             : // Find index of value in a sorted vector X that is closest to x
-      51             : size_t closestIndex(double x, const std::vector<double> &X);
-      52             : /** @}*/
-      53             : 
-      54             : 
-      55             : // pow implementation as template for integer exponents pow_integer<2>(x)
-      56             : // evaluates to x*x
-      57             : template <unsigned int exponent>
-      58             : inline double pow_integer(double base)
-      59             : {
-      60       63069 :   return pow_integer<(exponent >> 1)>(base*base) * (((exponent & 1) > 0) ? base : 1);
-      61             : }
-      62             : 
-      63             : template <>
-      64             : inline double pow_integer<0>(double base)
-      65             : {
-      66             :   return 1;
-      67             : }
-      68             : 
-      69             : // - input:  function over which to integrate, integration limits A and B
-      70             : // - output: 8-points Gauß-Legendre integral
-      71             : static const double X[8] = {.0950125098, .2816035507, .4580167776, .6178762444, .7554044083, .8656312023, .9445750230, .9894009349};
-      72             : static const double W[8] = {.1894506104, .1826034150, .1691565193, .1495959888, .1246289712, .0951585116, .0622535239, .0271524594};
-      73             : template<typename Integrand>
-      74       10661 : double gaussInt(Integrand&& integrand, double A, double B) {
-      75       10661 :         const double XM = 0.5 * (B + A);
-      76       10661 :         const double XR = 0.5 * (B - A);
-      77             :         double SS = 0.;
-      78       95958 :         for (int i = 0; i < 8; ++i) {
-      79       85296 :                 double DX = XR * X[i];
-      80       85296 :                 SS += W[i] * (integrand(XM + DX) + integrand(XM - DX));
-      81             :         }
-      82       10661 :         return XR * SS;
-      83             : }
-      84             : 
-      85             : } // namespace crpropa
-      86             : 
-      87             : #endif // CRPROPA_COMMON_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html b/doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html deleted file mode 100644 index a2a1cc9dd..000000000 --- a/doc/coverageReport/include/crpropa/EmissionMap.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/EmissionMap.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - EmissionMap.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/EmissionMap.h.func.html b/doc/coverageReport/include/crpropa/EmissionMap.h.func.html deleted file mode 100644 index fd1749d15..000000000 --- a/doc/coverageReport/include/crpropa/EmissionMap.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/EmissionMap.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - EmissionMap.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html b/doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html deleted file mode 100644 index deeb84f2e..000000000 --- a/doc/coverageReport/include/crpropa/EmissionMap.h.gcov.html +++ /dev/null @@ -1,212 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/EmissionMap.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - EmissionMap.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_EMISSION_MAP_H
-       2             : #define CRPROPA_EMISSION_MAP_H
-       3             : 
-       4             : #include "Referenced.h"
-       5             : #include "Candidate.h"
-       6             : 
-       7             : namespace crpropa {
-       8             : 
-       9             : /**
-      10             :  @class CylindricalProjectionMap
-      11             :  @brief 2D histogram of spherical coordinates in equal-area projection
-      12             :  */
-      13             : class CylindricalProjectionMap : public Referenced {
-      14             : private:
-      15             :         size_t nPhi, nTheta;
-      16             :         double sPhi, sTheta;
-      17             :         mutable bool dirty;
-      18             :         std::vector<double> pdf;
-      19             :         mutable std::vector<double> cdf;
-      20             : 
-      21             :         /** Calculate the cdf from the pdf */
-      22             :         void updateCdf() const;
-      23             : 
-      24             : public:
-      25             :         CylindricalProjectionMap();
-      26             :         /** constructur
-      27             :          * @param nPhi number of bins for phi (0-2pi)
-      28             :          * @param nTheta number of bins for theta (0-pi)
-      29             :          */
-      30             :         CylindricalProjectionMap(size_t nPhi, size_t nTheta);
-      31             : 
-      32             :         /** Increment the bin value in direction by weight. */
-      33             :         void fillBin(const Vector3d& direction, double weight = 1.);
-      34             : 
-      35             :         /** Increment the bin value by weight. */
-      36             :         void fillBin(size_t bin, double weight = 1.);
-      37             : 
-      38             :         /** Draw a random vector from the distribution. */
-      39             :         Vector3d drawDirection() const;
-      40             : 
-      41             :         /** Check if the direction has a non zero propabiliy. */
-      42             :         bool checkDirection(const Vector3d &direction) const;
-      43             : 
-      44             :         const std::vector<double>& getPdf() const;
-      45             :         std::vector<double>& getPdf();
-      46             : 
-      47             :         const std::vector<double>& getCdf() const;
-      48             : 
-      49             :         size_t getNPhi();
-      50             :         size_t getNTheta();
-      51             : 
-      52             :         /** Calculate the bin from a direction */
-      53             :         size_t binFromDirection(const Vector3d& direction) const;
-      54             : 
-      55             :         /** Calculate a random vector inside the bin boundaries */
-      56             :         Vector3d directionFromBin(size_t bin) const;
-      57             : };
-      58             : 
-      59             : /**
-      60             :  @class EmissionMap
-      61             :  @brief Particle Type and energy binned emission maps.
-      62             : 
-      63             :  Use SourceEmissionMap to suppress directions at the source. Use EmissionMapFiller to create EmissionMap from Observer.
-      64             :  */
-      65           2 : class EmissionMap : public Referenced {
-      66             : public:
-      67             :         typedef std::pair<int, size_t> key_t;
-      68             :         typedef std::map<key_t, ref_ptr<CylindricalProjectionMap> > map_t;
-      69             : 
-      70             :         EmissionMap();
-      71             :         /**
-      72             :          * @param nPhi number of bins for phi (0-2pi)
-      73             :          * @param nTheta number of bins for theta (0-pi)
-      74             :          * @param nEnergy number of bins for energy (1e-4 - 1e4 EeV)
-      75             :          */
-      76             :         EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy);
-      77             : 
-      78             :         /**
-      79             :          * @param nPhi number of bins for phi (0-2pi)
-      80             :          * @param nTheta number of bins for theta (0-pi)
-      81             :          * @param nEnergy number of bins for energy (1e-4 - 1e4 EeV)
-      82             :          * @param minEnergy minimum energy for binning
-      83             :          * @param maxEnergy maximum energy for binning
-      84             :          */
-      85             :         EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy, double minEnergy, double maxEnergy);
-      86             : 
-      87             :         /** Calculate energy from bin */
-      88             :         double energyFromBin(size_t bin) const;
-      89             : 
-      90             :         /** Calculate bin from energy */
-      91             :         size_t binFromEnergy(double energy) const;
-      92             : 
-      93             :         map_t &getMaps();
-      94             :         const map_t &getMaps() const;
-      95             : 
-      96             :         /** Increment the value for particle type, energy and direction by weight. */
-      97             :         void fillMap(int pid, double energy, const Vector3d& direction, double weight = 1.);
-      98             :         /** Increment the value for the particle state by weight. */
-      99             :         void fillMap(const ParticleState& state, double weight = 1.);
-     100             : 
-     101             :         /** Draw a random vector from the distribution. */
-     102             :         bool drawDirection(int pid, double energy, Vector3d& direction) const;
-     103             :         /** Draw a random vector from the distribution. */
-     104             :         bool drawDirection(const ParticleState& state, Vector3d& direction) const;
-     105             : 
-     106             :         /** Check if the direction has a non zero propabiliy. */
-     107             :         bool checkDirection(int pid, double energy, const Vector3d& direction) const;
-     108             :         /** Check if the direction has a non zero propabiliy. */
-     109             :         bool checkDirection(const ParticleState& state) const;
-     110             : 
-     111             :         /** Check if a valid map exists */
-     112             :         bool hasMap(int pid, double energy);
-     113             : 
-     114             :         /** Get the map for the specified pid and energy */
-     115             :         ref_ptr<CylindricalProjectionMap> getMap(int pid, double energy);
-     116             : 
-     117             :         /** Save the content of the maps into a text file */
-     118             :         void save(const std::string &filename);
-     119             :         /** Load the content of the maps from a text file */
-     120             :         void load(const std::string &filename);
-     121             : 
-     122             :         /** Merge other maps, add pdfs */
-     123             :         void merge(const EmissionMap *other);
-     124             : 
-     125             :         /** Merge maps from file */
-     126             :         void merge(const std::string &filename);
-     127             : 
-     128             : protected:
-     129             :         double minEnergy, maxEnergy, logStep;
-     130             :         size_t nPhi, nTheta, nEnergy;
-     131             :         map_t maps;
-     132             : };
-     133             : 
-     134             : } // namespace crpropa
-     135             : 
-     136             : #endif // CRPROPA_EMISSION_MAP_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html deleted file mode 100644 index 6b4cfc036..000000000 --- a/doc/coverageReport/include/crpropa/Geometry.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Geometry.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Geometry.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3475.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa7Surface14getDescriptionB5cxx11Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Geometry.h.func.html b/doc/coverageReport/include/crpropa/Geometry.h.func.html deleted file mode 100644 index 9e2e188ad..000000000 --- a/doc/coverageReport/include/crpropa/Geometry.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Geometry.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Geometry.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3475.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa7Surface14getDescriptionB5cxx11Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Geometry.h.gcov.html b/doc/coverageReport/include/crpropa/Geometry.h.gcov.html deleted file mode 100644 index f7e267162..000000000 --- a/doc/coverageReport/include/crpropa/Geometry.h.gcov.html +++ /dev/null @@ -1,165 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Geometry.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Geometry.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3475.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_GEOMETRY_H
-       2             : #define CRPROPA_GEOMETRY_H
-       3             : 
-       4             : #include <vector>
-       5             : #include <string>
-       6             : 
-       7             : #include "crpropa/Candidate.h"
-       8             : #include "crpropa/Vector3.h"
-       9             : #include "crpropa/Referenced.h"
-      10             : 
-      11             : namespace crpropa {
-      12             : /**
-      13             :  * \addtogroup Core
-      14             :  * @{
-      15             :  */
-      16             : 
-      17             : /**
-      18             :  @class Surface
-      19             :  @brief A geometrical surface
-      20             : 
-      21             :  Defines a surface. Can be queried if the candidate has crossed the surface in the last step.
-      22             :  */
-      23             : class Surface : public Referenced {
-      24             : public:
-      25             :         /** Returns the distance of a point to the surface. Negative on the one side,
-      26             :          positive on the other. For closed surfaces it is negative on the inside.
-      27             :          @param point   vector corresponding to the point to which compute the distance
-      28             :          */
-      29             :         virtual double distance(const Vector3d& point) const = 0;
-      30             :         /**  Returns the normal to the surface at a point. Negative on the one side,
-      31             :          positive on the other. For closed surfaces it is negative on the inside.
-      32             :          @param point   vector corresponding to the point to which compute the normal vector
-      33             :          */
-      34             :         virtual Vector3d normal(const Vector3d& point) const = 0;
-      35           0 :         virtual std::string getDescription() const {return "Surface without description.";};
-      36             : };
-      37             : 
-      38             : 
-      39             : /**
-      40             :  @class Plane
-      41             :  @brief A plane given by a point x0 and two axes v1 and v2 with normal n = v1.cross(v2) or the normal n. Note that distance is negative on one side of the plane and positive on the other, depending on the orientation of the normal vector.
-      42             :  */
-      43           1 : class Plane: public Surface {
-      44             : private:
-      45             :         Vector3d x0, n;
-      46             : public:
-      47             :         Plane(const Vector3d& x0, const Vector3d& v1,const Vector3d& v2);
-      48             :         Plane(const Vector3d& x0, const Vector3d& n);
-      49             :         virtual double distance(const Vector3d &x) const;
-      50             :         virtual Vector3d normal(const Vector3d& point) const;
-      51             :         virtual std::string getDescription() const;
-      52             : };
-      53             : 
-      54             : 
-      55             : /**
-      56             :  @class Sphere
-      57             :  @brief A sphere around point _center with radius _radius.
-      58             :  */
-      59           1 : class Sphere: public Surface {
-      60             : private:
-      61             :         Vector3d center;
-      62             :         double radius;
-      63             : public:
-      64             :         Sphere(const Vector3d& center, double radius);
-      65             :         virtual double distance(const Vector3d &point) const;
-      66             :         virtual Vector3d normal(const Vector3d& point) const;
-      67             :         virtual std::string getDescription() const;
-      68             : };
-      69             : 
-      70             : 
-      71             : /**
-      72             :  @class ParaxialBox
-      73             :  @brief A box with perpendicular surfaces aligned to the x,y,z-axes.
-      74             :  */
-      75           1 : class ParaxialBox: public Surface {
-      76             : private:
-      77             :         Vector3d corner, size;
-      78             : public:
-      79             :         ParaxialBox(const Vector3d& corner, const Vector3d& size);
-      80             :         virtual double distance(const Vector3d &point) const;
-      81             :         virtual Vector3d normal(const Vector3d& point) const;
-      82             :         virtual std::string getDescription() const;
-      83             : };
-      84             : 
-      85             : 
-      86             : /** @}*/
-      87             : } // namespace crpropa
-      88             : 
-      89             : #endif // CRPROPA_GEOMETRY_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html deleted file mode 100644 index 3c651a9f5..000000000 --- a/doc/coverageReport/include/crpropa/Grid.h.func-sort-c.html +++ /dev/null @@ -1,296 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Grid.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Grid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:17319588.7 %
Date:2024-04-08 14:58:22Functions:235641.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14GridPropertiesD2Ev0
_ZN7crpropa4GridINS_7Vector3IdEEE11interpolateERKS2_0
_ZN7crpropa4GridINS_7Vector3IdEEE11setGridSizeEmmm0
_ZN7crpropa4GridINS_7Vector3IdEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_md0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmS2_0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmd0
_ZN7crpropa4GridINS_7Vector3IfEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmS4_0
_ZN7crpropa4GridIdE11interpolateERKNS_7Vector3IdEE0
_ZN7crpropa4GridIdE11setGridSizeEmmm0
_ZN7crpropa4GridIdE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmd0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmS3_0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmd0
_ZN7crpropa4GridIdEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridIfE20setInterpolationTypeENS_17interpolationTypeE0
_ZNK7crpropa4GridINS_7Vector3IdEEE12closestValueERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE17positionFromIndexEi0
_ZNK7crpropa4GridINS_7Vector3IdEEE17simdreflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE19tricubicInterpolateENS1_IfEERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE20trilinearInterpolateERKS2_0
_ZNK7crpropa4GridINS_7Vector3IfEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IfEEE17positionFromIndexEi0
_ZNK7crpropa4GridIdE12closestValueERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE13reflectiveGetEmmm0
_ZNK7crpropa4GridIdE17positionFromIndexEi0
_ZNK7crpropa4GridIdE19tricubicInterpolateEdRKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE20trilinearInterpolateERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE22CubicInterpolateScalarEddddd0
_ZNK7crpropa4GridIfE13reflectiveGetEmmm0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmd1
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmS3_1
_ZN7crpropa14GridPropertiesD0Ev2
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmd2
_ZN7crpropa4GridIfEC2ERKNS_14GridPropertiesE3
_ZNK7crpropa4GridIfE19tricubicInterpolateEdRKNS_7Vector3IdEE3
_ZN7crpropa4GridINS_7Vector3IfEEEC2ERKNS_14GridPropertiesE6
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmd6
_ZNK7crpropa4GridIfE12closestValueERKNS_7Vector3IdEE7
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmd9
_ZNK7crpropa4GridIfE20trilinearInterpolateERKNS_7Vector3IdEE9
_ZNK7crpropa4GridINS_7Vector3IfEEE12closestValueERKNS1_IdEE10
_ZN7crpropa4GridIfE11setGridSizeEmmm12
_ZNK7crpropa4GridINS_7Vector3IfEEE19tricubicInterpolateES2_RKNS1_IdEE15
_ZN7crpropa4GridINS_7Vector3IfEEE11setGridSizeEmmm16
_ZN7crpropa4GridIfE11interpolateERKNS_7Vector3IdEE18
_ZN7crpropa15reflectiveClampEdiRiS0_Rd20
_ZN7crpropa5roundEd51
_ZNK7crpropa4GridIfE22CubicInterpolateScalarEddddd63
_ZNK7crpropa4GridINS_7Vector3IfEEE17simdreflectiveGetEmmm384
_ZNK7crpropa4GridIfE17positionFromIndexEi10103
_ZNK7crpropa4GridINS_7Vector3IfEEE20trilinearInterpolateERKNS1_IdEE100046
_ZN7crpropa4GridINS_7Vector3IfEEE11interpolateERKNS1_IdEE100073
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Grid.h.func.html b/doc/coverageReport/include/crpropa/Grid.h.func.html deleted file mode 100644 index 0b9457ac3..000000000 --- a/doc/coverageReport/include/crpropa/Grid.h.func.html +++ /dev/null @@ -1,296 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Grid.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Grid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:17319588.7 %
Date:2024-04-08 14:58:22Functions:235641.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14GridPropertiesD0Ev2
_ZN7crpropa14GridPropertiesD2Ev0
_ZN7crpropa15reflectiveClampEdiRiS0_Rd20
_ZN7crpropa4GridINS_7Vector3IdEEE11interpolateERKS2_0
_ZN7crpropa4GridINS_7Vector3IdEEE11setGridSizeEmmm0
_ZN7crpropa4GridINS_7Vector3IdEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_md0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmS2_0
_ZN7crpropa4GridINS_7Vector3IdEEEC2ES2_mmmd0
_ZN7crpropa4GridINS_7Vector3IfEEE11interpolateERKNS1_IdEE100073
_ZN7crpropa4GridINS_7Vector3IfEEE11setGridSizeEmmm16
_ZN7crpropa4GridINS_7Vector3IfEEE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmd9
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmS4_0
_ZN7crpropa4GridINS_7Vector3IfEEEC2ENS1_IdEEmmmd1
_ZN7crpropa4GridINS_7Vector3IfEEEC2ERKNS_14GridPropertiesE6
_ZN7crpropa4GridIdE11interpolateERKNS_7Vector3IdEE0
_ZN7crpropa4GridIdE11setGridSizeEmmm0
_ZN7crpropa4GridIdE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmd0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmS3_0
_ZN7crpropa4GridIdEC2ENS_7Vector3IdEEmmmd0
_ZN7crpropa4GridIdEC2ERKNS_14GridPropertiesE0
_ZN7crpropa4GridIfE11interpolateERKNS_7Vector3IdEE18
_ZN7crpropa4GridIfE11setGridSizeEmmm12
_ZN7crpropa4GridIfE20setInterpolationTypeENS_17interpolationTypeE0
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmd2
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmS3_1
_ZN7crpropa4GridIfEC2ENS_7Vector3IdEEmmmd6
_ZN7crpropa4GridIfEC2ERKNS_14GridPropertiesE3
_ZN7crpropa5roundEd51
_ZNK7crpropa4GridINS_7Vector3IdEEE12closestValueERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE17positionFromIndexEi0
_ZNK7crpropa4GridINS_7Vector3IdEEE17simdreflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IdEEE19tricubicInterpolateENS1_IfEERKS2_0
_ZNK7crpropa4GridINS_7Vector3IdEEE20trilinearInterpolateERKS2_0
_ZNK7crpropa4GridINS_7Vector3IfEEE12closestValueERKNS1_IdEE10
_ZNK7crpropa4GridINS_7Vector3IfEEE13reflectiveGetEmmm0
_ZNK7crpropa4GridINS_7Vector3IfEEE17positionFromIndexEi0
_ZNK7crpropa4GridINS_7Vector3IfEEE17simdreflectiveGetEmmm384
_ZNK7crpropa4GridINS_7Vector3IfEEE19tricubicInterpolateES2_RKNS1_IdEE15
_ZNK7crpropa4GridINS_7Vector3IfEEE20trilinearInterpolateERKNS1_IdEE100046
_ZNK7crpropa4GridIdE12closestValueERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE13reflectiveGetEmmm0
_ZNK7crpropa4GridIdE17positionFromIndexEi0
_ZNK7crpropa4GridIdE19tricubicInterpolateEdRKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE20trilinearInterpolateERKNS_7Vector3IdEE0
_ZNK7crpropa4GridIdE22CubicInterpolateScalarEddddd0
_ZNK7crpropa4GridIfE12closestValueERKNS_7Vector3IdEE7
_ZNK7crpropa4GridIfE13reflectiveGetEmmm0
_ZNK7crpropa4GridIfE17positionFromIndexEi10103
_ZNK7crpropa4GridIfE19tricubicInterpolateEdRKNS_7Vector3IdEE3
_ZNK7crpropa4GridIfE20trilinearInterpolateERKNS_7Vector3IdEE9
_ZNK7crpropa4GridIfE22CubicInterpolateScalarEddddd63
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Grid.h.gcov.html b/doc/coverageReport/include/crpropa/Grid.h.gcov.html deleted file mode 100644 index cad5f1688..000000000 --- a/doc/coverageReport/include/crpropa/Grid.h.gcov.html +++ /dev/null @@ -1,640 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Grid.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Grid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:17319588.7 %
Date:2024-04-08 14:58:22Functions:235641.1 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_GRID_H
-       2             : #define CRPROPA_GRID_H
-       3             : 
-       4             : #include "crpropa/Referenced.h"
-       5             : #include "crpropa/Vector3.h"
-       6             : 
-       7             : #include "kiss/string.h"
-       8             : #include "kiss/logger.h"
-       9             : 
-      10             : #include <vector>
-      11             : #include <type_traits>
-      12             : #if HAVE_SIMD
-      13             : #include <immintrin.h>
-      14             : #include <smmintrin.h>
-      15             : #endif // HAVE_SIMD
-      16             : 
-      17             : namespace crpropa {
-      18             : 
-      19             : /** If set to TRILINEAR, use trilinear interpolation (standard)
-      20             : If set to TRICUBIC, use tricubic interpolation instead of trilinear interpolation
-      21             : If set to NEAREST_NEIGHBOUR , use nearest neighbour interpolation instead of trilinear interpolation */
-      22             : enum interpolationType {
-      23             :   TRILINEAR = 0,
-      24             :   TRICUBIC,
-      25             :   NEAREST_NEIGHBOUR
-      26             : };
-      27             : 
-      28             : /** Lower and upper neighbour in a periodically continued unit grid */
-      29             : inline void periodicClamp(double x, int n, int &lo, int &hi) {
-      30      100051 :         lo = ((int(floor(x)) % (n)) + (n)) % (n);
-      31          10 :         hi = (lo + 1) % (n);
-      32             : }
-      33             : 
-      34             : /** grid index in a reflective continued unit grid */
-      35             : inline int reflectiveBoundary(int index, int n) {
-      36        1963 :         while ((index < -0.5) or (index > (n-0.5)))
-      37         806 :                 index = 2 * n * (index > (n-0.5)) - index-1;
-      38             :         return index;
-      39             : }
-      40             : 
-      41             : /** grid index in a periodically continued unit grid */
-      42             : inline int periodicBoundary(int index, int n) {
-      43         768 :         return ((index % (n)) + (n)) % (n);
-      44             : }
-      45             : 
-      46             : /** Lower and upper neighbour in a reflectively repeated unit grid */
-      47          20 : inline void reflectiveClamp(double x, int n, int &lo, int &hi, double &res) {
-      48          36 :         while ((x < -0.5) or (x > (n-0.5)))
-      49          16 :                 x = 2 * n * (x > (n-0.5)) -x-1;
-      50          20 :         res = x;
-      51          20 :         lo = floor(x);
-      52          20 :         hi = lo + (lo < n-1);
-      53          20 :         if (x<0) {
-      54          10 :                 lo=0; 
-      55          10 :                 hi=0;
-      56             :         }
-      57          20 : }
-      58             : 
-      59             : /** Symmetrical round */
-      60          51 : inline double round(double r) {
-      61          51 :         return (r > 0.0) ? floor(r + 0.5) : ceil(r - 0.5);
-      62             : }
-      63             : 
-      64             : /**
-      65             :  * \addtogroup Core
-      66             :  * @{
-      67             :  */
-      68             : 
-      69             : /**
-      70             :  @class GridProperties
-      71             :  @brief Combines parameters that uniquely define Grid class
-      72             :  */
-      73             : class GridProperties: public Referenced {
-      74             : public:
-      75             :         size_t Nx, Ny, Nz;      // Number of grid points
-      76             :         Vector3d origin;        // Position of the lower left front corner of the volume
-      77             :         Vector3d spacing;       // Spacing vector between gridpoints
-      78             :         bool reflective;        // using reflective repetition of the grid instead of periodic
-      79             :         interpolationType ipol; // Interpolation type used between grid points
-      80             :         bool clipVolume;        // Set grid values to 0 outside the volume if true
-      81             : 
-      82             :         /** Constructor for cubic grid
-      83             :          @param origin  Position of the lower left front corner of the volume
-      84             :          @param N               Number of grid points in one direction
-      85             :          @param spacing Spacing between grid points
-      86             :          */
-      87           6 :         GridProperties(Vector3d origin, size_t N, double spacing) :
-      88           6 :                 origin(origin), Nx(N), Ny(N), Nz(N), spacing(Vector3d(spacing)), reflective(false), ipol(TRILINEAR), clipVolume(false) {
-      89             :         }
-      90             : 
-      91             :         /** Constructor for non-cubic grid
-      92             :          @param origin  Position of the lower left front corner of the volume
-      93             :          @param Nx              Number of grid points in x-direction
-      94             :          @param Ny              Number of grid points in y-direction
-      95             :          @param Nz              Number of grid points in z-direction
-      96             :          @param spacing Spacing between grid points
-      97             :          */
-      98           0 :         GridProperties(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, double spacing) :
-      99           0 :                 origin(origin), Nx(Nx), Ny(Ny), Nz(Nz), spacing(Vector3d(spacing)), reflective(false), ipol(TRILINEAR), clipVolume(false) {
-     100             :         }
-     101             : 
-     102             :         /** Constructor for non-cubic grid with spacing vector
-     103             :          @param origin  Position of the lower left front corner of the volume
-     104             :          @param Nx              Number of grid points in x-direction
-     105             :          @param Ny              Number of grid points in y-direction
-     106             :          @param Nz              Number of grid points in z-direction
-     107             :          @param spacing Spacing vector between grid points
-     108             :         */
-     109           1 :         GridProperties(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, Vector3d spacing) :
-     110           1 :                 origin(origin), Nx(Nx), Ny(Ny), Nz(Nz), spacing(spacing), reflective(false), ipol(TRILINEAR), clipVolume(false) {
-     111             :         }
-     112             :         
-     113           2 :         virtual ~GridProperties() {
-     114           4 :         }
-     115             :         
-     116             :         /** If True, the repetition of the grid is refletive instead of periodic. */
-     117             :         void setReflective(bool b) {
-     118           0 :                 reflective = b;
-     119             :         }
-     120             : 
-     121             :         /** set the type of interpolation between grid points.
-     122             :          * @param i: interpolationType (TRILINEAR, TRICUBIC, NEAREST_NEIGHBOUR) */
-     123             :         void setInterpolationType(interpolationType i) {
-     124           0 :                 ipol = i;
-     125             :         }
-     126             : 
-     127             :         /** If True, the grid is set to zero outside of the volume. */
-     128             :         void setClipVolume(bool b) {
-     129           0 :                 clipVolume = b;
-     130             :         }
-     131             : };
-     132             : 
-     133             : /**
-     134             :  @class Grid
-     135             :  @brief Template class for fields on a periodic grid with trilinear interpolation
-     136             : 
-     137             :  The grid spacing is constant with diffrent resolution along all three axes.
-     138             :  Values are calculated by trilinear interpolation of the surrounding 8 grid points.
-     139             :  The grid is periodically (default) or reflectively extended.
-     140             :  The grid sample positions are at 1/2 * size/N, 3/2 * size/N ... (2N-1)/2 * size/N.
-     141             :  */
-     142             : template<typename T>
-     143          17 : class Grid: public Referenced {
-     144             :         std::vector<T> grid;
-     145             :         size_t Nx, Ny, Nz; /**< Number of grid points */
-     146             :         Vector3d origin; /**< Origin of the volume that is represented by the grid. */
-     147             :         Vector3d gridOrigin; /**< Grid origin */
-     148             :         Vector3d spacing; /**< Distance between grid points, determines the extension of the grid */
-     149             :         bool clipVolume; /**< If set to true, all values outside of the grid will be 0*/
-     150             :         bool reflective; /**< If set to true, the grid is repeated reflectively instead of periodically */
-     151             :         interpolationType ipolType; /**< Type of interpolation between the grid points */
-     152             : 
-     153             : public:
-     154             :         /** Constructor for cubic grid
-     155             :          @param origin  Position of the lower left front corner of the volume
-     156             :          @param N               Number of grid points in one direction
-     157             :          @param spacing Spacing between grid points
-     158             :          */
-     159          11 :         Grid(Vector3d origin, size_t N, double spacing) {
-     160             :                 setOrigin(origin);
-     161          11 :                 setGridSize(N, N, N);
-     162             :                 setSpacing(Vector3d(spacing));
-     163             :                 setReflective(false);
-     164             :                 setClipVolume(false);
-     165             :                 setInterpolationType(TRILINEAR);
-     166          11 :         }
-     167             : 
-     168             :         /** Constructor for non-cubic grid
-     169             :          @param origin  Position of the lower left front corner of the volume
-     170             :          @param Nx              Number of grid points in x-direction
-     171             :          @param Ny              Number of grid points in y-direction
-     172             :          @param Nz              Number of grid points in z-direction
-     173             :          @param spacing Spacing between grid points
-     174             :          */
-     175           7 :         Grid(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, double spacing) {
-     176             :                 setOrigin(origin);
-     177           7 :                 setGridSize(Nx, Ny, Nz);
-     178             :                 setSpacing(Vector3d(spacing));
-     179             :                 setReflective(false);
-     180             :                 setClipVolume(false);
-     181             :                 setInterpolationType(TRILINEAR);
-     182           7 :         }
-     183             : 
-     184             :         /** Constructor for non-cubic grid with spacing vector
-     185             :          @param origin  Position of the lower left front corner of the volume
-     186             :          @param Nx              Number of grid points in x-direction
-     187             :          @param Ny              Number of grid points in y-direction
-     188             :          @param Nz              Number of grid points in z-direction
-     189             :          @param spacing Spacing vector between grid points
-     190             :         */
-     191           1 :         Grid(Vector3d origin, size_t Nx, size_t Ny, size_t Nz, Vector3d spacing) {
-     192             :                 setOrigin(origin);
-     193           1 :                 setGridSize(Nx, Ny, Nz);
-     194             :                 setSpacing(spacing);
-     195             :                 setReflective(false);
-     196             :                 setClipVolume(false);
-     197             :                 setInterpolationType(TRILINEAR);
-     198           1 :         }
-     199             : 
-     200             :         /** Constructor for GridProperties
-     201             :          @param p       GridProperties instance
-     202             :      */
-     203           9 :         Grid(const GridProperties &p) :
-     204           9 :                 origin(p.origin), spacing(p.spacing), reflective(p.reflective), ipolType(p.ipol) {
-     205           9 :                 setGridSize(p.Nx, p.Ny, p.Nz);
-     206           9 :                 setClipVolume(p.clipVolume);
-     207           9 :         }
-     208             : 
-     209             :         void setOrigin(Vector3d origin) {
-     210             :                 this->origin = origin;
-     211             :                 this->gridOrigin = origin + spacing/2;
-     212             :         }
-     213             : 
-     214             :         /** Resize grid, also enlarges the volume as the spacing stays constant */
-     215          28 :         void setGridSize(size_t Nx, size_t Ny, size_t Nz) {
-     216          28 :                 this->Nx = Nx;
-     217          28 :                 this->Ny = Ny;
-     218          28 :                 this->Nz = Nz;
-     219          28 :                 grid.resize(Nx * Ny * Nz);
-     220             :                 setOrigin(origin);
-     221          28 :         }
-     222             : 
-     223             :         void setSpacing(Vector3d spacing) {
-     224             :                 this->spacing = spacing;
-     225             :                 setOrigin(origin);
-     226             :         }
-     227             : 
-     228             :         void setReflective(bool b) {
-     229           8 :                 reflective = b;
-     230             :         }
-     231             : 
-     232             :         // If set to true, all values outside of the grid will be 0.
-     233             :         void setClipVolume(bool b) {
-     234          21 :                 clipVolume = b;
-     235             :         }
-     236             : 
-     237             :         /** Change the interpolation type to the routine specified by the user. Check if this routine is
-     238             :                 contained in the enum interpolationType and thus supported by CRPropa.*/
-     239           0 :         void setInterpolationType(interpolationType ipolType) {
-     240           0 :                 if (ipolType == TRILINEAR || ipolType == TRICUBIC || ipolType == NEAREST_NEIGHBOUR) {
-     241          30 :                         this->ipolType = ipolType;
-     242           0 :                         if ((ipolType == TRICUBIC) && (std::is_same<T, Vector3d>::value)) {
-     243           0 :                                 KISS_LOG_WARNING << "Tricubic interpolation on Grid3d works only with float-precision, doubles will be downcasted";
-     244             :                 }
-     245             :                 } else {
-     246           0 :                         throw std::runtime_error("InterpolationType: unknown interpolation type");
-     247             :                 }
-     248           0 :         }
-     249             : 
-     250             :         /** returns the position of the lower left front corner of the volume */
-     251             :         Vector3d getOrigin() const {
-     252             :                 return origin;
-     253             :         }
-     254             : 
-     255             :         bool getClipVolume() const {
-     256           0 :                 return clipVolume;
-     257             :         }
-     258             : 
-     259             :         size_t getNx() const {
-     260         728 :                 return Nx;
-     261             :         }
-     262             : 
-     263             :         size_t getNy() const {
-     264       41792 :                 return Ny;
-     265             :         }
-     266             : 
-     267             :         size_t getNz() const {
-     268     2663721 :                 return Nz;
-     269             :         }
-     270             : 
-     271             :         /** Calculates the total size of the grid in bytes */
-     272             :         size_t getSizeOf() const {
-     273           0 :                 return sizeof(grid) + (sizeof(grid[0]) * grid.size());
-     274             :         }
-     275             : 
-     276             :         Vector3d getSpacing() const {
-     277             :                 return spacing;
-     278             :         }
-     279             : 
-     280             :         bool isReflective() const {
-     281           0 :                 return reflective;
-     282             :         }
-     283             : 
-     284             :         /** Choose the interpolation algorithm based on the set interpolation type.
-     285             :           By default this it the trilinear interpolation. The user can change the
-     286             :           routine with the setInterpolationType function.*/
-     287      100091 :         T interpolate(const Vector3d &position) {
-     288             :                 // check for volume
-     289      100091 :                 if (clipVolume) {
-     290           5 :                         Vector3d edge = origin + Vector3d(Nx, Ny, Nz) * spacing;
-     291           5 :                         bool isInVolume = (position.x >= origin.x) && (position.x <= edge.x);
-     292           5 :                         isInVolume &= (position.y >= origin.y) && (position.y <= edge.y);
-     293           5 :                         isInVolume &= (position.z >= origin.z) && (position.z <= edge.z);
-     294           5 :                         if (!isInVolume) 
-     295             :                                 return T(0.);
-     296             :                 } 
-     297             : 
-     298      100086 :                 if (ipolType == TRICUBIC)
-     299          18 :                         return tricubicInterpolate(T(), position);
-     300      100068 :                 else if (ipolType == NEAREST_NEIGHBOUR)
-     301          13 :                         return closestValue(position);
-     302             :                 else
-     303      100055 :                         return trilinearInterpolate(position);
-     304             :         }
-     305             : 
-     306             :         /** Inspector & Mutator */
-     307             :         T &get(size_t ix, size_t iy, size_t iz) {
-     308     8391022 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
-     309             :         }
-     310             : 
-     311             :         /** Inspector */
-     312             :         const T &get(size_t ix, size_t iy, size_t iz) const {
-     313      100072 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
-     314             :         }
-     315             : 
-     316             :         const T &periodicGet(size_t ix, size_t iy, size_t iz) const {
-     317         192 :                 ix = periodicBoundary(ix, Nx);
-     318         192 :                 iy = periodicBoundary(iy, Ny);
-     319         192 :                 iz = periodicBoundary(iz, Nz);
-     320         192 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
-     321             :         }
-     322             : 
-     323           0 :         const T &reflectiveGet(size_t ix, size_t iy, size_t iz) const {
-     324           0 :                 ix = reflectiveBoundary(ix, Nx);
-     325           0 :                 iy = reflectiveBoundary(iy, Ny);
-     326           0 :                 iz = reflectiveBoundary(iz, Nz);
-     327           0 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
-     328             :         }
-     329             : 
-     330             :         T getValue(size_t ix, size_t iy, size_t iz) {
-     331           0 :                 return grid[ix * Ny * Nz + iy * Nz + iz];
-     332             :         }
-     333             : 
-     334             :         void setValue(size_t ix, size_t iy, size_t iz, T value) {
-     335           0 :                 grid[ix * Ny * Nz + iy * Nz + iz] = value;
-     336             :         }
-     337             : 
-     338             :         /** Return a reference to the grid values */
-     339             :         std::vector<T> &getGrid() {
-     340       10102 :                 return grid;
-     341             :         }
-     342             : 
-     343             :         /** Position of the grid point of a given index */
-     344       10103 :         Vector3d positionFromIndex(int index) const {
-     345       10103 :                 int ix = index / (Ny * Nz);
-     346       10103 :                 int iy = (index / Nz) % Ny;
-     347       10103 :                 int iz = index % Nz;
-     348       10103 :                 return Vector3d(ix, iy, iz) * spacing + gridOrigin;
-     349             :         }
-     350             : 
-     351             :         /** Value of a grid point that is closest to a given position / nearest neighbour interpolation */
-     352          17 :         T closestValue(const Vector3d &position) const {
-     353             :                 Vector3d r = (position - gridOrigin) / spacing;
-     354             :                 int ix, iy, iz;
-     355          17 :                 if (reflective) {
-     356           6 :                         ix = round(r.x);
-     357           6 :                         iy = round(r.y);
-     358           6 :                         iz = round(r.z);
-     359           9 :                         while ((ix < -0.5) or (ix > (Nx-0.5)))
-     360           3 :                                 ix = 2 * Nx * (ix > (Nx-0.5)) - ix-1;
-     361          11 :                         while ((iy < -0.5) or (iy > (Ny-0.5)))
-     362           5 :                                 iy = 2 * Ny * (iy > (Ny-0.5)) - iy-1;
-     363           9 :                         while ((iz < -0.5) or (iz > (Nz-0.5)))
-     364           3 :                                 iz = 2 * Nz * (iz > (Nz-0.5)) - iz-1;
-     365             :                 } else {
-     366          11 :                         ix = round(fmod(r.x, Nx));
-     367          11 :                         iy = round(fmod(r.y, Ny));
-     368          11 :                         iz = round(fmod(r.z, Nz));
-     369          11 :                         ix = (ix + Nx * (ix < 0)) % Nx;
-     370          11 :                         iy = (iy + Ny * (iy < 0)) % Ny;
-     371          11 :                         iz = (iz + Nz * (iz < 0)) % Nz;
-     372             :                 }
-     373          17 :                 return get(ix, iy, iz);
-     374             :         }
-     375             : 
-     376             : private:
-     377             :         #ifdef HAVE_SIMD
-     378             :         __m128 simdperiodicGet(size_t ix, size_t iy, size_t iz) const {
-     379         576 :                 ix = periodicBoundary(ix, Nx);
-     380         576 :                 iy = periodicBoundary(iy, Ny);
-     381         576 :                 iz = periodicBoundary(iz, Nz);
-     382         576 :                 return convertVector3fToSimd(grid[ix * Ny * Nz + iy * Nz + iz]);
-     383             :         }
-     384             : 
-     385         384 :         __m128 simdreflectiveGet(size_t ix, size_t iy, size_t iz) const {
-     386         384 :                 ix = reflectiveBoundary(ix, Nx);
-     387         384 :                 iy = reflectiveBoundary(iy, Ny);
-     388         384 :                 iz = reflectiveBoundary(iz, Nz);
-     389         384 :                 return convertVector3fToSimd(grid[ix * Ny * Nz + iy * Nz + iz]);
-     390             :         }
-     391             : 
-     392             :         __m128 convertVector3fToSimd(const Vector3f v) const {
-     393             :                 __m128 simdVar = _mm_set_ps(0,v.z,v.y,v.x);
-     394             :                 return simdVar;
-     395             :         }
-     396             :         
-     397             :         Vector3f convertSimdToVector3f(__m128 res) const {
-     398             :                 float vec[4];   
-     399             :                 _mm_store_ps(&vec[0], res);
-     400             :                 Vector3f result = Vector3f(vec[0], vec[1], vec[2]);
-     401             :                 return result;
-     402             :         }
-     403             : 
-     404             :         /** Vectorized cubic Interpolator in 1D */
-     405             :         __m128 CubicInterpolate(__m128 p0,__m128 p1,__m128 p2,__m128 p3,double position) const {
-     406             :                 __m128 c1 = _mm_set1_ps (1/2.);
-     407             :                 __m128 c2 = _mm_set1_ps (3/2.);
-     408             :                 __m128 c3 = _mm_set1_ps (2.);
-     409             :                 __m128 c4 = _mm_set1_ps (5/2.);
-     410             : 
-     411         315 :                 __m128 pos  = _mm_set1_ps (position);
-     412         315 :                 __m128 pos2 = _mm_set1_ps (position*position);
-     413         300 :                 __m128 pos3 = _mm_set1_ps (position*position*position);
-     414             : 
-     415             :                 /** SIMD optimized routine to calculate 'res = ((-0.5*p0+3/2.*p1-3/2.*p2+0.5*p3)*pos*pos*pos+(p0-5/2.*p1+p2*2-0.5*p3)*pos*pos+(-0.5*p0+0.5*p2)*pos+p1);'
-     416             :                          where terms are used as:
-     417             :                         term = (-0.5*p0+0.5*p2)*pos
-     418             :                         term2 = (p0-5/2.*p1+p2*2-0.5*p3)*pos*pos;
-     419             :                         term3 = (-0.5*p0+3/2.*p1-3/2.*p2+0.5*p3)*pos*pos*pos;  */
-     420             :                 __m128 term = _mm_mul_ps(_mm_sub_ps(_mm_mul_ps(c1,p2),_mm_mul_ps(c1,p0)),pos);
-     421             :                 __m128 term2 = _mm_mul_ps(_mm_sub_ps(_mm_add_ps(p0,_mm_mul_ps(c3,p2)),_mm_add_ps(_mm_mul_ps(c4,p1),_mm_mul_ps(c1,p3))),pos2);
-     422             :                 __m128 term3 = _mm_mul_ps(_mm_sub_ps(_mm_add_ps(_mm_mul_ps(c2,p1),_mm_mul_ps(c1,p3)),_mm_add_ps(_mm_mul_ps(c1,p0),_mm_mul_ps(c2,p2))),pos3);
-     423             :                 __m128 res = _mm_add_ps(_mm_add_ps(_mm_add_ps(term3,term2),term),p1);
-     424             :                 return res;
-     425             :         }
-     426             :         #endif // HAVE_SIMD
-     427             :         /** Interpolate the grid tricubic at a given position (see https://www.paulinternet.nl/?page=bicubic, http://graphics.cs.cmu.edu/nsp/course/15-462/Fall04/assts/catmullRom.pdf) */
-     428          15 :         Vector3f tricubicInterpolate(Vector3f, const Vector3d &position) const {
-     429             :                 #ifdef HAVE_SIMD
-     430             :                 // position on a unit grid
-     431             :                 Vector3d r = (position - gridOrigin) / spacing;
-     432             : 
-     433             :                 int iX0, iY0, iZ0;
-     434          15 :                 iX0 = floor(r.x);
-     435          15 :                 iY0 = floor(r.y);
-     436          15 :                 iZ0 = floor(r.z);
-     437             : 
-     438             :                 double fX, fY, fZ;
-     439          15 :                 fX = r.x - iX0;
-     440          15 :                 fY = r.y - iY0;
-     441          15 :                 fZ = r.z - iZ0;
-     442             : 
-     443             :                 int nrCubicInterpolations = 4;
-     444          15 :                 __m128 interpolateVaryX[nrCubicInterpolations];
-     445          15 :                 __m128 interpolateVaryY[nrCubicInterpolations];
-     446          15 :                 __m128 interpolateVaryZ[nrCubicInterpolations];
-     447             :                 /** Perform 1D interpolations while iterating in each for loop over the index of another direction */
-     448          75 :                 for (int iLoopX = -1; iLoopX < nrCubicInterpolations-1; iLoopX++) {
-     449         300 :                         for (int iLoopY = -1; iLoopY < nrCubicInterpolations-1; iLoopY++) {
-     450        1200 :                                 for (int iLoopZ = -1; iLoopZ < nrCubicInterpolations-1; iLoopZ++) {
-     451         960 :                                         if (reflective)
-     452         384 :                                                 interpolateVaryZ[iLoopZ+1] = simdreflectiveGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
-     453             :                                         else 
-     454         576 :                                                 interpolateVaryZ[iLoopZ+1] = simdperiodicGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
-     455             :                                 }
-     456         240 :                                 interpolateVaryY[iLoopY+1] = CubicInterpolate(interpolateVaryZ[0], interpolateVaryZ[1], interpolateVaryZ[2], interpolateVaryZ[3], fZ);
-     457             :                         }
-     458          60 :                         interpolateVaryX[iLoopX+1] = CubicInterpolate(interpolateVaryY[0], interpolateVaryY[1], interpolateVaryY[2], interpolateVaryY[3], fY);
-     459             :                 }
-     460          15 :                 __m128 result = CubicInterpolate(interpolateVaryX[0], interpolateVaryX[1], interpolateVaryX[2], interpolateVaryX[3], fX);
-     461          15 :                 return convertSimdToVector3f(result);
-     462             :                 #else // HAVE_SIMD
-     463             :                 throw std::runtime_error( "Tried to use tricubic Interpolation without SIMD_EXTENSION. SIMD Optimization is necessary for tricubic interpolation of vector grids.\n");
-     464             :                 #endif // HAVE_SIMD     
-     465          15 :         }
-     466             : 
-     467             :         /** Vectorized cubic Interpolator in 1D that returns a scalar (see https://www.paulinternet.nl/?page=bicubic, http://graphics.cs.cmu.edu/nsp/course/15-462/Fall04/assts/catmullRom.pdf) */
-     468          63 :         double CubicInterpolateScalar(double p0,double p1,double p2,double p3,double pos) const {
-     469          63 :                 return((-0.5*p0+3/2.*p1-3/2.*p2+0.5*p3)*pos*pos*pos+(p0-5/2.*p1+p2*2-0.5*p3)*pos*pos+(-0.5*p0+0.5*p2)*pos+p1);
-     470             :         }
-     471             : 
-     472             :   /** Interpolate the grid tricubic at a given position (see https://www.paulinternet.nl/?page=bicubic, http://graphics.cs.cmu.edu/nsp/course/15-462/Fall04/assts/catmullRom.pdf) */
-     473           3 :         double tricubicInterpolate(double, const Vector3d &position) const {
-     474             :                 /** position on a unit grid */
-     475             :                 Vector3d r = (position - gridOrigin) / spacing;
-     476             : 
-     477             :                 int iX0, iY0, iZ0;
-     478           3 :                 iX0 = floor(r.x);
-     479           3 :                 iY0 = floor(r.y);
-     480           3 :                 iZ0 = floor(r.z);
-     481             : 
-     482             :                 double fX, fY, fZ;
-     483           3 :                 fX = r.x - iX0;
-     484           3 :                 fY = r.y - iY0;
-     485           3 :                 fZ = r.z - iZ0;
-     486             : 
-     487             :                 int nrCubicInterpolations = 4;
-     488           3 :                 double interpolateVaryX[nrCubicInterpolations];
-     489           3 :                 double interpolateVaryY[nrCubicInterpolations];
-     490           3 :                 double interpolateVaryZ[nrCubicInterpolations];
-     491             :                 /** Perform 1D interpolations while iterating in each for loop over the index of another direction */
-     492          15 :                 for (int iLoopX = -1; iLoopX < nrCubicInterpolations-1; iLoopX++) {
-     493          60 :                         for (int iLoopY = -1; iLoopY < nrCubicInterpolations-1; iLoopY++) {
-     494         240 :                                 for (int iLoopZ = -1; iLoopZ < nrCubicInterpolations-1; iLoopZ++) {
-     495         192 :                                         if (reflective)
-     496           0 :                                                 interpolateVaryZ[iLoopZ+1] = reflectiveGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
-     497             :                                         else
-     498         192 :                                                 interpolateVaryZ[iLoopZ+1] = periodicGet(iX0+iLoopX, iY0+iLoopY, iZ0+iLoopZ);
-     499             :                                 }
-     500          48 :                                 interpolateVaryY[iLoopY+1] = CubicInterpolateScalar(interpolateVaryZ[0], interpolateVaryZ[1], interpolateVaryZ[2], interpolateVaryZ[3], fZ);
-     501             :                         }
-     502          12 :                         interpolateVaryX[iLoopX+1] = CubicInterpolateScalar(interpolateVaryY[0], interpolateVaryY[1], interpolateVaryY[2], interpolateVaryY[3], fY);
-     503             :                 }
-     504           3 :                 double result = CubicInterpolateScalar(interpolateVaryX[0], interpolateVaryX[1], interpolateVaryX[2], interpolateVaryX[3], fX);
-     505           3 :                 return result;
-     506           3 :         }
-     507             : 
-     508             :         /** Interpolate the grid trilinear at a given position */
-     509      100055 :         T trilinearInterpolate(const Vector3d &position) const {
-     510             :                 /** position on a unit grid */
-     511             :                 Vector3d r = (position - gridOrigin) / spacing;
-     512             : 
-     513             :                 /** indices of lower (0) and upper (1) neighbours. The neighbours span a grid
-     514             :                   with the origin at [iX0, iY0, iZ0] and the most distant corner [iX1, iY1, iZ1]. */
-     515             :                 int iX0, iX1, iY0, iY1, iZ0, iZ1;
-     516             :                 double resX, resY, resZ, fX0, fY0, fZ0;
-     517             : 
-     518      100055 :                 if (reflective) {
-     519           6 :                         reflectiveClamp(r.x, Nx, iX0, iX1, resX);
-     520           6 :                         reflectiveClamp(r.y, Ny, iY0, iY1, resY);
-     521           6 :                         reflectiveClamp(r.z, Nz, iZ0, iZ1, resZ);
-     522           6 :                         fX0 = resX - floor(resX);
-     523           6 :                         fY0 = resY - floor(resY);
-     524           6 :                         fZ0 = resZ - floor(resZ);
-     525             :                 } else {
-     526      100049 :                         periodicClamp(r.x, Nx, iX0, iX1);
-     527      100049 :                         periodicClamp(r.y, Ny, iY0, iY1);
-     528      100049 :                         periodicClamp(r.z, Nz, iZ0, iZ1);
-     529      100049 :                         fX0 = r.x - floor(r.x);
-     530      100049 :                         fY0 = r.y - floor(r.y);
-     531      100049 :                         fZ0 = r.z - floor(r.z);
-     532             :                 }
-     533             : 
-     534             :                 /** linear fraction to upper neighbours based on lower neighbours calculated above */
-     535      100055 :                 double fX1 = 1 - fX0;
-     536      100055 :                 double fY1 = 1 - fY0;
-     537      100055 :                 double fZ1 = 1 - fZ0;
-     538             : 
-     539             :                 /** trilinear interpolation (see http://paulbourke.net/miscellaneous/interpolation) */
-     540             :                 T b(0.);
-     541      100055 :                 b += get(iX0, iY0, iZ0) * fX1 * fY1 * fZ1;
-     542      100055 :                 b += get(iX1, iY0, iZ0) * fX0 * fY1 * fZ1;
-     543      100055 :                 b += get(iX0, iY1, iZ0) * fX1 * fY0 * fZ1;
-     544      100055 :                 b += get(iX0, iY0, iZ1) * fX1 * fY1 * fZ0;
-     545           9 :                 b += get(iX1, iY0, iZ1) * fX0 * fY1 * fZ0;
-     546           9 :                 b += get(iX0, iY1, iZ1) * fX1 * fY0 * fZ0;
-     547           9 :                 b += get(iX1, iY1, iZ0) * fX0 * fY0 * fZ1;
-     548           9 :                 b += get(iX1, iY1, iZ1) * fX0 * fY0 * fZ0;
-     549             : 
-     550      100055 :                 return b;
-     551             :         }
-     552             : 
-     553             : }; // class Grid
-     554             : 
-     555             : typedef Grid<double> Grid1d;
-     556             : typedef Grid<float> Grid1f;
-     557             : typedef Grid<Vector3f> Grid3f;
-     558             : typedef Grid<Vector3d> Grid3d;
-     559             : 
-     560             : /** @}*/
-     561             : 
-     562             : } // namespace crpropa
-     563             : 
-     564             : #endif // CRPROPA_GRID_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html deleted file mode 100644 index df316be7f..000000000 --- a/doc/coverageReport/include/crpropa/Logging.h.func-sort-c.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Logging.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Logging.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0180.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_Z10logWarningRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z11setLogLeveli0
_Z12setLogStreamRSo0
_Z7logInfoRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logDebugRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logErrorRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Logging.h.func.html b/doc/coverageReport/include/crpropa/Logging.h.func.html deleted file mode 100644 index 118e0b0b8..000000000 --- a/doc/coverageReport/include/crpropa/Logging.h.func.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Logging.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Logging.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0180.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_Z10logWarningRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z11setLogLeveli0
_Z12setLogStreamRSo0
_Z7logInfoRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logDebugRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_Z8logErrorRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Logging.h.gcov.html b/doc/coverageReport/include/crpropa/Logging.h.gcov.html deleted file mode 100644 index adb602fd6..000000000 --- a/doc/coverageReport/include/crpropa/Logging.h.gcov.html +++ /dev/null @@ -1,111 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Logging.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Logging.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0180.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_LOGGING_H
-       2             : #define CRPROPA_LOGGING_H
-       3             : 
-       4             : #include "crpropa/Version.h"
-       5             : 
-       6             : #include "kiss/logger.h"
-       7             : 
-       8             : #include <fstream>
-       9             : 
-      10             : // make the kiss log functions available in python
-      11           0 : void inline logError(const std::string &log) {
-      12           0 :         KISS_LOG_ERROR << log;
-      13           0 : }
-      14             : 
-      15           0 : void inline logInfo(const std::string &log) {
-      16           0 :         KISS_LOG_INFO << log;
-      17           0 : }
-      18             : 
-      19           0 : void inline logWarning(const std::string &log) {
-      20           0 :         KISS_LOG_WARNING << log;
-      21           0 : }
-      22             : 
-      23           0 : void inline logDebug(const std::string &log) {
-      24           0 :         KISS_LOG_DEBUG << log;
-      25           0 : }
-      26             : 
-      27           0 : void setLogStream(std::ostream &stream) {
-      28           0 :         kiss::Logger::setLogStream(stream);
-      29           0 : }
-      30             : 
-      31           0 : void setLogLevel(int level) {
-      32           0 :         kiss::Logger::setLogLevel(static_cast<kiss::eLogLevel>(level));
-      33           0 : }
-      34             : 
-      35             : #endif // CRPROPA_LOGGING_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Module.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Module.h.func-sort-c.html deleted file mode 100644 index 33e798596..000000000 --- a/doc/coverageReport/include/crpropa/Module.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Module.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Module.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2825.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Module.h.func.html b/doc/coverageReport/include/crpropa/Module.h.func.html deleted file mode 100644 index 1d53a83bf..000000000 --- a/doc/coverageReport/include/crpropa/Module.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Module.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Module.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2825.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Module.h.gcov.html b/doc/coverageReport/include/crpropa/Module.h.gcov.html deleted file mode 100644 index be630b8ed..000000000 --- a/doc/coverageReport/include/crpropa/Module.h.gcov.html +++ /dev/null @@ -1,141 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Module.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Module.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2825.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_MODULE_H
-       2             : #define CRPROPA_MODULE_H
-       3             : 
-       4             : #include "crpropa/Candidate.h"
-       5             : #include "crpropa/Referenced.h"
-       6             : #include "crpropa/Common.h"
-       7             : 
-       8             : #include <string>
-       9             : 
-      10             : namespace crpropa {
-      11             : 
-      12             : class Candidate;
-      13             : 
-      14             : /**
-      15             :  @class Module
-      16             :  @brief Abstract base class for modules
-      17             :  */
-      18             : class Module: public Referenced {
-      19             :         std::string description;
-      20             : public:
-      21             :         Module();
-      22          37 :         virtual ~Module() {
-      23           4 :         }
-      24             :         virtual std::string getDescription() const;
-      25             :         void setDescription(const std::string &description);
-      26             :         virtual void process(Candidate *candidate) const = 0;
-      27             :         inline void process(ref_ptr<Candidate> candidate) const {
-      28           0 :                 process(candidate.get());
-      29           0 :         }
-      30             : };
-      31             : 
-      32             : 
-      33             : /**
-      34             :  @class AbstractCondition
-      35             :  @brief Abstract Module providing common features for conditional modules.
-      36             :  */
-      37             : class AbstractCondition: public Module {
-      38             : protected:
-      39             :         ref_ptr<Module> rejectAction, acceptAction;
-      40             :         bool makeRejectedInactive, makeAcceptedInactive;
-      41             :         std::string rejectFlagKey, rejectFlagValue;
-      42             :         std::string acceptFlagKey, acceptFlagValue;
-      43             : 
-      44             :         void reject(Candidate *candidate) const;
-      45             :         inline void reject(ref_ptr<Candidate> candidate) const {
-      46           0 :                 reject(candidate.get());
-      47           0 :         }
-      48             : 
-      49             :         void accept(Candidate *candidate) const;
-      50             :         inline void accept(ref_ptr<Candidate> candidate) const {
-      51           0 :                 accept(candidate.get());
-      52           0 :         }
-      53             : 
-      54             : public:
-      55             :         AbstractCondition();
-      56             :         void onReject(Module *rejectAction);
-      57             :         void onAccept(Module *acceptAction);
-      58             :         void setMakeRejectedInactive(bool makeInactive);
-      59             :         void setMakeAcceptedInactive(bool makeInactive);
-      60             :         void setRejectFlag(std::string key, std::string value);
-      61             :         void setAcceptFlag(std::string key, std::string value);
-      62             : };
-      63             : } // namespace crpropa
-      64             : 
-      65             : #endif /* CRPROPA_MODULE_H */
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html b/doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html deleted file mode 100644 index 71558e0b3..000000000 --- a/doc/coverageReport/include/crpropa/ParticleState.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/ParticleState.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - ParticleState.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/ParticleState.h.func.html b/doc/coverageReport/include/crpropa/ParticleState.h.func.html deleted file mode 100644 index 0ff39823d..000000000 --- a/doc/coverageReport/include/crpropa/ParticleState.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/ParticleState.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - ParticleState.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/ParticleState.h.gcov.html b/doc/coverageReport/include/crpropa/ParticleState.h.gcov.html deleted file mode 100644 index 3c2bcfa41..000000000 --- a/doc/coverageReport/include/crpropa/ParticleState.h.gcov.html +++ /dev/null @@ -1,196 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/ParticleState.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - ParticleState.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_PARTICLE_STATE_H
-       2             : #define CRPROPA_PARTICLE_STATE_H
-       3             : 
-       4             : #include "crpropa/Vector3.h"
-       5             : 
-       6             : namespace crpropa {
-       7             : /**
-       8             :  * \addtogroup Core
-       9             :  * @{
-      10             :  */
-      11             : 
-      12             : /**
-      13             :  @class ParticleState
-      14             :  @brief State of the particle: ID, energy, position, direction
-      15             : 
-      16             :  The ParticleState defines the state of an ultra-high energy cosmic ray, which
-      17             :  is assumed to be traveling at the exact speed of light.
-      18             :  The cosmic ray state is defined by particle ID, energy and position and
-      19             :  direction vector.
-      20             :  For faster lookup mass and charge of the particle are stored as members.
-      21             :  */
-      22     7199005 : class ParticleState {
-      23             : private:
-      24             :         int id; ///< particle ID (Particle Data Group numbering scheme)
-      25             :         double energy; ///< total energy
-      26             :         Vector3d position; ///< position vector in comoving coordinates
-      27             :         Vector3d direction; ///< unit vector of velocity or momentum
-      28             :         double pmass; ///< particle rest mass
-      29             :         double charge; ///< particle charge
-      30             : 
-      31             : public:
-      32             :         /** Constructor for a particle state.
-      33             :          @param id                      id of the particle following the PDG numbering scheme
-      34             :          @param energy          energy of the particle [in Joules]
-      35             :          @param position        vector containing the coordinates of the particle [in meters]
-      36             :          @param direction       vector containing the direction of motion of the particle
-      37             :          */
-      38             :         ParticleState(int id = 0, double energy = 0,
-      39             :                         Vector3d position = Vector3d(0, 0, 0),
-      40             :                         Vector3d direction = Vector3d(-1, 0, 0));
-      41             : 
-      42             :         /** Set particle position.
-      43             :          In simulations including cosmological effects, the position is given in comoving coordinates.
-      44             :          @param pos             vector containing the coordinates of the particle [in meters]
-      45             :         */
-      46             :         void setPosition(const Vector3d &pos);
-      47             :         /** Get position of particle.
-      48             :          @returns Position vector of particle. If cosmological effects are included, the coordinates are comoving.
-      49             :          */
-      50             :         const Vector3d &getPosition() const;
-      51             : 
-      52             :         /** Set direction unit vector, non unit-vectors are normalized
-      53             :          @param dir     vector containing the direction of motion of the particle
-      54             :          */
-      55             :         void setDirection(const Vector3d &dir);
-      56             :         /** Get direction unit vector
-      57             :          @returns Normalized vector containing direction of motion of particle.
-      58             :          */
-      59             :         const Vector3d &getDirection() const;
-      60             : 
-      61             :         /** Set energy of particle.
-      62             :          @param newEnergy       energy to be assigned to particle [in Joules]
-      63             :          */
-      64             :         void setEnergy(double newEnergy);
-      65             :         /** Get energy of particle.
-      66             :          @returns Energy of particle [in Joules]
-      67             :          */
-      68             :         double getEnergy() const;
-      69             :         /** Get rigidity of particle, defined as E/(Z*e).
-      70             :          @returns Rigidity of the particle [in Volts]
-      71             :          */
-      72             :         double getRigidity() const;
-      73             : 
-      74             :         /** Set particle ID.
-      75             :          This follows the PDG numbering scheme:
-      76             :           https://pdg.lbl.gov/2019/reviews/rpp2019-rev-monte-carlo-numbering.pdf
-      77             :          @param newId           id to be assigned to the particle 
-      78             :          */
-      79             :         void setId(int newId);
-      80             :         /** Get particle ID
-      81             :          @returns Particle ID (in PDG format).
-      82             :          */
-      83             :         int getId() const;
-      84             : 
-      85             :         std::string getDescription() const;
-      86             : 
-      87             :         // ======== Helper methods ========
-      88             : 
-      89             :         /** Get electrical charge of the particle.
-      90             :          @returns Charge of the particle [in Coulombs]
-      91             :          */
-      92             :         double getCharge() const;
-      93             :         /** Get mass of the particle.
-      94             :          @returns Mass of the particle [kg]
-      95             :          */
-      96             :         double getMass() const;
-      97             : 
-      98             :         /** Set Lorentz factor and modify the particle's energy accordingly.
-      99             :          @param gamma           Lorentz factor
-     100             :          */
-     101             :         void setLorentzFactor(double gamma);
-     102             :         /** Get Lorentz factor
-     103             :          @returns Lorentz factor of particle
-     104             :          */
-     105             :         double getLorentzFactor() const;
-     106             : 
-     107             :         /** Get velocity: direction times the speed of light.
-     108             :          @returns Velocity of particle [m/s]
-     109             :          */
-     110             :         Vector3d getVelocity() const;
-     111             :         /** Get momentum: direction times energy divided by the speed of light 
-     112             :          @returns The momentum [kg m/s]
-     113             :         */
-     114             :         Vector3d getMomentum() const;
-     115             : };
-     116             : /** @}*/
-     117             : 
-     118             : } // namespace crpropa
-     119             : 
-     120             : #endif // CRPROPA_PARTICLE_STATE_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html b/doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html deleted file mode 100644 index 167da8226..000000000 --- a/doc/coverageReport/include/crpropa/PhotonBackground.h.func-sort-c.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/PhotonBackground.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - PhotonBackground.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:222781.5 %
Date:2024-04-08 14:58:22Functions:171989.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19IRB_Saldana21_lowerC2Ev0
_ZN7crpropa19IRB_Saldana21_upperC2Ev0
_ZN7crpropa12URB_Fixsen11C2Ev4
_ZN7crpropa13IRB_Saldana21C2Ev4
_ZN7crpropa15URB_Protheroe96C2Ev6
_ZN7crpropa11IRB_Finke10C2Ev7
_ZN7crpropa11IRB_Finke22C2Ev7
_ZN7crpropa13IRB_Gilmore12C2Ev7
_ZN7crpropa13IRB_Stecker05C2Ev7
_ZN7crpropa15IRB_Dominguez11C2Ev7
_ZN7crpropa18IRB_Franceschini08C2Ev7
_ZN7crpropa19IRB_Stecker16_lowerC2Ev7
_ZN7crpropa19IRB_Stecker16_upperC2Ev7
_ZN7crpropa10URB_Nitu21C2Ev11
_ZN7crpropa13IRB_Kneiske04C2Ev13
_ZN7crpropa3CMBC2Ev40
_ZN7crpropa11PhotonFieldC2Ev135
_ZNK7crpropa11PhotonField12getFieldNameB5cxx11Ev175
_ZNK7crpropa11PhotonField18getRedshiftScalingEd16549
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/PhotonBackground.h.func.html b/doc/coverageReport/include/crpropa/PhotonBackground.h.func.html deleted file mode 100644 index f8d9a9eee..000000000 --- a/doc/coverageReport/include/crpropa/PhotonBackground.h.func.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/PhotonBackground.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - PhotonBackground.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:222781.5 %
Date:2024-04-08 14:58:22Functions:171989.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10URB_Nitu21C2Ev11
_ZN7crpropa11IRB_Finke10C2Ev7
_ZN7crpropa11IRB_Finke22C2Ev7
_ZN7crpropa11PhotonFieldC2Ev135
_ZN7crpropa12URB_Fixsen11C2Ev4
_ZN7crpropa13IRB_Gilmore12C2Ev7
_ZN7crpropa13IRB_Kneiske04C2Ev13
_ZN7crpropa13IRB_Saldana21C2Ev4
_ZN7crpropa13IRB_Stecker05C2Ev7
_ZN7crpropa15IRB_Dominguez11C2Ev7
_ZN7crpropa15URB_Protheroe96C2Ev6
_ZN7crpropa18IRB_Franceschini08C2Ev7
_ZN7crpropa19IRB_Saldana21_lowerC2Ev0
_ZN7crpropa19IRB_Saldana21_upperC2Ev0
_ZN7crpropa19IRB_Stecker16_lowerC2Ev7
_ZN7crpropa19IRB_Stecker16_upperC2Ev7
_ZN7crpropa3CMBC2Ev40
_ZNK7crpropa11PhotonField12getFieldNameB5cxx11Ev175
_ZNK7crpropa11PhotonField18getRedshiftScalingEd16549
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html b/doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html deleted file mode 100644 index 0a582c195..000000000 --- a/doc/coverageReport/include/crpropa/PhotonBackground.h.gcov.html +++ /dev/null @@ -1,398 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/PhotonBackground.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - PhotonBackground.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:222781.5 %
Date:2024-04-08 14:58:22Functions:171989.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_PHOTONBACKGROUND_H
-       2             : #define CRPROPA_PHOTONBACKGROUND_H
-       3             : 
-       4             : #include "crpropa/Common.h"
-       5             : #include "crpropa/Referenced.h"
-       6             : 
-       7             : #include <vector>
-       8             : #include <string>
-       9             : 
-      10             : namespace crpropa {
-      11             : /**
-      12             :  * \addtogroup PhotonFields
-      13             :  * @{
-      14             :  */
-      15             : 
-      16             : /**
-      17             :  @class PhotonField
-      18             :  @brief Abstract base class for photon fields.
-      19             :  */
-      20           1 : class PhotonField: public Referenced {
-      21             : public:
-      22         135 :         PhotonField() {
-      23             :                 this->fieldName = "AbstractPhotonField";
-      24         135 :                 this->isRedshiftDependent = false;
-      25         135 :         }
-      26             : 
-      27             :         /**
-      28             :          returns comoving photon density [1/m^3].
-      29             :          multiply with (1+z^3) for physical number density.
-      30             :          @param ePhoton         photon energy [J]
-      31             :          @param z                       redshift (if redshift dependent, default = 0.)
-      32             :          */
-      33             :         virtual double getPhotonDensity(double ePhoton, double z = 0.) const = 0;
-      34             :         virtual double getMinimumPhotonEnergy(double z) const = 0;
-      35             :         virtual double getMaximumPhotonEnergy(double z) const = 0;
-      36         175 :         virtual std::string getFieldName() const {
-      37         175 :                 return this->fieldName;
-      38             :         }
-      39             : 
-      40             :         /**
-      41             :          returns overall comoving scaling factor
-      42             :          (cf. CRPropa3-data/calc_scaling.py)
-      43             :          @param z               redshift
-      44             :          */
-      45       16549 :         virtual double getRedshiftScaling(double z) const {
-      46       16549 :                 return 1.;
-      47             :         };
-      48             : 
-      49             :         bool hasRedshiftDependence() const {
-      50           0 :                 return this->isRedshiftDependent;
-      51             :         }
-      52             : 
-      53             :         void setFieldName(std::string fieldName) {
-      54           0 :                 this->fieldName = fieldName;
-      55           0 :         }
-      56             : 
-      57             : protected:
-      58             :         std::string fieldName;
-      59             :         bool isRedshiftDependent;
-      60             : };
-      61             : 
-      62             : /**
-      63             :  @class TabularPhotonField
-      64             :  @brief Photon field decorator for tabulated photon fields.
-      65             : 
-      66             :  This class reads photon field data from files;
-      67             :  The first file must be a list of photon energies [J], named fieldName_photonEnergy.txt
-      68             :  The second file must be a list of comoving photon field densities [1/m^3], named fieldName_photonDensity.txt
-      69             :  Optionally, a third file contains redshifts, named fieldName_redshift.txt
-      70             :  */
-      71             : class TabularPhotonField: public PhotonField {
-      72             : public:
-      73             :         TabularPhotonField(const std::string fieldName, const bool isRedshiftDependent = true);
-      74             : 
-      75             :         double getPhotonDensity(double ePhoton, double z = 0.) const;
-      76             :         double getRedshiftScaling(double z) const;
-      77             :         double getMinimumPhotonEnergy(double z) const;
-      78             :         double getMaximumPhotonEnergy(double z) const;
-      79             : 
-      80             : protected:
-      81             :         void readPhotonEnergy(std::string filePath);
-      82             :         void readPhotonDensity(std::string filePath);
-      83             :         void readRedshift(std::string filePath);
-      84             :         void initRedshiftScaling();
-      85             :         void checkInputData() const;
-      86             : 
-      87             :         std::vector<double> photonEnergies;
-      88             :         std::vector<double> photonDensity;
-      89             :         std::vector<double> redshifts;
-      90             :         std::vector<double> redshiftScalings;
-      91             : };
-      92             : 
-      93             : /**
-      94             :  @class IRB_Kneiske04
-      95             :  @brief Extragalactic background light model from Kneiske et al. 2004
-      96             : 
-      97             :  Source info:
-      98             :  DOI:10.1051/0004-6361:20031542,
-      99             :  https://www.aanda.org/articles/aa/pdf/2004/03/aa3848.pdf, figure 1 ("Best-fit" model)
-     100             :  */
-     101             : class IRB_Kneiske04: public TabularPhotonField {
-     102             : public:
-     103          26 :         IRB_Kneiske04() : TabularPhotonField("IRB_Kneiske04", true) {}
-     104             : };
-     105             : 
-     106             : /**
-     107             :  @class IRB_Stecker05
-     108             :  @brief Extragalactic background light model by Stecker at al. 2005
-     109             : 
-     110             :  Source info:
-     111             :  DOI:10.1086/506188, astro-ph/0510449
-     112             :  https://iopscience.iop.org/article/10.1086/506188/pdf
-     113             :  */
-     114             : class IRB_Stecker05: public TabularPhotonField {
-     115             : public:
-     116          14 :         IRB_Stecker05() : TabularPhotonField("IRB_Stecker05", true) {}
-     117             : };
-     118             : 
-     119             : /**
-     120             :  @class IRB_Franceschini08
-     121             :  @brief Extragalactic background light model from Franceschini et al. 2008
-     122             : 
-     123             :  Source info:
-     124             :  DOI:10.1051/0004-6361:200809691
-     125             :  https://arxiv.org/pdf/0805.1841.pdf, tables 1 and 2
-     126             :  */
-     127             : class IRB_Franceschini08: public TabularPhotonField {
-     128             : public:
-     129          14 :         IRB_Franceschini08() : TabularPhotonField("IRB_Franceschini08", true) {}
-     130             : };
-     131             : 
-     132             : /**
-     133             :  @class IRB_Finke10
-     134             :  @brief Extragalactic background light model from Finke et al. 2010
-     135             : 
-     136             :  Source info:
-     137             :  DOI:10.1088/0004-637X/712/1/238
-     138             :  https://iopscience.iop.org/article/10.1088/0004-637X/712/1/238/pdf
-     139             :  */
-     140             : class IRB_Finke10: public TabularPhotonField {
-     141             : public:
-     142          14 :         IRB_Finke10() : TabularPhotonField("IRB_Finke10", true) {}
-     143             : };
-     144             : 
-     145             : /**
-     146             :  @class IRB_Dominguez11
-     147             :  @brief Extragalactic background light model from Dominguez et al. 2011
-     148             : 
-     149             :  Source info:
-     150             :  DOI:10.1111/j.1365-2966.2010.17631.x
-     151             :  https://academic.oup.com/mnras/article/410/4/2556/1008012
-     152             :  */
-     153             : class IRB_Dominguez11: public TabularPhotonField {
-     154             : public:
-     155          14 :         IRB_Dominguez11() : TabularPhotonField("IRB_Dominguez11", true) {}
-     156             : };
-     157             : 
-     158             : /**
-     159             :  @class IRB_Gilmore12
-     160             :  @brief Extragalactic background light model from Gilmore et al. 2012
-     161             : 
-     162             :  Source info:
-     163             :  DOI:10.1111/j.1365-2966.2012.20841.x
-     164             :  https://academic.oup.com/mnras/article/422/4/3189/1050758
-     165             :  */
-     166             : class IRB_Gilmore12: public TabularPhotonField {
-     167             : public:
-     168          14 :         IRB_Gilmore12() : TabularPhotonField("IRB_Gilmore12", true) {}
-     169             : };
-     170             : 
-     171             : /**
-     172             :  @class IRB_Stecker16_upper
-     173             :  @brief Extragalactic background light model from Stecker et al. 2016 (upper-bound model)
-     174             : 
-     175             :  Source info:
-     176             :  DOI:10.3847/0004-637X/827/1/6
-     177             :  https://iopscience.iop.org/article/10.3847/0004-637X/827/1/6
-     178             :  */
-     179             : class IRB_Stecker16_upper: public TabularPhotonField {
-     180             : public:
-     181          14 :         IRB_Stecker16_upper() : TabularPhotonField("IRB_Stecker16_upper", true) {}
-     182             : };
-     183             : 
-     184             : /**
-     185             :  @class IRB_Stecker16_lower
-     186             :  @brief Extragalactic background light model from Stecker et al. 2016 (lower-bound model)
-     187             : 
-     188             :  Source info:
-     189             :  DOI:10.3847/0004-637X/827/1/6
-     190             :  https://iopscience.iop.org/article/10.3847/0004-637X/827/1/6
-     191             :  */
-     192             : class IRB_Stecker16_lower: public TabularPhotonField {
-     193             : public:
-     194          14 :         IRB_Stecker16_lower() : TabularPhotonField("IRB_Stecker16_lower", true) {}
-     195             : };
-     196             : 
-     197             : /**
-     198             :  @class IRB_Saldana21
-     199             :  @brief Extragalactic background light model from Saldana-Lopez et al. 2021
-     200             : 
-     201             :  Source info:
-     202             :  DOI:10.1093/mnras/stab2393
-     203             :  https://ui.adsabs.harvard.edu/abs/2021MNRAS.507.5144S/abstract
-     204             :  */
-     205             : class IRB_Saldana21: public TabularPhotonField {
-     206             : public:
-     207           8 :         IRB_Saldana21() : TabularPhotonField("IRB_Saldana21", true) {}
-     208             : };
-     209             : 
-     210             : /**
-     211             :  @class IRB_Saldana21_upper
-     212             :  @brief Extragalactic background light model from Saldana-Lopez et al. 2021 (upper-bound model)
-     213             : 
-     214             :  Source info:
-     215             :  DOI:10.1093/mnras/stab2393
-     216             :  https://ui.adsabs.harvard.edu/abs/2021MNRAS.507.5144S/abstract
-     217             :  */
-     218             : class IRB_Saldana21_upper: public TabularPhotonField {
-     219             : public:
-     220           0 :         IRB_Saldana21_upper() : TabularPhotonField("IRB_Saldana21_upper", true) {}
-     221             : };
-     222             : 
-     223             : /**
-     224             :  @class IRB_Saldana21_lower
-     225             :  @brief Extragalactic background light model from Saldana-Lopez et al. 2021 (lower-bound model)
-     226             : 
-     227             :  Source info:
-     228             :  DOI:10.1093/mnras/stab2393
-     229             :  https://ui.adsabs.harvard.edu/abs/2021MNRAS.507.5144S/abstract
-     230             :  */
-     231             : class IRB_Saldana21_lower: public TabularPhotonField {
-     232             : public:
-     233           0 :         IRB_Saldana21_lower() : TabularPhotonField("IRB_Saldana21_lower", true) {}
-     234             : };
-     235             : 
-     236             : /**
-     237             :  @class IRB_Finke22
-     238             :  @brief Extragalactic background light model from Finke et al. 2022
-     239             : 
-     240             :  Source info:
-     241             :  DOI:10.3847/1538-4357/ac9843
-     242             :  https://iopscience.iop.org/article/10.3847/1538-4357/ac9843/pdf
-     243             :  */
-     244             : class IRB_Finke22: public TabularPhotonField {
-     245             : public:
-     246          14 :         IRB_Finke22() : TabularPhotonField("IRB_Finke22", true) {}
-     247             : };
-     248             : 
-     249             : /**
-     250             :  @class URB
-     251             :  @brief Extragalactic background light model from Protheroe & Biermann 1996
-     252             : 
-     253             :  Source info:
-     254             :  DOI:10.1016/S0927-6505(96)00041-2
-     255             :  https://www.sciencedirect.com/science/article/abs/pii/S0927650596000412
-     256             :  */
-     257             : class URB_Protheroe96: public TabularPhotonField {
-     258             : public:
-     259          12 :         URB_Protheroe96() : TabularPhotonField("URB_Protheroe96", false) {}
-     260             : };
-     261             : 
-     262             : /**
-     263             :  @class URB
-     264             :  @brief Extragalactic background light model based on ARCADE2 observations, by Fixsen et al.
-     265             :  Note that this model does not cover the same energy range as other URB models. Here, only ~10 MHz - 10 GHz is considered.
-     266             :  Therefore, it only makes sense to use this model in very specific studies.
-     267             : 
-     268             :  Source info:
-     269             :  DOI:10.1088/0004-637X/734/1/5
-     270             :  https://iopscience.iop.org/article/10.1088/0004-637X/734/1/5
-     271             :  */
-     272             : class URB_Fixsen11: public TabularPhotonField {
-     273             : public:
-     274           8 :         URB_Fixsen11() : TabularPhotonField("URB_Fixsen11", false) {}
-     275             : };
-     276             : 
-     277             : /**
-     278             :  @class URB
-     279             :  @brief Extragalactic background light model by Nitu et al.
-     280             : 
-     281             :  Source info:
-     282             :  DOI:10.1016/j.astropartphys.2020.102532
-     283             :  https://www.sciencedirect.com/science/article/pii/S0927650520301043?
-     284             :  */
-     285             : class URB_Nitu21: public TabularPhotonField {
-     286             : public:
-     287          22 :         URB_Nitu21() : TabularPhotonField("URB_Nitu21", false) {}
-     288             : };
-     289             : 
-     290             : /**
-     291             :  @class BlackbodyPhotonField
-     292             :  @brief Photon field decorator for black body photon fields.
-     293             :  */
-     294             : class BlackbodyPhotonField: public PhotonField {
-     295             : public:
-     296             :         BlackbodyPhotonField(const std::string fieldName, const double blackbodyTemperature);
-     297             :         double getPhotonDensity(double ePhoton, double z = 0.) const;
-     298             :         double getMinimumPhotonEnergy(double z) const;
-     299             :         double getMaximumPhotonEnergy(double z) const;
-     300             :         void setQuantile(double q);
-     301             : 
-     302             : protected:
-     303             :         double blackbodyTemperature;
-     304             :         double quantile;
-     305             : };
-     306             : 
-     307             : /**
-     308             :  @class CMB
-     309             :  @brief Cosmic mircowave background photon field
-     310             : 
-     311             :  Source info:
-     312             :  This field is an isotropic blackbody photon field with temperature T = 2.73 K
-     313             :  */
-     314             : class CMB: public BlackbodyPhotonField {
-     315             : public:
-     316          80 :         CMB() : BlackbodyPhotonField("CMB", 2.73) {}
-     317             : };
-     318             : 
-     319             : 
-     320             : } // namespace crpropa
-     321             : 
-     322             : #endif // CRPROPA_PHOTONBACKGROUND_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Random.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Random.h.func-sort-c.html deleted file mode 100644 index e8f69e8b4..000000000 --- a/doc/coverageReport/include/crpropa/Random.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Random.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Random.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7887.5 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Random.h.func.html b/doc/coverageReport/include/crpropa/Random.h.func.html deleted file mode 100644 index 16cf98e23..000000000 --- a/doc/coverageReport/include/crpropa/Random.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Random.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Random.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7887.5 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Random.h.gcov.html b/doc/coverageReport/include/crpropa/Random.h.gcov.html deleted file mode 100644 index 5799cec29..000000000 --- a/doc/coverageReport/include/crpropa/Random.h.gcov.html +++ /dev/null @@ -1,317 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Random.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Random.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7887.5 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : // Random.h
-       2             : // Mersenne Twister random number generator -- a C++ class Random
-       3             : // Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
-       4             : // Richard J. Wagner  v1.0  15 May 2003  rjwagner@writeme.com
-       5             : 
-       6             : // The Mersenne Twister is an algorithm for generating random numbers.  It
-       7             : // was designed with consideration of the flaws in various other generators.
-       8             : // The period, 2^19937-1, and the order of equidistribution, 623 dimensions,
-       9             : // are far greater.  The generator is also fast; it avoids multiplication and
-      10             : // division, and it benefits from caches and pipelines.  For more information
-      11             : // see the inventors' web page at http://www.math.keio.ac.jp/~matumoto/emt.html
-      12             : 
-      13             : // Reference
-      14             : // M. Matsumoto and T. Nishimura, "Mersenne Twister: A 623-Dimensionally
-      15             : // Equidistributed Uniform Pseudo-Random Number Generator", ACM Transactions on
-      16             : // Modeling and Computer Simulation, Vol. 8, No. 1, January 1998, pp 3-30.
-      17             : 
-      18             : // Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura,
-      19             : // Copyright (C) 2000 - 2003, Richard J. Wagner
-      20             : // All rights reserved.
-      21             : //
-      22             : // Redistribution and use in source and binary forms, with or without
-      23             : // modification, are permitted provided that the following conditions
-      24             : // are met:
-      25             : //
-      26             : //   1. Redistributions of source code must retain the above copyright
-      27             : //      notice, this list of conditions and the following disclaimer.
-      28             : //
-      29             : //   2. Redistributions in binary form must reproduce the above copyright
-      30             : //      notice, this list of conditions and the following disclaimer in the
-      31             : //      documentation and/or other materials provided with the distribution.
-      32             : //
-      33             : //   3. The names of its contributors may not be used to endorse or promote
-      34             : //      products derived from this software without specific prior written
-      35             : //      permission.
-      36             : //
-      37             : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-      38             : // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-      39             : // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-      40             : // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
-      41             : // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
-      42             : // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
-      43             : // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
-      44             : // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
-      45             : // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
-      46             : // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
-      47             : // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-      48             : 
-      49             : // The original code included the following notice:
-      50             : //
-      51             : //     When you use this, send an email to: matumoto@math.keio.ac.jp
-      52             : //     with an appropriate reference to your work.
-      53             : //
-      54             : // It would be nice to CC: rjwagner@writeme.com and Cokus@math.washington.edu
-      55             : // when you write.
-      56             : 
-      57             : // Parts of this file are modified beginning in 29.10.09 for adaption in PXL.
-      58             : // Parts of this file are modified beginning in 10.02.12 for adaption in CRPropa.
-      59             : 
-      60             : #ifndef RANDOM_H
-      61             : #define RANDOM_H
-      62             : 
-      63             : // Not thread safe (unless auto-initialization is avoided and each thread has
-      64             : // its own Random object)
-      65             : #include "crpropa/Vector3.h"
-      66             : 
-      67             : #include <iostream>
-      68             : #include <limits>
-      69             : #include <ctime>
-      70             : #include <cmath>
-      71             : #include <vector>
-      72             : #include <stdexcept>
-      73             : #include <algorithm>
-      74             : 
-      75             : #include <stdint.h>
-      76             : #include <string>
-      77             : 
-      78             : //necessary for win32
-      79             : #ifndef M_PI
-      80             : #define M_PI 3.14159265358979323846
-      81             : #endif
-      82             : 
-      83             : namespace crpropa {
-      84             : 
-      85             : /**
-      86             :  * \addtogroup Core
-      87             :  * @{
-      88             :  */
-      89             : /**
-      90             :  @class Random
-      91             :  @brief Random number generator.
-      92             : 
-      93             :  Mersenne Twister random number generator -- a C++ class Random
-      94             :  Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
-      95             :  Richard J. Wagner  v1.0  15 May 2003  rjwagner@writeme.com
-      96             :  */
-      97           3 : class Random {
-      98             : public:
-      99             :         enum {N = 624}; // length of state vector
-     100             :         enum {SAVE = N + 1}; // length of array for save()
-     101             : 
-     102             : protected:
-     103             :         enum {M = 397}; // period parameter
-     104             :         uint32_t state[N];// internal state
-     105             :         std::vector<uint32_t> initial_seed;//
-     106             :         uint32_t *pNext;// next value to get from state
-     107             :         int left;// number of values left before reload needed
-     108             : 
-     109             : //Methods
-     110             : public:
-     111             :         /// initialize with a simple uint32_t
-     112             :         Random( const uint32_t& oneSeed );
-     113             :         // initialize with an array
-     114             :         Random( uint32_t *const bigSeed, uint32_t const seedLength = N );
-     115             :         /// auto-initialize with /dev/urandom or time() and clock()
-     116             :         /// Do NOT use for CRYPTOGRAPHY without securely hashing several returned
-     117             :         /// values together, otherwise the generator state can be learned after
-     118             :         /// reading 624 consecutive values.
-     119             :         Random();
-     120             :         // Access to 32-bit random numbers
-     121             :         double rand();///< real number in [0,1]
-     122             :         double rand( const double& n );///< real number in [0,n]
-     123             :         double randExc();///< real number in [0,1)
-     124             :         double randExc( const double& n );///< real number in [0,n)
-     125             :         double randDblExc();///< real number in (0,1)
-     126             :         double randDblExc( const double& n );///< real number in (0,n)
-     127             :         // Pull a 32-bit integer from the generator state
-     128             :         // Every other access function simply transforms the numbers extracted here
-     129             :         uint32_t randInt();///< integer in [0,2**32-1]
-     130             :         uint32_t randInt( const uint32_t& n );///< integer in [0,n] for n < 2**32
-     131             : 
-     132             :         uint64_t randInt64(); ///< integer in [0, 2**64 -1]. PROBABLY NOT SECURE TO USE
-     133             :         uint64_t randInt64(const uint64_t &n); ///< integer in [0, n] for n < 2**64 -1. PROBABLY NOT SECURE TO USE
-     134             : 
-     135           0 :         double operator()() {return rand();} ///< same as rand()
-     136             : 
-     137             :         // Access to 53-bit random numbers (capacity of IEEE double precision)
-     138             :         double rand53();///< real number in [0,1)  (capacity of IEEE double precision)
-     139             :         ///Exponential distribution in (0,inf)
-     140             :         double randExponential();
-     141             :         /// Normal distributed random number
-     142     1715954 :         double randNorm( const double& mean = 0.0, const double& variance = 1.0 );
-     143             :         /// Uniform distribution in [min, max]
-     144             :         double randUniform(double min, double max);
-     145             :         /// Rayleigh distributed random number
-     146             :         double randRayleigh(double sigma);
-     147             :         /// Fisher distributed random number
-     148             :         double randFisher(double k);
-     149             : 
-     150             :         /// Draw a random bin from a (unnormalized) cumulative distribution function, without leading zero.
-     151             :         size_t randBin(const std::vector<float> &cdf);
-     152             :         size_t randBin(const std::vector<double> &cdf);
-     153             : 
-     154             :         /// Random point on a unit-sphere
-     155             :         Vector3d randVector();
-     156             :         /// Random vector with given angular separation around mean direction
-     157             :         Vector3d randVectorAroundMean(const Vector3d &meanDirection, double angle);
-     158             :         /// Fisher distributed random vector
-     159             :         Vector3d randFisherVector(const Vector3d &meanDirection, double kappa);
-     160             :         /// Uniform distributed random vector inside a cone
-     161             :         Vector3d randConeVector(const Vector3d &meanDirection, double angularRadius);
-     162             :         /// Random lamberts distributed vector with theta distribution: sin(t) * cos(t),
-     163             :         /// aka cosine law (https://en.wikipedia.org/wiki/Lambert%27s_cosine_law),
-     164             :         /// for a surface element with normal vector pointing in positive z-axis (0, 0, 1)
-     165             :         Vector3d randVectorLamberts();
-     166             :         /// Same as above but rotated to the respective normalVector of surface element
-     167             :         Vector3d randVectorLamberts(const Vector3d &normalVector);
-     168             :         ///_Position vector uniformly distributed within propagation step size bin
-     169             :         Vector3d randomInterpolatedPosition(const Vector3d &a, const Vector3d &b);
-     170             : 
-     171             :         /// Power-law distribution of a given differential spectral index
-     172             :         double randPowerLaw(double index, double min, double max);
-     173             :         /// Broken power-law distribution
-     174             :         double randBrokenPowerLaw(double index1, double index2, double breakpoint, double min, double max );
-     175             : 
-     176             :         /// Seed the generator with a simple uint32_t
-     177             :         void seed( const uint32_t oneSeed );
-     178             :         /// Seed the generator with an array of uint32_t's
-     179             :         /// There are 2^19937-1 possible initial states.  This function allows
-     180             :         /// all of those to be accessed by providing at least 19937 bits (with a
-     181             :         /// default seed length of N = 624 uint32_t's).  Any bits above the lower 32
-     182             :         /// in each element are discarded.
-     183             :         /// Just call seed() if you want to get array from /dev/urandom
-     184             :         void seed( uint32_t *const bigSeed, const uint32_t seedLength = N );
-     185             :         // seed via an b64 encoded string
-     186             :         void seed( const std::string &b64Seed);
-     187             :         /// Seed the generator with an array from /dev/urandom if available
-     188             :         /// Otherwise use a hash of time() and clock() values
-     189             :         void seed();
-     190             : 
-     191             :         // Saving and loading generator state
-     192             :         void save( uint32_t* saveArray ) const;// to array of size SAVE
-     193             :         void load( uint32_t *const loadArray );// from such array
-     194             :         const std::vector<uint32_t> &getSeed() const; // copy the seed to the array
-     195             :         const std::string getSeed_base64() const; // get the base 64 encoded seed
-     196             : 
-     197             :         friend std::ostream& operator<<( std::ostream& os, const Random& mtrand );
-     198             :         friend std::istream& operator>>( std::istream& is, Random& mtrand );
-     199             : 
-     200             :         static Random &instance();
-     201             :         static void seedThreads(const uint32_t oneSeed);
-     202             :         static std::vector< std::vector<uint32_t> > getSeedThreads();
-     203             : 
-     204             : protected:
-     205             :         /// Initialize generator state with seed
-     206             :         /// See Knuth TAOCP Vol 2, 3rd Ed, p.106 for multiplier.
-     207             :         /// In previous versions, most significant bits (MSBs) of the seed affect
-     208             :         /// only MSBs of the state array.  Modified 9 Jan 2002 by Makoto Matsumoto.
-     209             :         void initialize( const uint32_t oneSeed );
-     210             : 
-     211             :         /// Generate N new values in state
-     212             :         /// Made clearer and faster by Matthew Bellew (matthew.bellew@home.com)
-     213             :         void reload();
-     214    28904304 :         uint32_t hiBit( const uint32_t& u ) const {return u & 0x80000000UL;}
-     215    28904304 :         uint32_t loBit( const uint32_t& u ) const {return u & 0x00000001UL;}
-     216    28904304 :         uint32_t loBits( const uint32_t& u ) const {return u & 0x7fffffffUL;}
-     217             :         uint32_t mixBits( const uint32_t& u, const uint32_t& v ) const
-     218    28904304 :         {       return hiBit(u) | loBits(v);}
-     219             : 
-     220             : #ifdef _MSC_VER
-     221             : #pragma warning( push )
-     222             : #pragma warning( disable : 4146 )
-     223             : #endif
-     224             :         uint32_t twist( const uint32_t& m, const uint32_t& s0, const uint32_t& s1 ) const
-     225    28857983 :         {       return m ^ (mixBits(s0,s1)>>1) ^ (-loBit(s1) & 0x9908b0dfUL);}
-     226             : 
-     227             : #ifdef _MSC_VER
-     228             : #pragma warning( pop )
-     229             : #endif
-     230             : 
-     231             :         /// Get a uint32_t from t and c
-     232             :         /// Better than uint32_t(x) in case x is floating point in [0,1]
-     233             :         /// Based on code by Lawrence Kirby (fred@genesis.demon.co.uk)
-     234             :         static uint32_t hash( time_t t, clock_t c );
-     235             : 
-     236             : };
-     237             : /** @}*/
-     238             : 
-     239             : } //namespace crpropa
-     240             : 
-     241             : #endif  // RANDOM_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html deleted file mode 100644 index ce69cfb72..000000000 --- a/doc/coverageReport/include/crpropa/Referenced.h.func-sort-c.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Referenced.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Referenced.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:415673.2 %
Date:2024-04-08 14:58:22Functions:101952.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10ReferencedD0Ev0
_ZN7crpropa10ReferencedD2Ev0
_ZN7crpropa7ref_ptrINS_10ModuleListEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_11EmissionMapEEaSEPS1_0
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEE6assignIS4_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridIfEEE6assignIS2_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridIfEEEaSEPS2_0
_ZN7crpropa7ref_ptrINS_6ModuleEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_7DensityEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_13MagneticFieldEEaSEPS1_2
_ZN7crpropa7ref_ptrINS_6ModuleEEaSEPS1_4
_ZN7crpropa7ref_ptrINS_24CylindricalProjectionMapEE6assignIS1_EEvRKNS0_IT_EE5
_ZN7crpropa7ref_ptrINS_14AdvectionFieldEE6assignIS1_EEvRKNS0_IT_EE6
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEEaSEPS4_6
_ZN7crpropa7ref_ptrINS_13MagneticFieldEE6assignIS1_EEvRKNS0_IT_EE46
_ZN7crpropa7ref_ptrINS_11PhotonFieldEEaSEPS1_66
_ZN7crpropa7ref_ptrINS_11PhotonFieldEE6assignIS1_EEvRKNS0_IT_EE159
_ZN7crpropa7ref_ptrINS_9CandidateEE6assignIS1_EEvRKNS0_IT_EE1103
_ZNK7crpropa10Referenced15removeReferenceEv10914622
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Referenced.h.func.html b/doc/coverageReport/include/crpropa/Referenced.h.func.html deleted file mode 100644 index 1897f7f51..000000000 --- a/doc/coverageReport/include/crpropa/Referenced.h.func.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Referenced.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Referenced.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:415673.2 %
Date:2024-04-08 14:58:22Functions:101952.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10ReferencedD0Ev0
_ZN7crpropa10ReferencedD2Ev0
_ZN7crpropa7ref_ptrINS_10ModuleListEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_11EmissionMapEEaSEPS1_0
_ZN7crpropa7ref_ptrINS_11PhotonFieldEE6assignIS1_EEvRKNS0_IT_EE159
_ZN7crpropa7ref_ptrINS_11PhotonFieldEEaSEPS1_66
_ZN7crpropa7ref_ptrINS_13MagneticFieldEE6assignIS1_EEvRKNS0_IT_EE46
_ZN7crpropa7ref_ptrINS_13MagneticFieldEEaSEPS1_2
_ZN7crpropa7ref_ptrINS_14AdvectionFieldEE6assignIS1_EEvRKNS0_IT_EE6
_ZN7crpropa7ref_ptrINS_24CylindricalProjectionMapEE6assignIS1_EEvRKNS0_IT_EE5
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEE6assignIS4_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridINS_7Vector3IfEEEEEaSEPS4_6
_ZN7crpropa7ref_ptrINS_4GridIfEEE6assignIS2_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_4GridIfEEEaSEPS2_0
_ZN7crpropa7ref_ptrINS_6ModuleEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_6ModuleEEaSEPS1_4
_ZN7crpropa7ref_ptrINS_7DensityEE6assignIS1_EEvRKNS0_IT_EE0
_ZN7crpropa7ref_ptrINS_9CandidateEE6assignIS1_EEvRKNS0_IT_EE1103
_ZNK7crpropa10Referenced15removeReferenceEv10914622
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Referenced.h.gcov.html b/doc/coverageReport/include/crpropa/Referenced.h.gcov.html deleted file mode 100644 index 5a9b12d1c..000000000 --- a/doc/coverageReport/include/crpropa/Referenced.h.gcov.html +++ /dev/null @@ -1,320 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Referenced.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Referenced.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:415673.2 %
Date:2024-04-08 14:58:22Functions:101952.6 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_REFERENCED_H
-       2             : #define CRPROPA_REFERENCED_H
-       3             : 
-       4             : #include <cstddef>
-       5             : 
-       6             : #ifdef DEBUG
-       7             : #include <iostream>
-       8             : #include <typeinfo>
-       9             : #endif
-      10             : 
-      11             : namespace crpropa {
-      12             : /**
-      13             :  * \addtogroup Core
-      14             :  * @{
-      15             :  */
-      16             : 
-      17             : /**
-      18             :  @class Referenced
-      19             :  @brief Base class for reference counting
-      20             : 
-      21             :  A form of memory management is needed to prevent memory leaks when using MPC in Python via SWIG.
-      22             :  This base class enables reference counting.
-      23             :  Every reference increases the reference counter, every dereference decreases it.
-      24             :  When the counter is decreased to 0, the object is deleted.
-      25             :  Candidate, Module, MagneticField and Source inherit from this class
-      26             :  */
-      27             : class Referenced {
-      28             : public:
-      29             : 
-      30     3369415 :         inline Referenced() :
-      31     3369394 :                         _referenceCount(0) {
-      32             :         }
-      33             : 
-      34           0 :         inline Referenced(const Referenced&) :
-      35           0 :                         _referenceCount(0) {
-      36             :         }
-      37             : 
-      38             :         inline Referenced& operator =(const Referenced&) {
-      39             :                 return *this;
-      40             :         }
-      41             : 
-      42             :         inline size_t addReference() const {
-      43             :                 int newRef;
-      44             : #if defined(OPENMP_3_1)
-      45             :                 #pragma omp atomic capture
-      46             :                 {newRef = _referenceCount++;}
-      47             : #elif defined(__GNUC__)
-      48    10913236 :                 newRef = __sync_add_and_fetch(&_referenceCount, 1);
-      49             : #else
-      50             :                 #pragma omp critical
-      51             :                 {newRef = _referenceCount++;}
-      52             : #endif
-      53     7546128 :                 return newRef;
-      54             :         }
-      55             : 
-      56    10914622 :         inline size_t removeReference() const {
-      57             : #ifdef DEBUG
-      58             :                 if (_referenceCount == 0)
-      59             :                         std::cerr
-      60             :                                         << "WARNING: Remove reference from Object with NO references: "
-      61             :                                         << typeid(*this).name() << std::endl;
-      62             : #endif
-      63             :                 int newRef;
-      64             : #if defined(OPENMP_3_1)
-      65             :                 #pragma omp atomic capture
-      66             :                 {newRef = _referenceCount--;}
-      67             : #elif defined(__GNUC__)
-      68    10914622 :                 newRef = __sync_sub_and_fetch(&_referenceCount, 1);
-      69             : #else
-      70             :                 #pragma omp critical
-      71             :                 {newRef = _referenceCount--;}
-      72             : #endif
-      73             : 
-      74    10914622 :                 if (newRef == 0) {
-      75     3367410 :                         delete this;
-      76             :                 }
-      77    10914622 :                 return newRef;
-      78             :         }
-      79             : 
-      80             :         int removeReferenceNoDelete() const {
-      81           0 :                 return --_referenceCount;
-      82             :         }
-      83             : 
-      84             :         inline size_t getReferenceCount() const {
-      85           0 :                 return _referenceCount;
-      86             :         }
-      87             : 
-      88             : protected:
-      89             : 
-      90           0 :         virtual inline ~Referenced() {
-      91             : #ifdef DEBUG
-      92             :                 if (_referenceCount)
-      93             :                         std::cerr << "WARNING: Deleting Object with references: "
-      94             :                                         << typeid(*this).name() << std::endl;
-      95             : #endif
-      96           0 :         }
-      97             : 
-      98             :         mutable size_t _referenceCount;
-      99             : };
-     100             : 
-     101             : inline void intrusive_ptr_add_ref(Referenced* p) {
-     102             :         p->addReference();
-     103             : }
-     104             : inline void intrusive_ptr_release(Referenced* p) {
-     105           0 :         p->removeReference();
-     106             : }
-     107             : 
-     108             : /**
-     109             :  @class ref_ptr
-     110             :  @brief Referenced pointer
-     111             :  */
-     112             : template<class T>
-     113             : class ref_ptr {
-     114             : public:
-     115             :         typedef T element_type;
-     116             : 
-     117         167 :         ref_ptr() :
-     118         167 :                         _ptr(0) {
-     119             :         }
-     120     3328293 :         ref_ptr(T* ptr) :
-     121     3330334 :                         _ptr(ptr) {
-     122        3307 :                 if (_ptr)
-     123             :                         _ptr->addReference();
-     124             :         }
-     125     7541490 :         ref_ptr(const ref_ptr& rp) :
-     126     7541372 :                         _ptr(rp._ptr) {
-     127     7541428 :                 if (_ptr)
-     128             :                         _ptr->addReference();
-     129           2 :         }
-     130           4 :         template<class Other> ref_ptr(const ref_ptr<Other>& rp) :
-     131           4 :                         _ptr(rp._ptr) {
-     132             :                 if (_ptr)
-     133             :                         _ptr->addReference();
-     134             :         }
-     135             : 
-     136             :         ~ref_ptr() {
-     137    10870856 :                 if (_ptr)
-     138    10870929 :                         _ptr->removeReference();
-     139             :                 _ptr = 0;
-     140    10870851 :         }
-     141             : 
-     142             :         ref_ptr& operator =(const ref_ptr& rp) {
-     143         218 :                 assign(rp);
-     144           0 :                 return *this;
-     145             :         }
-     146             : 
-     147             :         template<class Other> ref_ptr& operator =(const ref_ptr<Other>& rp) {
-     148             :                 assign(rp);
-     149             :                 return *this;
-     150             :         }
-     151             : 
-     152          78 :         inline ref_ptr& operator =(T* ptr) {
-     153          78 :                 if (_ptr == ptr)
-     154             :                         return *this;
-     155             :                 T* tmp_ptr = _ptr;
-     156          78 :                 _ptr = ptr;
-     157          78 :                 if (_ptr)
-     158             :                         _ptr->addReference();
-     159          78 :                 if (tmp_ptr)
-     160          68 :                         tmp_ptr->removeReference();
-     161             :                 return *this;
-     162             :         }
-     163             : 
-     164             :         operator T*() const {
-     165      481185 :                 return _ptr;
-     166             :         }
-     167             : 
-     168             :         T& operator*() const {
-     169        6611 :                 return *_ptr;
-     170             :         }
-     171             :         T* operator->() const {
-     172     6292284 :                 return _ptr;
-     173             :         }
-     174             :         T* get() const {
-     175          37 :                 return _ptr;
-     176             :         }
-     177             : 
-     178             :         bool operator!() const {
-     179           0 :                 return _ptr == 0;
-     180             :         } // not required
-     181             :         bool valid() const {
-     182     5881570 :                 return _ptr != 0;
-     183             :         }
-     184             : 
-     185             :         T* release() {
-     186           0 :                 T* tmp = _ptr;
-     187           0 :                 if (_ptr)
-     188             :                         _ptr->removeReferenceNoDelete();
-     189           0 :                 _ptr = 0;
-     190             :                 return tmp;
-     191             :         }
-     192             : 
-     193             :         void swap(ref_ptr& rp) {
-     194           0 :                 T* tmp = _ptr;
-     195           0 :                 _ptr = rp._ptr;
-     196           0 :                 rp._ptr = tmp;
-     197             :         }
-     198             : 
-     199             : private:
-     200             : 
-     201        1319 :         template<class Other> void assign(const ref_ptr<Other>& rp) {
-     202        1319 :                 if (_ptr == rp._ptr)
-     203             :                         return;
-     204             :                 T* tmp_ptr = _ptr;
-     205        1315 :                 _ptr = rp._ptr;
-     206        1315 :                 if (_ptr)
-     207             :                         _ptr->addReference();
-     208        1315 :                 if (tmp_ptr)
-     209          91 :                         tmp_ptr->removeReference();
-     210             :         }
-     211             : 
-     212             :         template<class Other> friend class ref_ptr;
-     213             : 
-     214             :         T* _ptr;
-     215             : };
-     216             : 
-     217             : template<class T> inline
-     218             : void swap(ref_ptr<T>& rp1, ref_ptr<T>& rp2) {
-     219             :         rp1.swap(rp2);
-     220             : }
-     221             : 
-     222             : template<class T> inline T* get_pointer(const ref_ptr<T>& rp) {
-     223             :         return rp.get();
-     224             : }
-     225             : 
-     226             : template<class T, class Y> inline ref_ptr<T> static_pointer_cast(
-     227             :                 const ref_ptr<Y>& rp) {
-     228             :         return static_cast<T*>(rp.get());
-     229             : }
-     230             : 
-     231             : template<class T, class Y> inline ref_ptr<T> dynamic_pointer_cast(
-     232             :                 const ref_ptr<Y>& rp) {
-     233             :         return dynamic_cast<T*>(rp.get());
-     234             : }
-     235             : 
-     236             : template<class T, class Y> inline ref_ptr<T> const_pointer_cast(
-     237             :                 const ref_ptr<Y>& rp) {
-     238             :         return const_cast<T*>(rp.get());
-     239             : }
-     240             : 
-     241             : /** @}*/
-     242             : } // namespace crpropa
-     243             : 
-     244             : #endif // CRPROPA_REFERENCED_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Source.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Source.h.func-sort-c.html deleted file mode 100644 index e0c693ff0..000000000 --- a/doc/coverageReport/include/crpropa/Source.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Source.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Source.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:141877.8 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13SourceFeature15prepareParticleERNS_13ParticleStateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Source.h.func.html b/doc/coverageReport/include/crpropa/Source.h.func.html deleted file mode 100644 index 646b8d073..000000000 --- a/doc/coverageReport/include/crpropa/Source.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Source.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Source.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:141877.8 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13SourceFeature15prepareParticleERNS_13ParticleStateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Source.h.gcov.html b/doc/coverageReport/include/crpropa/Source.h.gcov.html deleted file mode 100644 index 82cca4d84..000000000 --- a/doc/coverageReport/include/crpropa/Source.h.gcov.html +++ /dev/null @@ -1,1002 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Source.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Source.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:141877.8 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_SOURCE_H
-       2             : #define CRPROPA_SOURCE_H
-       3             : 
-       4             : #include "crpropa/Candidate.h"
-       5             : #include "crpropa/Grid.h"
-       6             : #include "crpropa/EmissionMap.h"
-       7             : #include "crpropa/massDistribution/Density.h"
-       8             : 
-       9             : 
-      10             : #include <vector>
-      11             : 
-      12             : namespace crpropa {
-      13             : /** @addtogroup SourceFeatures
-      14             :  *  @{
-      15             :  */
-      16             : 
-      17             : 
-      18             : /**
-      19             :  @class SourceFeature
-      20             :  @brief Abstract base class for specific source features
-      21             :  */
-      22           7 : class SourceFeature: public Referenced {
-      23             : protected:
-      24             :         std::string description;
-      25             : public:
-      26           0 :         virtual void prepareParticle(ParticleState& particle) const {};
-      27             :         virtual void prepareCandidate(Candidate& candidate) const;
-      28             :         std::string getDescription() const;
-      29             : };
-      30             : 
-      31             : 
-      32             : /**
-      33             :  @class SourceInterface
-      34             :  @brief Abstract base class for sources
-      35             :  */
-      36             : class SourceInterface : public Referenced {
-      37             : public:
-      38             :         virtual ref_ptr<Candidate> getCandidate() const = 0;
-      39             :         virtual std::string getDescription() const = 0;
-      40             : };
-      41             : 
-      42             : 
-      43             : /**
-      44             :  @class Source
-      45             :  @brief General source of particles
-      46             : 
-      47             :  This class is a container for source features.
-      48             :  The source prepares a new candidate by passing it to all its source features
-      49             :  to be modified accordingly.
-      50             :  */
-      51          10 : class Source: public SourceInterface {
-      52             :         std::vector<ref_ptr<SourceFeature> > features;
-      53             : public:
-      54             :         void add(SourceFeature* feature);
-      55             :         ref_ptr<Candidate> getCandidate() const;
-      56             :         std::string getDescription() const;
-      57             : };
-      58             : 
-      59             : 
-      60             : /**
-      61             :  @class SourceList
-      62             :  @brief List of particle sources of individual luminosities.
-      63             : 
-      64             :  The SourceList is a source itself. It can be used if several sources are
-      65             :  needed in one simulation.
-      66             :  */
-      67           3 : class SourceList: public SourceInterface {
-      68             :         std::vector<ref_ptr<Source> > sources;
-      69             :         std::vector<double> cdf;
-      70             : public:
-      71             :         /** Add an individual source to the list.
-      72             :          @param source          source to be added
-      73             :          @param weight          weight of the source; defaults to 1.
-      74             :          */
-      75             :         void add(Source* source, double weight = 1);
-      76             :         ref_ptr<Candidate> getCandidate() const;
-      77             :         std::string getDescription() const;
-      78             : };
-      79             : 
-      80             : 
-      81             : /**
-      82             :  @class SourceParticleType
-      83             :  @brief Particle type at the source
-      84             : 
-      85             :  This feature assigns a single particle type to the source.
-      86             :  For multiple types, use e.g. SourceMultipleParticleTypes.
-      87             :  Particles are identified following the PDG numbering scheme:
-      88             :    https://pdg.lbl.gov/2019/reviews/rpp2019-rev-monte-carlo-numbering.pdf
-      89             :  */
-      90             : class SourceParticleType: public SourceFeature {
-      91             :         int id;
-      92             : public:
-      93             :         /** Constructor for a source with a sign
-      94             :          @param id              id of the particle following the PDG numbering scheme
-      95             :         */
-      96             :         SourceParticleType(int id);
-      97             :         void prepareParticle(ParticleState &particle) const;
-      98             :         void setDescription();
-      99             : };
-     100             : 
-     101             : 
-     102             : /**
-     103             :  @class SourceMultipleParticleTypes
-     104             :  @brief Multiple particle types with individual relative abundances
-     105             : 
-     106             :  This feature assigns particle types to the events emitted by the sources.
-     107             :  It is possible to control the relative abundance of each particle species.
-     108             :  Particles are identified following the PDG numbering scheme:
-     109             :    https://pdg.lbl.gov/2019/reviews/rpp2019-rev-monte-carlo-numbering.pdf
-     110             :  */
-     111             : class SourceMultipleParticleTypes: public SourceFeature {
-     112             :         std::vector<int> particleTypes;
-     113             :         std::vector<double> cdf;
-     114             : public:
-     115             :         /** Constructor
-     116             :          */
-     117             :         SourceMultipleParticleTypes();
-     118             :         /** Add an individual particle type.
-     119             :          @param id                      id of the particle following the PDG numbering scheme
-     120             :          @param weight          relative abundance of individual particle species
-     121             :          */
-     122             :         void add(int id, double weight = 1);
-     123             :         void prepareParticle(ParticleState &particle) const;
-     124             :         void setDescription();
-     125             : };
-     126             : 
-     127             : 
-     128             : /**
-     129             :  @class SourceEnergy
-     130             :  @brief Sets the initial energy of the emitted particles to a specific value
-     131             : 
-     132             :  This feature assigns a monochromatic spectrum, i.e., a single energy to all particles.
-     133             :  */
-     134             : class SourceEnergy: public SourceFeature {
-     135             :         double E;
-     136             : public:
-     137             :         /** Constructor
-     138             :          @param energy          energy of the particle (in Joules)
-     139             :          */
-     140             :         SourceEnergy(double energy);
-     141             :         void prepareParticle(ParticleState &particle) const;
-     142             :         void setDescription();
-     143             : };
-     144             : 
-     145             : 
-     146             : /**
-     147             :  @class SourcePowerLawSpectrum
-     148             :  @brief Particle energy following a power-law spectrum
-     149             : 
-     150             :  The power law is of the form: dN/dE ~ E^index, for energies in the interval [Emin, Emax].
-     151             :  */
-     152           1 : class SourcePowerLawSpectrum: public SourceFeature {
-     153             :         double Emin;
-     154             :         double Emax;
-     155             :         double index;
-     156             : public:
-     157             :         /** Constructor
-     158             :          @param Emin            minimum energy (in Joules)
-     159             :          @param Emax            maximum energy (in Joules)
-     160             :          @param index           spectral index of the power law
-     161             :          */
-     162             :         SourcePowerLawSpectrum(double Emin, double Emax, double index);
-     163             :         void prepareParticle(ParticleState &particle) const;
-     164             :         void setDescription();
-     165             : };
-     166             : 
-     167             : 
-     168             : /**
-     169             :  @class SourceComposition
-     170             :  @brief Multiple nuclear species with a rigidity-dependent power-law spectrum
-     171             : 
-     172             :  The power law is of the form: E^index, for energies in the interval [Emin, Z * Rmax].
-     173             :  */
-     174             : class SourceComposition: public SourceFeature {
-     175             :         double Emin;
-     176             :         double Rmax;
-     177             :         double index;
-     178             :         std::vector<int> nuclei;
-     179             :         std::vector<double> cdf;
-     180             : public:
-     181             :         /** Constructor
-     182             :          @param Emin            minimum energy (in Joules)
-     183             :          @param Rmax            maximum rigidity (in Volts)
-     184             :          @param index           spectral index of the power law
-     185             :          */
-     186             :         SourceComposition(double Emin, double Rmax, double index);
-     187             :         /** Add individual particle species with a given abundance
-     188             :          @param id                      id of the particle following the PDG numbering scheme
-     189             :          @param abundance       relative abundance of the particle species
-     190             :          */
-     191             :         void add(int id, double abundance);
-     192             :         /** Add individual particle species with a given abundance
-     193             :          @param A                       atomic mass of the cosmic-ray nucleus
-     194             :          @param Z                       atomic number of the cosmic-ray nucleus
-     195             :          @param abundance       relative abundance of the particle species
-     196             :          */
-     197             :         void add(int A, int Z, double abundance);
-     198             :         void prepareParticle(ParticleState &particle) const;
-     199             :         void setDescription();
-     200             : };
-     201             : 
-     202             : 
-     203             : /**
-     204             :  @class SourcePosition
-     205             :  @brief Position of a point source
-     206             :  */
-     207           1 : class SourcePosition: public SourceFeature {
-     208             :         Vector3d position; 
-     209             : public:
-     210             :         /** Constructor for a source in 3D
-     211             :          @param position        vector containing the coordinates of the point source [in meters]
-     212             :          */
-     213             :         SourcePosition(Vector3d position);
-     214             :         /** Constructor for a source in 1D
-     215             :          @param d       distance of the point source to the observer at x = 0 [in meters]; 
-     216             :                                 internally this will be converted to a vector with x-coordinate equal to d
-     217             :          */
-     218             :         SourcePosition(double d);
-     219             :         void prepareParticle(ParticleState &state) const;
-     220             :         void setDescription();
-     221             : };
-     222             : 
-     223             : 
-     224             : /**
-     225             :  @class SourceMultiplePositions
-     226             :  @brief Multiple point-source positions with individual luminosities
-     227             :  */
-     228             : class SourceMultiplePositions: public SourceFeature {
-     229             :         std::vector<Vector3d> positions;
-     230             :         std::vector<double> cdf;
-     231             : public:
-     232             :         /** Constructor.
-     233             :          The sources must be added individually to the object.
-     234             :          */
-     235             :         SourceMultiplePositions();
-     236             :         /** Add an individual source with a given luminosity/contribution.
-     237             :          @param position        vector containing the coordinates of the point source [in meters]
-     238             :          @param weight          luminosity/contribution of the individual source
-     239             :          */
-     240             :         void add(Vector3d position, double weight = 1);
-     241             :         void prepareParticle(ParticleState &particle) const;
-     242             :         void setDescription();
-     243             : };
-     244             : 
-     245             : 
-     246             : /**
-     247             :  @class SourceUniformSphere
-     248             :  @brief Uniform distribution of sources in a spherical volume
-     249             :  */
-     250           1 : class SourceUniformSphere: public SourceFeature {
-     251             :         Vector3d center;
-     252             :         double radius;
-     253             : public:
-     254             :         /** Constructor
-     255             :          @param center          vector containing the coordinates of the center of the sphere
-     256             :          @param radius          radius of the sphere
-     257             :          */
-     258             :         SourceUniformSphere(Vector3d center, double radius);
-     259             :         void prepareParticle(ParticleState &particle) const;
-     260             :         void setDescription();
-     261             : };
-     262             : 
-     263             : 
-     264             : /**
-     265             :  @class SourceUniformHollowSphere
-     266             :  @brief Uniform distribution of sources between two spheres
-     267             :  */
-     268           1 : class SourceUniformHollowSphere: public SourceFeature {
-     269             :         Vector3d center;
-     270             :         double radius_inner;
-     271             :         double radius_outer;
-     272             : public:
-     273             :         /** Constructor
-     274             :          @param center                  vector containing the coordinates of the center of the sphere
-     275             :          @param radius_inner    radius of the inner sphere
-     276             :          @param radius_outer    radius of the outer sphere
-     277             :          */
-     278             :         SourceUniformHollowSphere(Vector3d center,
-     279             :                         double radius_inner, double radius_outer);
-     280             :         void prepareParticle(ParticleState &particle) const;
-     281             :         void setDescription();
-     282             : };
-     283             : 
-     284             : 
-     285             : /**
-     286             :  @class SourceUniformShell
-     287             :  @brief Uniform distribution of source positions on the surface of a sphere
-     288             :  */
-     289             : class SourceUniformShell: public SourceFeature {
-     290             :         Vector3d center;
-     291             :         double radius;
-     292             : public:
-     293             :         /** Constructor
-     294             :          @param center          vector containing the coordinates of the center of the sphere
-     295             :          @param radius          radius of the sphere
-     296             :          */
-     297             :         SourceUniformShell(Vector3d center, double radius);
-     298             :         void prepareParticle(ParticleState &particle) const;
-     299             :         void setDescription();
-     300             : };
-     301             : 
-     302             : 
-     303             : /**
-     304             :  @class SourceUniformBox
-     305             :  @brief Uniform random source positions inside a box. The box is aligned with the coordinate axes.
-     306             :  */
-     307           1 : class SourceUniformBox: public SourceFeature {
-     308             :         Vector3d origin;        // lower box corner
-     309             :         Vector3d size;          // sizes along each coordinate axes.
-     310             : public:
-     311             :         /** Constructor
-     312             :          @param origin  vector corresponding to the lower box corner
-     313             :          @param size    vector corresponding to the box sizes along each direction
-     314             :          */
-     315             :         SourceUniformBox(Vector3d origin, Vector3d size);
-     316             :         void prepareParticle(ParticleState &particle) const;
-     317             :         void setDescription();
-     318             : };
-     319             : 
-     320             : 
-     321             : /**
-     322             :  @class SourceUniformCylinder
-     323             :  @brief Uniform distribution of source positions inside the volume of a cylinder whose axis is along the z-axis. 
-     324             : 
-     325             :  The circle of the cylinder lays in the xy-plane and the height is along the z-axis.
-     326             :  */
-     327           1 : class SourceUniformCylinder: public SourceFeature {
-     328             :         Vector3d origin;        // central point of cylinder 
-     329             :         double height;          // total height of the cylinder along z-axis. Half over/under the center.
-     330             :         double radius;          // radius of the cylinder in the xy-plane
-     331             : public:
-     332             :         /** Constructor
-     333             :          @param origin  vector corresponding to the center of the cylinder axis
-     334             :          @param height  height of the cylinder, half lays over the origin, half is lower
-     335             :          @param radius  radius of the cylinder
-     336             :          */
-     337             :         SourceUniformCylinder(Vector3d origin, double height, double radius);
-     338             :         void prepareParticle(ParticleState &particle) const;
-     339             :         void setDescription();
-     340             : };
-     341             : 
-     342             : 
-     343             : /**
-     344             :  @class SourceSNRDistribution
-     345             :  @brief Source distribution that follows the Galactic SNR distribution in 2D
-     346             : 
-     347             :  The origin of the distribution is the Galactic center. The default maximum radius is set 
-     348             :  to rMax=20 kpc and the default maximum height is zMax = 5 kpc.
-     349             :  See G. Case and D. Bhattacharya (1996) for the details of the distribution.
-     350             :  */
-     351           1 : class SourceSNRDistribution: public SourceFeature {
-     352             :         double rEarth; // parameter given by observation
-     353             :         double alpha; // parameter to shift the maximum in R direction
-     354             :         double beta; // parameter to shift the maximum in R direction
-     355             :         double zg; // exponential cut parameter in z direction
-     356             :         double frMax; // helper for efficient sampling
-     357             :         double fzMax; // helper for efficient sampling
-     358             :         double rMax; // maximum radial distance - default 20 kpc 
-     359             :                       // (due to the extension of the JF12 field)
-     360             :         double zMax; // maximum distance from galactic plane - default 5 kpc
-     361             :         void setFrMax(); // calculate frMax with the current parameter. 
-     362             : 
-     363             : public:
-     364             :         /** Default constructor. 
-     365             :          Default parameters are:
-     366             :          . rEarth = 8.5 kpc
-     367             :          . alpha = 2
-     368             :          . beta = 3.53
-     369             :          . zg = 300 pc
-     370             :          . rMax = 20 kpc
-     371             :          . zMax = 5 kpc
-     372             :         */ 
-     373             :         SourceSNRDistribution();
-     374             :         /** Generic constructor
-     375             :          @param rEarth    distance from Earth to the Galactic centre [in meters]
-     376             :          @param alpha     parameter that shifts radially the maximum of the distributions
-     377             :          @param beta      parameter that shifts radially the maximum of the distributions 
-     378             :          @param zg                exponential cut-off parameter in the z-direction [in meters]
-     379             :         */      
-     380             :         SourceSNRDistribution(double rEarth,double alpha, double beta, double zg);
-     381             : 
-     382             :         void prepareParticle(ParticleState &particle) const;
-     383             :         /**
-     384             :          radial distribution of the SNR density.
-     385             :          @param r       galactocentric radius in [meter]
-     386             :         */
-     387             :         double fr(double r) const;
-     388             :         /**
-     389             :          height distribution of the SNR density.
-     390             :          @param z       height over/under the galactic plane in [meter]
-     391             :         */
-     392             :         double fz(double z) const;
-     393             : 
-     394             :         /**
-     395             :          Set the exponential cut-off parameter in the z-direction.
-     396             :          @param Zg      cut-off parameter
-     397             :         */
-     398             :         void setFzMax(double Zg);
-     399             : 
-     400             :         /**
-     401             :          @param rMax maximal radius up to which sources are possible
-     402             :         */
-     403             :         void setRMax(double rMax);
-     404             : 
-     405             :         /**
-     406             :          @param zMax maximal height up to which sources are possible
-     407             :         */
-     408             :         void setZMax(double zMax);
-     409             : 
-     410             :         // parameter for the raidal distribution
-     411             :         void setAlpha(double a);
-     412             :         // parameter for the exponential cut-off in the radial distribution
-     413             :         void setBeta(double b);
-     414             :         double getFrMax() const;
-     415             :         double getFzMax() const;
-     416             :         double getRMax() const;
-     417             :         double getZMax() const;
-     418             :         double getAlpha() const;
-     419             :         double getBeta() const;
-     420             :         void setDescription();
-     421             : };
-     422             : 
-     423             : 
-     424             : /**
-     425             :  @class SourcePulsarDistribution
-     426             :  @brief Source distribution following the Galactic pulsar distribution
-     427             : 
-     428             :  A logarithmic spiral with four arms is used for the radial distribution.
-     429             :  The z-distribution is a simple exponentially decaying distribution.
-     430             :  The pulsar distribution is explained in detail in C.-A. Faucher-Giguere
-     431             :  and V. M. Kaspi, ApJ 643 (May, 2006) 332. The radial distribution is 
-     432             :  parametrized as in Blasi and Amato, JCAP 1 (Jan., 2012) 10.
-     433             :  */
-     434             : class SourcePulsarDistribution: public SourceFeature {
-     435             :         double rEarth; // parameter given by observation
-     436             :         double beta; // parameter to shift the maximum in R direction
-     437             :         double zg; // exponential cut parameter in z direction
-     438             :         double frMax; // helper for efficient sampling
-     439             :         double fzMax; // helper for efficient sampling
-     440             :         double rMax; // maximum radial distance - default 22 kpc 
-     441             :         double zMax; // maximum distance from galactic plane - default 5 kpc
-     442             :         double rBlur; // relative smearing factor for the radius
-     443             :         double thetaBlur; // smearing factor for the angle. Unit = [1/length]
-     444             : public:
-     445             :         /** Default constructor. 
-     446             :          Default parameters are:
-     447             :          . rEarth = 8.5 kpc
-     448             :          . beta = 3.53
-     449             :          . zg = 300 pc
-     450             :          . Rmax = 22 kpc
-     451             :          . Zmax = 5 kpc
-     452             :          . rBlur = 0.07
-     453             :          . thetaBlur = 0.35 / kpc
-     454             :          */ 
-     455             :         SourcePulsarDistribution();     
-     456             :         /** Generic constructor
-     457             :          @param rEarth          distance from Earth to the Galactic centre [in meters]
-     458             :          @param beta            parameter that shifts radially the maximum of the distributions 
-     459             :          @param zg                      exponential cut-off parameter in the z-direction [in meters]
-     460             :          @param rBlur           relative smearing factor for radius
-     461             :          @param thetaBlur       smearing factor for the angle [in 1 / meters]
-     462             :          */     
-     463             :         SourcePulsarDistribution(double rEarth, double beta, double zg, double rBlur, double thetaBlur);
-     464             :         void prepareParticle(ParticleState &particle) const;
-     465             : 
-     466             :         /** 
-     467             :          radial distribution of pulsars
-     468             :          @param r       galactocentric radius
-     469             :         */
-     470             :         double fr(double r) const;
-     471             :         /**
-     472             :          z distribution of pulsars
-     473             :          @param z       height over/under the galactic plane
-     474             :         */
-     475             :         double fz(double z) const;
-     476             :         double ftheta(int i, double r) const;
-     477             :         double blurR(double r_tilde) const;
-     478             :         double blurTheta(double theta_tilde, double r_tilde) const;
-     479             :         void setFrMax(double R, double b);
-     480             :         void setFzMax(double zg);
-     481             :         void setRMax(double rMax);
-     482             :         void setZMax(double zMax);
-     483             :         void setRBlur(double rBlur);
-     484             :         void setThetaBlur(double thetaBlur);
-     485             :         double getFrMax();
-     486             :         double getFzMax();
-     487             :         double getRMax();
-     488             :         double getZMax();
-     489             :         double getRBlur();
-     490             :         double getThetaBlur();
-     491             :         void setDescription();
-     492             : };
-     493             : 
-     494             : 
-     495             : /**
-     496             :  @class SourceUniform1D
-     497             :  @brief Uniform source distribution in 1D
-     498             : 
-     499             :  This source property sets random x-coordinates according to a uniform source
-     500             :  distribution in a given distance interval. If cosmological effects are included, 
-     501             :  this is done by drawing a light-travel distance from a flat distribution and
-     502             :  converting to a comoving distance. In the absence of cosmological effects, the
-     503             :  positions are drawn uniformly in the light-travel distance interval (as opposed
-     504             :  to a comoving interval).
-     505             :  The source positions are assigned to the x-coordinate (Vector3d(distance, 0, 0))
-     506             :  in this one-dimensional case.
-     507             :  */
-     508             : class SourceUniform1D: public SourceFeature {
-     509             :         double minD; // minimum light-travel distance
-     510             :         double maxD; // maximum light-travel distance
-     511             :         bool withCosmology;     // whether to account for cosmological effects (expansion of the Universe)
-     512             : public:
-     513             :         /** Constructor
-     514             :          @param minD                    minimum distance; comoving if withCosmology is True
-     515             :          @param maxD                    maximum distance; comoving if withCosmology is True
-     516             :          @param withCosmology   whether to account for cosmological effects (expansion of the Universe)
-     517             :          */
-     518             :         SourceUniform1D(double minD, double maxD, bool withCosmology = true);
-     519             :         void prepareParticle(ParticleState& particle) const;
-     520             :         void setDescription();
-     521             : };
-     522             : 
-     523             : 
-     524             : /**
-     525             :  @class SourceDensityGrid
-     526             :  @brief Random source positions from a density grid
-     527             :  */
-     528             : class SourceDensityGrid: public SourceFeature {
-     529             :         ref_ptr<Grid1f> grid;
-     530             : public:
-     531             :         /** Constructor
-     532             :          @param densityGrid     3D grid containing the density of sources in each cell
-     533             :          */
-     534             :         SourceDensityGrid(ref_ptr<Grid1f> densityGrid);
-     535             :         void prepareParticle(ParticleState &particle) const;
-     536             :         void setDescription();
-     537             : };
-     538             : 
-     539             : 
-     540             : /**
-     541             :  @class SourceDensityGrid1D
-     542             :  @brief Random source positions from a 1D density grid
-     543             :  */
-     544             : class SourceDensityGrid1D: public SourceFeature {
-     545             :         ref_ptr<Grid1f> grid;     // 1D grid with Ny = Nz = 1
-     546             : public:
-     547             :         /** Constructor
-     548             :          @param densityGrid     1D grid containing the density of sources in each cell, Ny and Nz must be 1
-     549             :          */
-     550             :         SourceDensityGrid1D(ref_ptr<Grid1f> densityGrid);
-     551             :         void prepareParticle(ParticleState &particle) const;
-     552             :         void setDescription();
-     553             : };
-     554             : 
-     555             : 
-     556             : /**
-     557             :  @class SourceIsotropicEmission
-     558             :  @brief Isotropic emission from a source
-     559             :  */
-     560             : class SourceIsotropicEmission: public SourceFeature {
-     561             : public:
-     562             :         /** Constructor
-     563             :          */
-     564             :         SourceIsotropicEmission();
-     565             :         void prepareParticle(ParticleState &particle) const;
-     566             :         void setDescription();
-     567             : };
-     568             : 
-     569             : 
-     570             : /**
-     571             :  @class SourceDirectedEmission
-     572             :  @brief Directed emission from a source from the von-Mises-Fisher distribution 
-     573             :  
-     574             :  The emission from the source is generated following the von-Mises-Fisher distribution
-     575             :  with mean direction mu and concentration parameter kappa.
-     576             :  The sampling from the vMF distribution follows this document by Julian Straub:
-     577             :  http://people.csail.mit.edu/jstraub/download/straub2017vonMisesFisherInference.pdf
-     578             :  The emitted particles are assigned a weight so that the detected particles can be
-     579             :  reweighted to an isotropic emission distribution instead of a vMF distribution.
-     580             :  For details, see PoS (ICRC2019) 447.
-     581             :  */
-     582           1 : class SourceDirectedEmission: public SourceFeature {
-     583             :         Vector3d mu; // Mean emission direction in the vMF distribution
-     584             :         double kappa; // Concentration parameter of the vMF distribution
-     585             : public:
-     586             :         /** Constructor
-     587             :          @param mu      mean direction of the emission, mu should be normelized
-     588             :          @param kappa   concentration parameter
-     589             :         */
-     590             :         SourceDirectedEmission(Vector3d mu, double kappa);
-     591             :         void prepareCandidate(Candidate &candidate) const;
-     592             :         void setDescription();
-     593             : };
-     594             : 
-     595             : /**
-     596             :  @class SourceLambertDistributionOnSphere
-     597             :  @brief Uniform random position on a sphere with isotropic Lamberts distributed directions.
-     598             : 
-     599             :  This function should be used for crosschecking the arrival distribution for a
-     600             :  Galactic propagation with an isotropic arrival distribution at the Edge of our
-     601             :  Galaxy. Note, that for simulation speed you should rather use the backtracking
-     602             :  technique: see e.g. http://physik.rwth-aachen.de/parsec
-     603             :  */
-     604             : class SourceLambertDistributionOnSphere: public SourceFeature {
-     605             :         Vector3d center;        // center of the sphere
-     606             :         double radius;          // radius of the sphere
-     607             :         bool inward;            // if true, direction point inwards
-     608             : public:
-     609             :         /** Constructor
-     610             :          @param center          vector containing the coordinates of the center of the sphere
-     611             :          @param radius          radius of the sphere
-     612             :          @param inward          if true, the directions point inwards
-     613             :          */
-     614             :         SourceLambertDistributionOnSphere(const Vector3d &center, double radius, bool inward);
-     615             :         void prepareParticle(ParticleState &particle) const;
-     616             :         void setDescription();
-     617             : };
-     618             : 
-     619             : 
-     620             : /**
-     621             :  @class SourceDirection
-     622             :  @brief Collimated emission along a specific direction
-     623             :  */
-     624             : class SourceDirection: public SourceFeature {
-     625             :         Vector3d direction;
-     626             : public:
-     627             :         /** Constructor
-     628             :          @param direction       Vector3d corresponding to the direction of emission
-     629             :          */
-     630             :         SourceDirection(Vector3d direction = Vector3d(-1, 0, 0));
-     631             :         void prepareParticle(ParticleState &particle) const;
-     632             :         void setDescription();
-     633             : };
-     634             : 
-     635             : 
-     636             : /**
-     637             :  @class SourceEmissionMap
-     638             :  @brief Deactivate Candidate if it has zero probability in provided EmissionMap. 
-     639             : 
-     640             :         This feature does not change the direction of the candidate. Therefore a usefull direction feature (isotropic or directed emission)
-     641             :         must be added to the sources before. The propability of the emission map is not taken into account. 
-     642             :  */
-     643             : class SourceEmissionMap: public SourceFeature {
-     644             :         ref_ptr<EmissionMap> emissionMap;
-     645             : public:
-     646             :         /** Constructor
-     647             :          @param emissionMap             emission map containing probabilities of emission in various directions
-     648             :          */
-     649             :         SourceEmissionMap(EmissionMap *emissionMap);
-     650             :         void prepareCandidate(Candidate &candidate) const;
-     651             :         void setEmissionMap(EmissionMap *emissionMap);
-     652             :         void setDescription();
-     653             : };
-     654             : 
-     655             : 
-     656             : /**
-     657             :  @class SourceEmissionCone
-     658             :  @brief Uniform emission within a cone
-     659             :  */
-     660           1 : class SourceEmissionCone: public SourceFeature {
-     661             :         Vector3d direction;
-     662             :         double aperture;
-     663             : public:
-     664             :         /** Constructor
-     665             :          @param direction               Vector3d corresponding to the cone axis 
-     666             :          @param aperture                opening angle of the cone
-     667             :          */
-     668             :         SourceEmissionCone(Vector3d direction, double aperture);
-     669             :         void prepareParticle(ParticleState &particle) const;
-     670             : 
-     671             :         /**
-     672             :          @param direction Vector3d corresponding to the cone axis
-     673             :         */
-     674             :         void setDirection(Vector3d direction);
-     675             :         void setDescription();
-     676             : };
-     677             : 
-     678             : 
-     679             : /**
-     680             :  @class SourceRedshift
-     681             :  @brief Emission of particles at a specific redshift (or time)
-     682             : 
-     683             :  The redshift coordinate is used to treat cosmological effects and as a time coordinate.
-     684             :  Consider, for instance, a source located at a distance corresponding to a redshift z. 
-     685             :  In the absence of processes that cause time delays (e.g., magnetic deflections), particles
-     686             :  from this source could arrive after a time corresponding to the source redshift. Charged 
-     687             :  particles, on the other hand, can arrive at a time later than the corresponding straight-
-     688             :  line travel duration. 
-     689             :  This treatment is also useful for time-dependent studies (e.g. transient sources).
-     690             :  */
-     691             : class SourceRedshift: public SourceFeature {
-     692             :         double z;
-     693             : public:
-     694             :         /** Constructor
-     695             :          @param z               redshift of emission
-     696             :          */
-     697             :         SourceRedshift(double z);
-     698             :         void prepareCandidate(Candidate &candidate) const;
-     699             :         void setDescription();
-     700             : };
-     701             : 
-     702             : 
-     703             : /**
-     704             :  @class SourceUniformRedshift
-     705             :  @brief Random redshift (time of emission) from a uniform distribution
-     706             : 
-     707             :  This function assigns random redshifts to the particles emitted by a given source.
-     708             :  These values are drawn from a uniform redshift distribution in the interval [zmin, zmax].
-     709             :  The redshift coordinate is used to treat cosmological effects and as a time coordinate.
-     710             :  Consider, for instance, a source located at a distance corresponding to a redshift z. 
-     711             :  In the absence of processes that cause time delays (e.g., magnetic deflections), particles
-     712             :  from this source could arrive after a time corresponding to the source redshift. Charged 
-     713             :  particles, on the other hand, can arrive at a time later than the corresponding straight-
-     714             :  line travel duration. 
-     715             :  This treatment is also useful for time-dependent studies (e.g. transient sources).
-     716             :  */
-     717             : class SourceUniformRedshift: public SourceFeature {
-     718             :         double zmin, zmax;
-     719             : public:
-     720             :         /** Constructor
-     721             :          @param zmin    minimum redshift
-     722             :          @param zmax    maximum redshift
-     723             :          */
-     724             :         SourceUniformRedshift(double zmin, double zmax);
-     725             :         void prepareCandidate(Candidate &candidate) const;
-     726             :         void setDescription();
-     727             : };
-     728             : 
-     729             : 
-     730             : /**
-     731             :  @class SourceRedshiftEvolution
-     732             :  @brief Random redshift (time of emission) from (1+z)^m distribution
-     733             : 
-     734             :  This assigns redshifts to a given source according to a typical power-law distribution.
-     735             :  The redshift coordinate is used to treat cosmological effects and as a time coordinate.
-     736             :  Consider, for instance, a source located at a distance corresponding to a redshift z. 
-     737             :  In the absence of processes that cause time delays (e.g., magnetic deflections), particles
-     738             :  from this source could arrive after a time corresponding to the source redshift. Charged 
-     739             :  particles, on the other hand, can arrive at a time later than the corresponding straight-
-     740             :  line travel duration. 
-     741             :  This treatment is also useful for time-dependent studies (e.g. transient sources).
-     742             :  */
-     743           2 : class SourceRedshiftEvolution: public SourceFeature {
-     744             :         double zmin, zmax;
-     745             :         double m;
-     746             : public:
-     747             :         /** Constructor
-     748             :          @param m               index of the power law (1 + z)^m
-     749             :          @param zmin    minimum redshift
-     750             :          @param zmax    maximum redshift
-     751             :          */
-     752             :         SourceRedshiftEvolution(double m, double zmin, double zmax);
-     753             :         void prepareCandidate(Candidate &candidate) const;
-     754             : };
-     755             : 
-     756             : 
-     757             : /**
-     758             :  @class SourceRedshift1D
-     759             :  @brief Redshift according to the distance to 0
-     760             : 
-     761             :  This source property sets the redshift according to the distance from 
-     762             :  the source to the origin (0, 0, 0). 
-     763             :  It must be added after the position of the source is set because it
-     764             :  computes the redshifts based on the source distance.
-     765             :  */
-     766             : class SourceRedshift1D: public SourceFeature {
-     767             : public:
-     768             :         /** Constructor
-     769             :          */
-     770             :         SourceRedshift1D();
-     771             :         void prepareCandidate(Candidate &candidate) const;
-     772             :         void setDescription();
-     773             : };
-     774             : 
-     775             : 
-     776             : #ifdef CRPROPA_HAVE_MUPARSER
-     777             : /**
-     778             :  @class SourceGenericComposition
-     779             :  @brief Add multiple cosmic rays with energies described by an expression string
-     780             : 
-     781             :  This is particularly useful if an arbitrary combination of nuclei types with 
-     782             :  specific energy spectra. The strings parsed may contain 'A' (atomic mass), 
-     783             :  'Z' (atomic number).  The following units are recognized as part of the strings:
-     784             :  GeV, TeV, PeV, EeV.  The variable for energy is 'E', with limits 'Emin', 'Emax'.
-     785             :  This property only works if muparser is available.
-     786             :  For details about the library see:
-     787             :         https://beltoforion.de/en/muparser/
-     788             :  */
-     789             : class SourceGenericComposition: public SourceFeature {
-     790             : public:
-     791           7 :         struct Nucleus {
-     792             :                 int id;
-     793             :                 std::vector<double> cdf;
-     794             :         };
-     795             :         /** Constructor
-     796             :          @param Emin            minimum energy [in Joules]
-     797             :          @param Emax            maximum energy [in Joules]
-     798             :          @param expression      string containing the expression to generate the composition
-     799             :          @param bins            number of energy bins
-     800             :          */
-     801             :         SourceGenericComposition(double Emin, double Emax, std::string expression, size_t bins = 1024);
-     802             :         /** Add an individual particle id.
-     803             :          @param id                      id of the particle following the PDG numbering scheme
-     804             :          @param abundance       relative abundance of individual particle species
-     805             :          */
-     806             :         void add(int id, double abundance);
-     807             :         /** Add an individual particle id.
-     808             :          @param A                       atomic mass of the cosmic-ray nucleus
-     809             :          @param Z                       atomic number of the cosmic-ray nucleus
-     810             :          @param abundance       relative abundance of individual particle species
-     811             :          */
-     812             :         void add(int A, int Z, double abundance);
-     813             :         void prepareParticle(ParticleState &particle) const;
-     814             :         void setDescription();
-     815             : 
-     816             :         const std::vector<double> *getNucleusCDF(int id) const {
-     817           0 :                 for (size_t i = 0; i < nuclei.size(); i++) {
-     818           0 :                         if (nuclei[i].id == id)
-     819           0 :                                 return &nuclei[i].cdf;
-     820             :                 }
-     821             :                 return 0;
-     822             :         }
-     823             : 
-     824             : protected:
-     825             :         double Emin, Emax;
-     826             :         size_t bins;
-     827             :         std::string expression;
-     828             :         std::vector<double> energy;
-     829             : 
-     830             :         std::vector<Nucleus> nuclei;
-     831             :         std::vector<double> cdf;
-     832             : 
-     833             : };
-     834             : #endif
-     835             : 
-     836             : /**
-     837             :  * @class SourceTag
-     838             :  * @brief All candidates from this source get a given tag. This can be used to distinguish between different sources that follow the same spatial distribution
-     839             :  * 
-     840             :  * Sets the tag of the candidate. Can be used to trace back additional candidate properties, e.g. production interaction or source type. 
-     841             :  * The interaction overwrites the candidate tag from the source for all secondaries. 
-     842             :  */
-     843             : 
-     844             : class SourceTag: public SourceFeature {
-     845             : private:
-     846             :         std::string sourceTag;
-     847             : 
-     848             : public:
-     849             :         SourceTag(std::string tag);
-     850             :         void prepareCandidate(Candidate &candidate) const;
-     851             :         void setDescription();
-     852             :         void setTag(std::string tag);
-     853             : };
-     854             : 
-     855             : /**
-     856             :         @class SourceMassDistribution
-     857             :         @brief  Source position follows a given mass distribution
-     858             : 
-     859             :         The (source)position of the candidate is sampled from a given mass distribution. The distribution uses the getDensity function of the density module. 
-     860             :         If a weighting for different components is desired, the use of different densities in a densityList is recommended.
-     861             : 
-     862             :         The sampling range of the position can be restricted. Default is a sampling for x in [-20, 20] * kpc, y in [-20, 20] * kpc and z in [-4, 4] * kpc.
-     863             : */
-     864             : class SourceMassDistribution: public SourceFeature {
-     865             : private: 
-     866             :         ref_ptr<Density> density; //< density distribution
-     867             :         double maxDensity;                      //< maximal value of the density in the region of interest
-     868             :         double xMin, xMax;                      //< x-range to sample positions
-     869             :         double yMin, yMax;                      //< y-range to sample positions
-     870             :         double zMin, zMax;                      //< z-range to sample positions
-     871             :         int maxTries = 10000;           //< maximal number of tries to sample the position 
-     872             : 
-     873             : public: 
-     874             :         /** Constructor
-     875             :         @param density: CRPropa mass distribution 
-     876             :         @param maxDensity:      maximal density in the region where the position should be sampled
-     877             :         @param x:       the position will be sampled in the range [-x, x]. Non symmetric values can be set with setXrange.
-     878             :         @param y:       the position will be sampled in the range [-y, y]. Non symmetric values can be set with setYrange.
-     879             :         @param z:       the position will be sampled in the range [-z, z]. Non symmetric values can be set with setZrange.
-     880             :         */
-     881             :         SourceMassDistribution(ref_ptr<Density> density, double maxDensity = 0, double x = 20 * kpc, double y = 20 * kpc, double z = 4 * kpc);
-     882             : 
-     883             :         void prepareParticle(ParticleState &particle) const;
-     884             : 
-     885             :         /** Set the maximal density in the region of interest. This parameter is necessary for the sampling
-     886             :         @param maxDensity:      maximal density in [particle / m^3]
-     887             :         */
-     888             :         void setMaximalDensity(double maxDensity);
-     889             : 
-     890             :         /** set x-range in which the position of the candidate will be sampled. x in [xMin, xMax].
-     891             :         @param xMin: minimal x value of the allowed sample range in [m]
-     892             :         @param xMax: maximal x value of the allowed sample range in [m]
-     893             :         */
-     894             :         void setXrange(double xMin, double xMax);
-     895             : 
-     896             :         /** set y-range in which the position of the candidate will be sampled. y in [yMin, yMax].
-     897             :         @param yMin: minimal y value of the allowed sample range in [m]
-     898             :         @param yMax: maximal y value of the allowed sample range in [m]
-     899             :         */
-     900             :         void setYrange(double yMin, double yMax);
-     901             : 
-     902             :         /** set z-range in which the position of the candidate will be sampled. z in [zMin, zMax].
-     903             :         @param zMin: minimal z value of the allowed sample range in [m]
-     904             :         @param zMax: maximal z value of the allowed sample range in [m]
-     905             :         */
-     906             :         void setZrange(double zMin, double zMax);
-     907             : 
-     908             :         /*      samples the position. Can be used for testing.
-     909             :                 @return Vector3d with sampled position
-     910             :         */
-     911             :         Vector3d samplePosition() const;
-     912             : 
-     913             : 
-     914             :         /** set the number of maximal tries until the sampling routine breaks.
-     915             :                 @param tries: number of the maximal tries
-     916             :         */
-     917             :         void setMaximalTries(int tries);
-     918             : 
-     919             :         std::string getDescription();
-     920             : };
-     921             : 
-     922             : /**  @} */ // end of group SourceFeature
-     923             : 
-     924             : } // namespace crpropa
-     925             : 
-     926             : #endif // CRPROPA_SOURCE_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html deleted file mode 100644 index fa4e80473..000000000 --- a/doc/coverageReport/include/crpropa/Variant.h.func-sort-c.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Variant.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Variant.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:133537.1 %
Date:2024-04-08 14:58:22Functions:41625.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10safeDeleteINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEEvRPT_0
_ZN7crpropa10safeDeleteISt6vectorINS_7VariantESaIS2_EEEEvRPT_0
_ZN7crpropa7Variant14bad_conversionC2ENS0_4TypeES2_0
_ZN7crpropa7Variant14bad_conversionD0Ev0
_ZN7crpropa7Variant14bad_conversionD2Ev0
_ZN7crpropa7VariantaSERKNS_7Vector3ISt7complexIdEEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IdEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IfEE0
_ZN7crpropa7VariantaSERKSt6vectorIS0_SaIS0_EE0
_ZN7crpropa7VariantaSERKSt7complexIdE0
_ZN7crpropa7VariantaSERKSt7complexIfE0
_ZNK7crpropa7Variant14bad_conversion4whatEv0
_ZN7crpropa7VariantC2ERKSt6vectorIS0_SaIS0_EE1
_ZNK7crpropa7VariantcvNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEv1
_ZN7crpropa7VariantC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1130
_ZN7crpropa7VariantaSERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1136
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Variant.h.func.html b/doc/coverageReport/include/crpropa/Variant.h.func.html deleted file mode 100644 index 070430d10..000000000 --- a/doc/coverageReport/include/crpropa/Variant.h.func.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Variant.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Variant.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:133537.1 %
Date:2024-04-08 14:58:22Functions:41625.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10safeDeleteINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEEvRPT_0
_ZN7crpropa10safeDeleteISt6vectorINS_7VariantESaIS2_EEEEvRPT_0
_ZN7crpropa7Variant14bad_conversionC2ENS0_4TypeES2_0
_ZN7crpropa7Variant14bad_conversionD0Ev0
_ZN7crpropa7Variant14bad_conversionD2Ev0
_ZN7crpropa7VariantC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1130
_ZN7crpropa7VariantC2ERKSt6vectorIS0_SaIS0_EE1
_ZN7crpropa7VariantaSERKNS_7Vector3ISt7complexIdEEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IdEE0
_ZN7crpropa7VariantaSERKNS_7Vector3IfEE0
_ZN7crpropa7VariantaSERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1136
_ZN7crpropa7VariantaSERKSt6vectorIS0_SaIS0_EE0
_ZN7crpropa7VariantaSERKSt7complexIdE0
_ZN7crpropa7VariantaSERKSt7complexIfE0
_ZNK7crpropa7Variant14bad_conversion4whatEv0
_ZNK7crpropa7VariantcvNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Variant.h.gcov.html b/doc/coverageReport/include/crpropa/Variant.h.gcov.html deleted file mode 100644 index a97907206..000000000 --- a/doc/coverageReport/include/crpropa/Variant.h.gcov.html +++ /dev/null @@ -1,410 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Variant.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Variant.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:133537.1 %
Date:2024-04-08 14:58:22Functions:41625.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : //-------------------------------------------------------------
-       2             : // Based on Variant.hh of the Physics eXtension Library (PXL) -
-       3             : // http://vispa.physik.rwth-aachen.de/                        -
-       4             : // Licensed under a LGPL-2 or later license                   -
-       5             : //-------------------------------------------------------------
-       6             : 
-       7             : #ifndef CRPROPA_VARIANT_H
-       8             : #define CRPROPA_VARIANT_H
-       9             : 
-      10             : #include <complex>
-      11             : #include <cstdint>
-      12             : #include <cstdlib>
-      13             : #include <cstring>
-      14             : #include <iostream>
-      15             : #include <limits>
-      16             : #include <string>
-      17             : #include <sstream>
-      18             : #include <stdexcept>
-      19             : #include <typeinfo>
-      20             : 
-      21             : #include "crpropa/Vector3.h"
-      22             : 
-      23             : 
-      24             : 
-      25             : // defines copy constructor X(const X&), isX(), asX(), fromX(), toX(), op(), op=, op==, op!=
-      26             : #define VARIANT_ADD_TYPE_DECL_POD(NAME, TYPE, VALUE, FIELD) \
-      27             :         Variant(const VALUE& v) { \
-      28             :                 data._t_##FIELD = v; \
-      29             :                 type = TYPE;  \
-      30             :         } \
-      31             :         bool is##NAME() const { \
-      32             :                 return type == TYPE; \
-      33             :         } \
-      34             :         VALUE& as##NAME() { \
-      35             :                 check(TYPE); \
-      36             :                 return data._t_##FIELD; \
-      37             :         } \
-      38             :         const VALUE& as##NAME() const { \
-      39             :                 check(TYPE); \
-      40             :                 return data._t_##FIELD; \
-      41             :         } \
-      42             :         static Variant from##NAME(const VALUE& v) { \
-      43             :                 return Variant(v); \
-      44             :         } \
-      45             :         VALUE to##NAME() const; \
-      46             :         operator VALUE() const { \
-      47             :                 return to##NAME(); \
-      48             :         } \
-      49             :         Variant& operator=(const VALUE& v) { \
-      50             :                 clear(); \
-      51             :                 type = TYPE; \
-      52             :                 data._t_##FIELD = v; \
-      53             :                 return *this; \
-      54             :         } \
-      55             :         bool operator==(const VALUE& v) const { \
-      56             :                 check(TYPE); \
-      57             :                 return data._t_##FIELD == v; \
-      58             :         } \
-      59             :         bool operator!=(const VALUE& v) const { \
-      60             :                 check(TYPE); \
-      61             :                 return data._t_##FIELD != v; \
-      62             :         } \
-      63             : 
-      64             : // defines isX(), asX(), fromX()
-      65             : #define VARIANT_ADD_TYPE_DECL_PTR_BASE(NAME, TYPE, VALUE, FIELD) \
-      66             :         bool is##NAME() const { \
-      67             :                 return type == TYPE; \
-      68             :         } \
-      69             :         VALUE& as##NAME() { \
-      70             :                 check(TYPE); \
-      71             :                 return *data._t_##FIELD; \
-      72             :         } \
-      73             :         const VALUE& as##NAME() const { \
-      74             :                 check(TYPE); \
-      75             :                 return *data._t_##FIELD; \
-      76             :         } \
-      77             :         static Variant from##NAME(const VALUE& v) { \
-      78             :                 return Variant(v); \
-      79             :         } \
-      80             : 
-      81             : // defines isX(), asX(), fromX(), and copy constructor X(const X&), op=, op==, op!=
-      82             : #define VARIANT_ADD_TYPE_DECL_PTR(NAME, TYPE, VALUE, FIELD) \
-      83             :         VARIANT_ADD_TYPE_DECL_PTR_BASE(NAME, TYPE, VALUE, FIELD) \
-      84             :         Variant(const VALUE& v) { \
-      85             :                 data._t_##FIELD = new VALUE(v); \
-      86             :                 type = TYPE; \
-      87             :         } \
-      88             :         Variant& operator=(const VALUE& v) { \
-      89             :                 if (type != TYPE) { \
-      90             :                         clear(); \
-      91             :                         data._t_##FIELD = new VALUE();\
-      92             :                 } \
-      93             :                 type = TYPE; \
-      94             :                 (*data._t_##FIELD) = v; \
-      95             :                 return *this; \
-      96             :         } \
-      97             :         bool operator==(const VALUE& v) const { \
-      98             :                 check(TYPE); \
-      99             :                 return *data._t_##FIELD == v; \
-     100             :         } \
-     101             :         bool operator!=(const VALUE& v) const { \
-     102             :                 return !(*this == v); \
-     103             :         } \
-     104             : 
-     105             : #define VARIANT_ADD_ITER_DECL_PTR(NAME, TYPE, FIELD) \
-     106             :         typedef FIELD##_t::iterator FIELD##_iterator; \
-     107             :         typedef FIELD##_t::const_iterator FIELD##_const_iterator; \
-     108             :         inline FIELD##_iterator begin##NAME() { \
-     109             :                 check(TYPE); \
-     110             :                 return data._t_##FIELD->begin(); \
-     111             :         } \
-     112             :         inline FIELD##_iterator end##NAME() { \
-     113             :                 check(TYPE); \
-     114             :                 return data._t_##FIELD->end(); \
-     115             :         } \
-     116             :         inline FIELD##_const_iterator begin##NAME() const { \
-     117             :                 check(TYPE); \
-     118             :                 return data._t_##FIELD->begin(); \
-     119             :         } \
-     120             :         inline FIELD##_const_iterator end##NAME() const { \
-     121             :                 check(TYPE); \
-     122             :                 return data._t_##FIELD->end(); \
-     123             :         }                                                                                
-     124             : 
-     125             : 
-     126             : 
-     127             : namespace crpropa {
-     128             : 
-     129             : /**
-     130             :  @class Variant
-     131             :  @brief storage container for data types as e.g. int, float, string, etc.
-     132             : 
-     133             :  Allows storage of multiple data types in one base class. Used to construct a map of `arbitrary' data types.
-     134             :  Note that most default C++ types allow default conversions from `Variant` to the corresponding type.
-     135             :  Types that require an explicit call via `toTargetType()` are: complex (float and double), Vector3, and vector<Variant>.
-     136             :  */
-     137             : class Variant {
-     138             : public:
-     139             :         enum Type {
-     140             :                 TYPE_NONE = 0,
-     141             :                 TYPE_BOOL,
-     142             :                 TYPE_CHAR,
-     143             :                 TYPE_UCHAR,
-     144             :                 TYPE_INT16,
-     145             :                 TYPE_UINT16,
-     146             :                 TYPE_INT32,
-     147             :                 TYPE_UINT32,
-     148             :                 TYPE_INT64,
-     149             :                 TYPE_UINT64,
-     150             :                 TYPE_FLOAT,
-     151             :                 TYPE_DOUBLE,
-     152             :                 TYPE_LONGDOUBLE,
-     153             :                 TYPE_COMPLEXF,
-     154             :                 TYPE_COMPLEXD,
-     155             :                 TYPE_STRING,
-     156             :                 TYPE_VECTOR3F,
-     157             :                 TYPE_VECTOR3D,
-     158             :                 TYPE_VECTOR3C,
-     159             :                 TYPE_VECTOR
-     160             :         };
-     161             : 
-     162             :         class bad_conversion: public std::exception {
-     163             :                 protected:
-     164             :                         std::string msg;
-     165             :                 public:
-     166           0 :                         const char* what() const throw () {
-     167           0 :                                 return msg.c_str();
-     168             :                         }
-     169             : 
-     170           0 :                         bad_conversion(Type f, Type t) {
-     171             :                                 msg = "Variant: bad conversion from '";
-     172           0 :                                 msg += Variant::getTypeName(f);
-     173             :                                 msg += "' to '";
-     174           0 :                                 msg += Variant::getTypeName(t);
-     175             :                                 msg += "'";
-     176           0 :                         }
-     177             : 
-     178           0 :                         ~bad_conversion() throw () {
-     179           0 :                         }
-     180             :         };
-     181             : 
-     182             :         typedef std::complex<float> complex_f;
-     183             :         typedef std::complex<double> complex_d;
-     184             :         typedef Vector3<std::complex<double>> Vector3c;
-     185             :         typedef std::vector<Variant> vector_t;
-     186             : 
-     187             : protected:
-     188             :         Type type;
-     189             : 
-     190             :         union {
-     191             :                 bool _t_bool;
-     192             :                 char _t_char;
-     193             :                 unsigned char _t_uchar;
-     194             :                 int16_t _t_int16;
-     195             :                 uint16_t _t_uint16;
-     196             :                 int32_t _t_int32;
-     197             :                 uint32_t _t_uint32;
-     198             :                 int64_t _t_int64;
-     199             :                 uint64_t _t_uint64;
-     200             :                 float _t_float;
-     201             :                 double _t_double;
-     202             :                 long double _t_ldouble;
-     203             :                 complex_f* _t_complex_f;
-     204             :                 complex_d* _t_complex_d;
-     205             :                 std::string* _t_string;
-     206             :                 Vector3f* _t_vector3f;
-     207             :                 Vector3d* _t_vector3d;
-     208             :                 Vector3c* _t_vector3c;
-     209             :                 vector_t* _t_vector;
-     210             :         } data;
-     211             : 
-     212             : 
-     213             : public:
-     214             :         Variant();
-     215             :         Variant(Type t);
-     216             :         Variant(const Variant& v);
-     217             :         Variant(const char* s);
-     218             :         ~Variant();
-     219             :         inline Type getType() const {
-     220           2 :                 return type;
-     221             :         }
-     222             :         const char* getTypeName() const;
-     223             :         static const char* getTypeName(Type t);
-     224             :         const std::type_info& getTypeInfo() const;
-     225             :         static Type toType(const std::string& name);                
-     226             :         std::string toString(const std::string& delimiter = "\t") const;
-     227             :         std::complex<float> toComplexFloat() const;
-     228             :         std::complex<double> toComplexDouble() const;
-     229             :         Vector3f toVector3f() const;
-     230             :         Vector3d toVector3d() const;
-     231             :         Vector3c toVector3c() const;
-     232             :         vector_t toVector() const;
-     233             :         static Variant fromString(const std::string& str, Type type);
-     234             :         void clear(Type t = TYPE_NONE);
-     235             :         bool isValid() const;
-     236             :         size_t size() const;
-     237             :         size_t getSizeOf() const;
-     238             :         size_t getSize() const;
-     239             :         void resize(size_t i);
-     240             :         size_t copyToBuffer(void* buffer);
-     241           1 :         operator std::string() const {
-     242           2 :                 return toString();
-     243             :         }
-     244             :         Variant& operator=(const Variant& v);
-     245             :         bool operator==(const Variant& v) const;
-     246             :         bool operator!=(const Variant& v) const;
-     247             :         bool operator!=(const char* a) const;
-     248             :         Variant& operator[](size_t i);
-     249             :         inline Variant& operator[](int i) {
-     250             :                 return operator[]((size_t) i);
-     251             :         }
-     252             :         const Variant& operator[](size_t i) const;
-     253             :         const Variant& operator[](int i) const {
-     254             :                 return operator[]((size_t) i);
-     255             :         }
-     256             :         operator vector_t&();
-     257             :         operator const vector_t&() const;
-     258             : 
-     259             : 
-     260             :         template<class T>
-     261             :         T to() const {
-     262             :                 throw bad_conversion(type, TYPE_NONE);
-     263             :         }
-     264             : 
-     265             :         // automatically-generated functions    
-     266           6 :         VARIANT_ADD_TYPE_DECL_POD(Bool, TYPE_BOOL, bool, bool)
-     267           0 :         VARIANT_ADD_TYPE_DECL_POD(Char, TYPE_CHAR, char, char)
-     268           0 :         VARIANT_ADD_TYPE_DECL_POD(UChar, TYPE_UCHAR, unsigned char, uchar)
-     269           0 :         VARIANT_ADD_TYPE_DECL_POD(Int16, TYPE_INT16, int16_t, int16)
-     270           0 :         VARIANT_ADD_TYPE_DECL_POD(UInt16, TYPE_UINT16, uint16_t, uint16)
-     271          12 :         VARIANT_ADD_TYPE_DECL_POD(Int32, TYPE_INT32, int32_t, int32)
-     272           0 :         VARIANT_ADD_TYPE_DECL_POD(UInt32, TYPE_UINT32, uint32_t, uint32)
-     273           6 :         VARIANT_ADD_TYPE_DECL_POD(Int64, TYPE_INT64, int64_t, int64)
-     274          16 :         VARIANT_ADD_TYPE_DECL_POD(UInt64, TYPE_UINT64, uint64_t, uint64)
-     275           0 :         VARIANT_ADD_TYPE_DECL_POD(Float, TYPE_FLOAT, float, float)
-     276          34 :         VARIANT_ADD_TYPE_DECL_POD(Double, TYPE_DOUBLE, double, double)
-     277           0 :         VARIANT_ADD_TYPE_DECL_POD(LongDouble, TYPE_LONGDOUBLE, long double, ldouble)
-     278           0 :         VARIANT_ADD_TYPE_DECL_PTR(ComplexFloat, TYPE_COMPLEXF, std::complex<float>, complex_f)
-     279           1 :         VARIANT_ADD_TYPE_DECL_PTR(ComplexDouble, TYPE_COMPLEXD, std::complex<double>, complex_d)
-     280        3396 :         VARIANT_ADD_TYPE_DECL_PTR(String, TYPE_STRING, std::string, string)
-     281           0 :         VARIANT_ADD_TYPE_DECL_PTR(Vector3f, TYPE_VECTOR3F, Vector3f, vector3f)
-     282           1 :         VARIANT_ADD_TYPE_DECL_PTR(Vector3d, TYPE_VECTOR3D, Vector3d, vector3d)
-     283           1 :         VARIANT_ADD_TYPE_DECL_PTR(Vector3c, TYPE_VECTOR3C, Vector3c, vector3c)
-     284           2 :         VARIANT_ADD_TYPE_DECL_PTR(Vector, TYPE_VECTOR, vector_t, vector)
-     285             :         VARIANT_ADD_ITER_DECL_PTR(Vector, TYPE_VECTOR, vector)
-     286             :                 
-     287             : private:
-     288             :         void copy(const Variant& v);
-     289             :         void check(const Type t) const;
-     290             :         void check(const Type t);
-     291             : };
-     292             : 
-     293             : #define VARIANT_TO_DECL(NAME, VALUE) \
-     294             :         template<> inline VALUE Variant::to<VALUE>() const { \
-     295             :                 return to##NAME(); \
-     296             :         } \
-     297             : 
-     298             : // declare type conversion functions
-     299             : // not implemented for Vector3 and complex_*
-     300             : VARIANT_TO_DECL(Bool, bool)
-     301             : VARIANT_TO_DECL(Char, char)
-     302             : VARIANT_TO_DECL(UChar, unsigned char)
-     303             : VARIANT_TO_DECL(Int16, int16_t)
-     304             : VARIANT_TO_DECL(UInt16, uint16_t)
-     305             : VARIANT_TO_DECL(Int32, int32_t)
-     306             : VARIANT_TO_DECL(UInt32, uint32_t)
-     307             : VARIANT_TO_DECL(Int64, int64_t)
-     308             : VARIANT_TO_DECL(UInt64, uint64_t)
-     309             : VARIANT_TO_DECL(Float, float)
-     310             : VARIANT_TO_DECL(Double, double)
-     311             : VARIANT_TO_DECL(LongDouble, long double)
-     312             : VARIANT_TO_DECL(String, std::string)
-     313             : VARIANT_TO_DECL(Vector, Variant::vector_t)
-     314             : 
-     315             : std::ostream& operator <<(std::ostream& os, const Variant &v);
-     316             : 
-     317             : 
-     318             : /**
-     319             :  Taken from PXL
-     320             :  https://git.rwth-aachen.de/3pia/pxl/pxl/-/blob/master/core/include/pxl/core/Functions.hh
-     321             :  */
-     322             : template <class T> 
-     323           0 : inline void safeDelete(T*& p) {
-     324           0 :         if (p) {
-     325           0 :                 delete p;
-     326           0 :                 p = 0;
-     327             :         }
-     328           0 : }
-     329             : 
-     330             : 
-     331             : 
-     332             : } // namespace crpropa 
-     333             : 
-     334             : #endif // CRPROPA_VARIANT
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html b/doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html deleted file mode 100644 index b44071763..000000000 --- a/doc/coverageReport/include/crpropa/Vector3.h.func-sort-c.html +++ /dev/null @@ -1,236 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Vector3.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Vector3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9915165.6 %
Date:2024-04-08 14:58:22Functions:164139.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Vector3IdE4setREd0
_ZN7crpropa7Vector3IdErMERKS1_0
_ZN7crpropa7Vector3IfE12setRThetaPhiEfff0
_ZN7crpropa7Vector3IfE4setREf0
_ZN7crpropa7Vector3IfErMERKS1_0
_ZN7crpropa7Vector3IfErMERKf0
_ZN7crpropalsISt7complexIdEEERSoS3_RKNS_7Vector3IT_EE0
_ZNK7crpropa7Vector3IdE4ceilEv0
_ZNK7crpropa7Vector3IdE4clipEdd0
_ZNK7crpropa7Vector3IdErmERKS1_0
_ZNK7crpropa7Vector3IdErmERKd0
_ZNK7crpropa7Vector3IfE10getRotatedERKS1_f0
_ZNK7crpropa7Vector3IfE13getDistanceToERKS1_0
_ZNK7crpropa7Vector3IfE13getParallelToERKS1_0
_ZNK7crpropa7Vector3IfE13getUnitVectorEv0
_ZNK7crpropa7Vector3IfE16getUnitVectorPhiEv0
_ZNK7crpropa7Vector3IfE18getPerpendicularToERKS1_0
_ZNK7crpropa7Vector3IfE18getUnitVectorThetaEv0
_ZNK7crpropa7Vector3IfE4ceilEv0
_ZNK7crpropa7Vector3IfE4clipEff0
_ZNK7crpropa7Vector3IfE5floorEv0
_ZNK7crpropa7Vector3IfE6getPhiEv0
_ZNK7crpropa7Vector3IfE8getThetaEv0
_ZNK7crpropa7Vector3IfErmERKS1_0
_ZNK7crpropa7Vector3IfErmERKf0
_ZN7crpropa7Vector3IdErMERKd1
_ZNK7crpropa7Vector3IdE18getPerpendicularToERKS1_1
_ZNK7crpropa7Vector3IdE18getUnitVectorThetaEv1
_ZNK7crpropa7Vector3IdE13getParallelToERKS1_2
_ZN7crpropa7Vector3IdE12setRThetaPhiEddd3
_ZNK7crpropa7Vector3IdE16getUnitVectorPhiEv4
_ZNK7crpropa7Vector3IdE5floorEv6
_ZNK7crpropa7Vector3IdE10getAngleToERKS1_8
_ZNK7crpropa7Vector3IdE8getThetaEv8
_ZN7crpropalsIdEERSoS1_RKNS_7Vector3IT_EE11
_ZNK7crpropa7Vector3IdE6getPhiEv19
_ZN7crpropalsIfEERSoS1_RKNS_7Vector3IT_EE27
_ZNK7crpropa7Vector3IdE13getDistanceToERKS1_110
_ZNK7crpropa7Vector3IdE10getRotatedERKS1_d481006
_ZNK7crpropa7Vector3IfE10getAngleToERKS1_691017
_ZNK7crpropa7Vector3IdE13getUnitVectorEv7201361
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Vector3.h.func.html b/doc/coverageReport/include/crpropa/Vector3.h.func.html deleted file mode 100644 index 8b3511c68..000000000 --- a/doc/coverageReport/include/crpropa/Vector3.h.func.html +++ /dev/null @@ -1,236 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Vector3.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Vector3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9915165.6 %
Date:2024-04-08 14:58:22Functions:164139.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Vector3IdE12setRThetaPhiEddd3
_ZN7crpropa7Vector3IdE4setREd0
_ZN7crpropa7Vector3IdErMERKS1_0
_ZN7crpropa7Vector3IdErMERKd1
_ZN7crpropa7Vector3IfE12setRThetaPhiEfff0
_ZN7crpropa7Vector3IfE4setREf0
_ZN7crpropa7Vector3IfErMERKS1_0
_ZN7crpropa7Vector3IfErMERKf0
_ZN7crpropalsISt7complexIdEEERSoS3_RKNS_7Vector3IT_EE0
_ZN7crpropalsIdEERSoS1_RKNS_7Vector3IT_EE11
_ZN7crpropalsIfEERSoS1_RKNS_7Vector3IT_EE27
_ZNK7crpropa7Vector3IdE10getAngleToERKS1_8
_ZNK7crpropa7Vector3IdE10getRotatedERKS1_d481006
_ZNK7crpropa7Vector3IdE13getDistanceToERKS1_110
_ZNK7crpropa7Vector3IdE13getParallelToERKS1_2
_ZNK7crpropa7Vector3IdE13getUnitVectorEv7201361
_ZNK7crpropa7Vector3IdE16getUnitVectorPhiEv4
_ZNK7crpropa7Vector3IdE18getPerpendicularToERKS1_1
_ZNK7crpropa7Vector3IdE18getUnitVectorThetaEv1
_ZNK7crpropa7Vector3IdE4ceilEv0
_ZNK7crpropa7Vector3IdE4clipEdd0
_ZNK7crpropa7Vector3IdE5floorEv6
_ZNK7crpropa7Vector3IdE6getPhiEv19
_ZNK7crpropa7Vector3IdE8getThetaEv8
_ZNK7crpropa7Vector3IdErmERKS1_0
_ZNK7crpropa7Vector3IdErmERKd0
_ZNK7crpropa7Vector3IfE10getAngleToERKS1_691017
_ZNK7crpropa7Vector3IfE10getRotatedERKS1_f0
_ZNK7crpropa7Vector3IfE13getDistanceToERKS1_0
_ZNK7crpropa7Vector3IfE13getParallelToERKS1_0
_ZNK7crpropa7Vector3IfE13getUnitVectorEv0
_ZNK7crpropa7Vector3IfE16getUnitVectorPhiEv0
_ZNK7crpropa7Vector3IfE18getPerpendicularToERKS1_0
_ZNK7crpropa7Vector3IfE18getUnitVectorThetaEv0
_ZNK7crpropa7Vector3IfE4ceilEv0
_ZNK7crpropa7Vector3IfE4clipEff0
_ZNK7crpropa7Vector3IfE5floorEv0
_ZNK7crpropa7Vector3IfE6getPhiEv0
_ZNK7crpropa7Vector3IfE8getThetaEv0
_ZNK7crpropa7Vector3IfErmERKS1_0
_ZNK7crpropa7Vector3IfErmERKf0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/Vector3.h.gcov.html b/doc/coverageReport/include/crpropa/Vector3.h.gcov.html deleted file mode 100644 index f1fbcd9c0..000000000 --- a/doc/coverageReport/include/crpropa/Vector3.h.gcov.html +++ /dev/null @@ -1,516 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/Vector3.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa - Vector3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9915165.6 %
Date:2024-04-08 14:58:22Functions:164139.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_VECTOR3_H
-       2             : #define CRPROPA_VECTOR3_H
-       3             : 
-       4             : #include <iostream>
-       5             : #include <cmath>
-       6             : #include <vector>
-       7             : #include <limits>
-       8             : #include <algorithm>
-       9             : 
-      10             : namespace crpropa {
-      11             : 
-      12             : /**
-      13             :  * \addtogroup Core
-      14             :  * @{
-      15             :  */
-      16             : 
-      17             : /**
-      18             :  @class Vector3
-      19             :  @brief Template class for 3-vectors of type float, double, ...
-      20             : 
-      21             :  Allows accessing and changing the elements x, y, z directly or  through the
-      22             :  corresponding get and set methods.
-      23             : 
-      24             :  Angle definitions are
-      25             :  phi [-pi, pi]: azimuthal angle in the x-y plane, 0 pointing in x-direction
-      26             :  theta [0, pi]: zenith angle towards the z axis, 0 pointing in z-direction
-      27             :  */
-      28             : template<typename T>
-      29             : class Vector3 {
-      30             : public:
-      31             :         union {
-      32             :                 struct
-      33             :                 {
-      34             :                         T x;
-      35             :                         T y;
-      36             :                         T z;
-      37             :                 };
-      38             :                 T data[3];
-      39             :         };
-      40             : 
-      41     3187045 :         Vector3() : data{0., 0., 0.} {
-      42             :         }
-      43             : 
-      44             :         // avoid creation of default non-conversion constructor
-      45    20387451 :         Vector3(const Vector3 &v) : data{v.data[0], v.data[1], v.data[2]} {
-      46           0 :         }
-      47             : 
-      48             :         // Provides implicit conversion
-      49             :         template<typename U>
-      50           0 :         Vector3(const Vector3<U> &v) {
-      51          14 :                 data[0] = v.x;
-      52           4 :                 data[1] = v.y;
-      53           4 :                 data[2] = v.z;
-      54           0 :         }
-      55             : 
-      56             :         ~Vector3()
-      57             :         {
-      58    26216757 :         }
-      59             : 
-      60           0 :         explicit Vector3(const double *v) {
-      61           0 :                 data[0] = v[0];
-      62           0 :                 data[1] = v[1];
-      63           0 :                 data[2] = v[2];
-      64             :         }
-      65             : 
-      66           0 :         explicit Vector3(const float *v) {
-      67           0 :                 data[0] = v[0];
-      68           0 :                 data[1] = v[1];
-      69           0 :                 data[2] = v[2];
-      70             :         }
-      71             : 
-      72    12617888 :         explicit Vector3(const T &X, const T &Y, const T &Z) : data{X, Y, Z} {
-      73             :         }
-      74             : 
-      75    18504508 :         explicit Vector3(T t) : data{t, t, t} {
-      76           1 :         }
-      77             : 
-      78             :         void setX(const T X) {
-      79           1 :                 x = X;
-      80             :         }
-      81             : 
-      82             :         void setY(const T Y) {
-      83           0 :                 y = Y;
-      84             :         }
-      85             : 
-      86             :         void setZ(const T Z) {
-      87           0 :                 z = Z;
-      88             :         }
-      89             : 
-      90             :         void setXYZ(const T X, const T Y, const T Z) {
-      91     1351680 :                 x = X;
-      92     1351680 :                 y = Y;
-      93     1351680 :                 z = Z;
-      94             :         }
-      95             : 
-      96           0 :         void setR(const T r) {
-      97           0 :                 *this *= r / getR();
-      98           0 :         }
-      99             : 
-     100           3 :         void setRThetaPhi(const T r, const T theta, const T phi) {
-     101           3 :                 x = r * sin(theta) * cos(phi);
-     102           3 :                 y = r * sin(theta) * sin(phi);
-     103           3 :                 z = r * cos(theta);
-     104           3 :         }
-     105             : 
-     106             :         T getX() const {
-     107      370007 :                 return x;
-     108             :         }
-     109             : 
-     110             :         T getY() const {
-     111      370006 :                 return y;
-     112             :         }
-     113             : 
-     114             :         T getZ() const {
-     115       40006 :                 return z;
-     116             :         }
-     117             : 
-     118             :         // magnitude (2-norm) of the vector
-     119             :         T getR() const {
-     120    25099477 :                 return std::sqrt(x * x + y * y + z * z);
-     121             :         }
-     122             : 
-     123             :         // square of magnitude of the vector
-     124             :         T getR2() const {
-     125     2883584 :                 return x * x + y * y + z * z;
-     126             :         }
-     127             : 
-     128             :         // return the azimuth angle
-     129          19 :         T getPhi() const {
-     130             :                 T eps = std::numeric_limits < T > ::min();
-     131          19 :                 if ((fabs(x) < eps) && (fabs(y) < eps))
-     132             :                         return 0.0;
-     133             :                 else
-     134          18 :                         return std::atan2(y, x);
-     135             :         }
-     136             : 
-     137             :         // return the zenith angle
-     138           8 :         T getTheta() const {
-     139             :                 T eps = std::numeric_limits < T > ::min();
-     140           8 :                 if ((fabs(x) < eps) && (fabs(y) < eps) && (fabs(z) < eps))
-     141             :                         return 0.0;
-     142             :                 else
-     143           8 :                         return atan2((T) sqrt(x * x + y * y), z);
-     144             :         }
-     145             : 
-     146             :         // return the unit-vector e_r
-     147     7201361 :         Vector3<T> getUnitVector() const {
-     148     7201361 :                 return *this / getR();
-     149             :         }
-     150             : 
-     151             :         // return the unit-vector e_theta
-     152           1 :         Vector3<T> getUnitVectorTheta() const {
-     153           1 :                 T theta = getTheta();
-     154           1 :                 T phi = getPhi();
-     155           1 :                 return Vector3<T>(cos(theta) * cos(phi), cos(theta) * sin(phi),
-     156           1 :                                 -sin(theta));
-     157             :         }
-     158             : 
-     159             :         // return the unit-vector e_phi
-     160           4 :         Vector3<T> getUnitVectorPhi() const {
-     161           4 :                 return Vector3<T>(-sin(getPhi()), cos(getPhi()), 0);
-     162             :         }
-     163             : 
-     164             :         // return the angle [0, pi] between the vectors
-     165      691025 :         T getAngleTo(const Vector3<T> &v) const {
-     166      691025 :                 T cosdistance = dot(v) / v.getR() / getR();
-     167             :                 // In some directions cosdistance is > 1 on some compilers
-     168             :                 // This ensures that the correct result is returned
-     169      691025 :                 if (cosdistance >= 1.)
-     170             :                         return 0;
-     171      690880 :                 else if (cosdistance <= -1.)
-     172             :                         return M_PI;
-     173             :                 else
-     174      690880 :                         return acos(cosdistance);
-     175             :         }
-     176             : 
-     177             :         // return true if the angle between the vectors is smaller than a threshold
-     178             :         bool isParallelTo(const Vector3<T> &v, T maxAngle) const {
-     179      691017 :                 return getAngleTo(v) < maxAngle;
-     180             :         }
-     181             : 
-     182             :         // linear distance to a given vector
-     183         110 :         T getDistanceTo(const Vector3<T> &point) const {
-     184             :                 Vector3<T> d = *this - point;
-     185         110 :                 return d.getR();
-     186             :         }
-     187             : 
-     188             :         // return the component parallel to a second vector
-     189             :         // 0 if the second vector has 0 magnitude
-     190           2 :         Vector3<T> getParallelTo(const Vector3<T> &v) const {
-     191             :                 T vmag = v.getR();
-     192           2 :                 if (vmag == std::numeric_limits < T > ::min())
-     193             :                         return Vector3<T>(0.);
-     194             :                 return v * dot(v) / vmag;
-     195             :         }
-     196             : 
-     197             :         // return the component perpendicular to a second vector
-     198             :         // 0 if the second vector has 0 magnitude
-     199           1 :         Vector3<T> getPerpendicularTo(const Vector3<T> &v) const {
-     200           1 :                 if (v.getR() == std::numeric_limits < T > ::min())
-     201             :                         return Vector3<T>(0.);
-     202           1 :                 return (*this) - getParallelTo(v);
-     203             :         }
-     204             : 
-     205             :         // rotate the vector around a given axis by a given angle
-     206      481006 :         Vector3<T> getRotated(const Vector3<T> &axis, T angle) const {
-     207             :                 Vector3<T> u = axis;
-     208      481006 :                 if (u.getR() != 0.)
-     209             :                         u = u / u.getR();
-     210      481006 :                 T c = cos(angle);
-     211      481006 :                 T s = sin(angle);
-     212      481006 :                 Vector3<T> Rx(c + u.x * u.x * (1 - c), u.x * u.y * (1 - c) - u.z * s,
-     213      481006 :                                 u.x * u.z * (1 - c) + u.y * s);
-     214      481006 :                 Vector3<T> Ry(u.y * u.x * (1 - c) + u.z * s, c + u.y * u.y * (1 - c),
-     215      481006 :                                 u.y * u.z * (1 - c) - u.x * s);
-     216      481006 :                 Vector3<T> Rz(u.z * u.x * (1 - c) - u.y * s,
-     217      481006 :                                 u.z * u.y * (1 - c) + u.x * s, c + u.z * u.z * (1 - c));
-     218      481006 :                 return Vector3<T>(dot(Rx), dot(Ry), dot(Rz));
-     219             :         }
-     220             : 
-     221             :         // return vector with values limited to the range [lower, upper]
-     222           0 :         Vector3<T> clip(T lower, T upper) const {
-     223             :                 Vector3<T> out;
-     224           0 :                 out.x = std::max(lower, std::min(x, upper));
-     225           0 :                 out.y = std::max(lower, std::min(y, upper));
-     226           0 :                 out.z = std::max(lower, std::min(z, upper));
-     227           0 :                 return out;
-     228             :         }
-     229             : 
-     230             :         // return vector with absolute values
-     231             :         Vector3<T> abs() const {
-     232           0 :                 return Vector3<T>(std::abs(x), std::abs(y), std::abs(z));
-     233             :         }
-     234             : 
-     235             :         // return vector with floored values
-     236           6 :         Vector3<T> floor() const {
-     237           6 :                 return Vector3<T>(std::floor(x), std::floor(y), std::floor(z));
-     238             :         }
-     239             : 
-     240             :         // return vector with ceiled values
-     241           0 :         Vector3<T> ceil() const {
-     242           0 :                 return Vector3<T>(std::ceil(x), std::ceil(y), std::ceil(z));
-     243             :         }
-     244             : 
-     245             :         // minimum element
-     246             :         T min() const {
-     247           4 :                 return std::min(x, std::min(y, z));
-     248             :         }
-     249             : 
-     250             :         // maximum element
-     251             :         T max() const {
-     252           4 :                 return std::max(x, std::max(y, z));
-     253             :         }
-     254             : 
-     255             :         // dot product
-     256             :         T dot(const Vector3<T> &v) const {
-     257      692583 :                 return x * v.x + y * v.y + z * v.z;
-     258             :         }
-     259             : 
-     260             :         // cross product
-     261             :         Vector3<T> cross(const Vector3<T> &v) const {
-     262     2132230 :                 return Vector3<T>(y * v.z - v.y * z, z * v.x - v.z * x,
-     263     1652230 :                                 x * v.y - v.x * y);
-     264             :         }
-     265             : 
-     266             :         // returns true if all elements of the two vectors are equal
-     267             :         bool operator ==(const Vector3<T> &v) const {
-     268          33 :                 if (x != v.x)
-     269             :                         return false;
-     270          33 :                 if (y != v.y)
-     271             :                         return false;
-     272          33 :                 if (z != v.z)
-     273           0 :                         return false;
-     274             :                 return true;
-     275             :         }
-     276             : 
-     277             :         Vector3<T> operator +(const Vector3<T> &v) const {
-     278     4339186 :                 return Vector3(x + v.x, y + v.y, z + v.z);
-     279             :         }
-     280             : 
-     281             :         Vector3<T> operator +(const T &f) const {
-     282           0 :                 return Vector3(x + f, y + f, z + f);
-     283             :         }
-     284             : 
-     285             :         Vector3<T> operator -(const Vector3<T> &v) const {
-     286     7533903 :                 return Vector3(x - v.x, y - v.y, z - v.z);
-     287             :         }
-     288             : 
-     289             :         Vector3<T> operator -(const T &f) const {
-     290           0 :                 return Vector3(x - f, y - f, z - f);
-     291             :         }
-     292             : 
-     293             :         // element-wise multiplication
-     294             :         Vector3<T> operator *(const Vector3<T> &v) const {
-     295          20 :                 return Vector3(x * v.x, y * v.y, z * v.z);
-     296             :         }
-     297             : 
-     298             :         Vector3<T> operator *(T v) const {
-     299     1191262 :                 return Vector3(data[0] * v, data[1] * v, data[2] * v);
-     300             :         }
-     301             : 
-     302             :         // element-wise division
-     303             :         Vector3<T> operator /(const Vector3<T> &v) const {
-     304      100097 :                 return Vector3(x / v.x, y / v.y, z / v.z);
-     305             :         }
-     306             : 
-     307             :         Vector3<T> operator /(const T &f) const {
-     308     6242639 :                 return Vector3(x / f, y / f, z / f);
-     309             :         }
-     310             : 
-     311             :         // element-wise modulo operation
-     312           0 :         Vector3<T> operator %(const Vector3<T> &v) const {
-     313           0 :                 return Vector3(fmod(x, v.x), fmod(y, v.y), fmod(z, v.z));
-     314             :         }
-     315             : 
-     316           0 :         Vector3<T> operator %(const T &f) const {
-     317           0 :                 return Vector3(fmod(x, f), fmod(y, f), fmod(z, f));
-     318             :         }
-     319             : 
-     320             :         Vector3<T> &operator -=(const Vector3<T> &v) {
-     321           0 :                 data[0] -= v.x;
-     322           0 :                 data[1] -= v.y;
-     323           0 :                 data[2] -= v.z;
-     324             :                 return *this;
-     325             :         }
-     326             : 
-     327             :         Vector3<T> &operator -=(const T &f) {
-     328           0 :                 data[0] -= f;
-     329           0 :                 data[1] -= f;
-     330           0 :                 data[2] -= f;
-     331             :                 return *this;
-     332             :         }
-     333             : 
-     334             :         Vector3<T> &operator +=(const Vector3<T> &v) {
-     335    20664839 :                 data[0] += v.x;
-     336    20664839 :                 data[1] += v.y;
-     337    20544720 :                 data[2] += v.z;
-     338             :                 return *this;
-     339             :         }
-     340             : 
-     341             :         Vector3<T> &operator +=(const T &f) {
-     342           0 :                 data[0] += f;
-     343           0 :                 data[1] += f;
-     344           0 :                 data[2] += f;
-     345             :                 return *this;
-     346             :         }
-     347             : 
-     348             :         // element-wise multiplication
-     349             :         Vector3<T> &operator *=(const Vector3<T> &v) {
-     350           0 :                 data[0] *= v.x;
-     351           0 :                 data[1] *= v.y;
-     352           0 :                 data[2] *= v.z;
-     353             :                 return *this;
-     354             :         }
-     355             : 
-     356             :         Vector3<T> &operator *=(const T &f) {
-     357     3312538 :                 data[0] *= f;
-     358     3312538 :                 data[1] *= f;
-     359     3312538 :                 data[2] *= f;
-     360             :                 return *this;
-     361             :         }
-     362             : 
-     363             :         // element-wise division
-     364             :         Vector3<T> &operator /=(const Vector3<T> &v) {
-     365           0 :                 data[0] /= v.x;
-     366           0 :                 data[1] /= v.y;
-     367           0 :                 data[2] /= v.z;
-     368             :                 return *this;
-     369             :         }
-     370             : 
-     371             :         Vector3<T> &operator /=(const T &f) {
-     372      691019 :                 data[0] /= f;
-     373      691019 :                 data[1] /= f;
-     374      691019 :                 data[2] /= f;
-     375             :                 return *this;
-     376             :         }
-     377             : 
-     378             :         // element-wise modulo operation
-     379           0 :         Vector3<T> &operator %=(const Vector3<T> &v) {
-     380           0 :                 data[0] = fmod(x, v.x);
-     381           0 :                 data[1] = fmod(y, v.y);
-     382           0 :                 data[2] = fmod(z, v.z);
-     383           0 :                 return *this;
-     384             :         }
-     385             : 
-     386           1 :         Vector3<T> &operator %=(const T &f) {
-     387           1 :                 data[0] = fmod(x, f);
-     388           1 :                 data[1] = fmod(y, f);
-     389           1 :                 data[2] = fmod(z, f);
-     390           1 :                 return *this;
-     391             :         }
-     392             : 
-     393             :         Vector3<T> &operator =(const Vector3<T> &v) {
-     394    64125712 :                 data[0] = v.x;
-     395    64125726 :                 data[1] = v.y;
-     396    63640105 :                 data[2] = v.z;
-     397           0 :                 return *this;
-     398             :         }
-     399             : 
-     400             :         //Vector3<T> &operator =(Vector3<T> &&v) noexcept {
-     401             :         //      data[0] = v.data[0];
-     402             :         //      data[1] = v.data[1];
-     403             :         //      data[2] = v.data[2];
-     404             :         //      return *this;
-     405             :         //}
-     406             : 
-     407             :         Vector3<T> &operator =(const T &f) {
-     408             :                 data[0] = f;
-     409             :                 data[1] = f;
-     410             :                 data[2] = f;
-     411             :                 return *this;
-     412             :         }
-     413             : };
-     414             : 
-     415             : #ifndef SWIG
-     416             : template<typename T>
-     417          38 : inline std::ostream &operator <<(std::ostream &out, const Vector3<T> &v) {
-     418         114 :         out << v.x << " " << v.y << " " << v.z;
-     419          38 :         return out;
-     420             : }
-     421             : 
-     422             : template<typename T>
-     423             : inline std::istream &operator >>(std::istream &in, Vector3<T> &v) {
-     424             :         in >> v.x >> v.y >> v.z;
-     425             :         return in;
-     426             : }
-     427             : #endif
-     428             : 
-     429             : template<typename T>
-     430             : inline Vector3<T> operator *(T f, const Vector3<T> &v) {
-     431     3628978 :         return Vector3<T>(v.x * f, v.y * f, v.z * f);
-     432             : }
-     433             : 
-     434             : typedef Vector3<double> Vector3d;
-     435             : typedef Vector3<float> Vector3f;
-     436             : 
-     437             : /** @}*/
-     438             : }  // namespace crpropa
-     439             : 
-     440             : #endif  // CRPROPA_VECTOR3_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html deleted file mode 100644 index 429d191a5..000000000 --- a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/advectionField/AdvectionField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/advectionField - AdvectionField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html deleted file mode 100644 index 74fd9621e..000000000 --- a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/advectionField/AdvectionField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/advectionField - AdvectionField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html b/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html deleted file mode 100644 index 4be5bf68f..000000000 --- a/doc/coverageReport/include/crpropa/advectionField/AdvectionField.h.gcov.html +++ /dev/null @@ -1,367 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/advectionField/AdvectionField.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/advectionField - AdvectionField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_ADVECTIONFIELD_H
-       2             : #define CRPROPA_ADVECTIONFIELD_H
-       3             : 
-       4             : 
-       5             : #include <string>
-       6             : #include <iostream>
-       7             : #include <cmath>
-       8             : #include <cstdlib>
-       9             : #include <sstream>
-      10             : 
-      11             : #include "crpropa/Vector3.h"
-      12             : #include "crpropa/Referenced.h"
-      13             : #include "crpropa/Units.h"
-      14             : 
-      15             : namespace crpropa {
-      16             : 
-      17             : /**
-      18             :  @class AdvectionField
-      19             :  @brief Abstract base class for advection fields. These are used to model 
-      20             :         the deterministic part of the Fokker-Planck equation. The getDivergence()
-      21             :         method is used to model the adibatic cooling/heating.
-      22             :  */
-      23             : class AdvectionField: public Referenced {
-      24             : public:
-      25             :         virtual ~AdvectionField() {
-      26             :         }
-      27             :         virtual Vector3d getField(const Vector3d &position) const = 0;
-      28             :         virtual double getDivergence(const Vector3d &position) const = 0;
-      29             : };
-      30             : 
-      31             : 
-      32             : /**
-      33             :  @class AdvectionFieldList
-      34             :  @brief Advection field decorator implementing a superposition of fields.
-      35             :  */
-      36           2 : class AdvectionFieldList: public AdvectionField {
-      37             :         std::vector<ref_ptr<AdvectionField> > fields;
-      38             : public:
-      39             :         void addField(ref_ptr<AdvectionField> field);
-      40             :         Vector3d getField(const Vector3d &position) const;
-      41             :         double getDivergence(const Vector3d &position) const;
-      42             : };
-      43             : 
-      44             : 
-      45             : /**
-      46             :  @class UniformAdvectionField
-      47             :  @brief Advection field with one velocity/advection-field vector.
-      48             :  */
-      49           1 : class UniformAdvectionField: public AdvectionField {
-      50             :         Vector3d value;
-      51             : public:
-      52             :         UniformAdvectionField(const Vector3d &value);
-      53             :         Vector3d getField(const Vector3d &position) const;
-      54             :         double getDivergence(const Vector3d &position) const;
-      55             : 
-      56             :         std::string getDescription() const;
-      57             : };
-      58             : 
-      59             : 
-      60             : /**
-      61             : @class ConstantSphericalAdvectionField
-      62             : @brief Spherical advection field with a constant wind speed
-      63             : */
-      64             : 
-      65           1 : class ConstantSphericalAdvectionField: public AdvectionField {
-      66             :         Vector3d origin; //origin of the advection sphere
-      67             :         double vWind; // wind velocity
-      68             : public:
-      69             :         /** Constructor
-      70             :          @param origin  Origin of the advection field
-      71             :          @param vWind   Constant wind velocity
-      72             : 
-      73             : */
-      74             : 
-      75             :         ConstantSphericalAdvectionField(const Vector3d origin, double vWind);
-      76             :         Vector3d getField(const Vector3d &position) const;
-      77             :         double getDivergence(const Vector3d &position) const;
-      78             : 
-      79             :         void setOrigin(const Vector3d origin);
-      80             :         void setVWind(double vMax);
-      81             : 
-      82             :         Vector3d getOrigin() const;
-      83             :         double getVWind() const;
-      84             : 
-      85             :         std::string getDescription() const;
-      86             : 
-      87             :         
-      88             : };
-      89             :         
-      90             : /**
-      91             :  @class SphericalAdvectionField
-      92             :  @brief Spherical advection with a exponentially increasing and
-      93             :         exponentially constant velocity.
-      94             : */
-      95             : 
-      96           1 : class SphericalAdvectionField: public AdvectionField {
-      97             :         Vector3d origin; //origin of the advection sphere
-      98             :         double radius; //radius of the advection sphere
-      99             :         double vMax; // maximum wind velocity
-     100             :         double tau; // transition distance
-     101             :         double alpha; //tuning parameter
-     102             : public:
-     103             :         /** Constructor
-     104             :         @param origin   Origin of the advection sphere
-     105             :         @param radius   Radius of the advection sphere
-     106             :         @param vMax     Maximum wind velocity
-     107             :         @param tau      Transition distance
-     108             :         @param alpha    Tuning parameter
-     109             : */
-     110             :         SphericalAdvectionField(const Vector3d origin, double radius, double vMax, double tau, double alpha);
-     111             :         Vector3d getField(const Vector3d &position) const;
-     112             :         double getDivergence(const Vector3d &position) const;
-     113             : 
-     114             :         double getV(const double &r) const;
-     115             : 
-     116             :         void setOrigin(const Vector3d origin);
-     117             :         void setRadius(double radius);
-     118             :         void setVMax(double vMax);
-     119             :         void setTau(double tau);
-     120             :         void setAlpha(double alpha);
-     121             : 
-     122             :         Vector3d getOrigin() const;
-     123             :         double getRadius() const;
-     124             :         double getVMax() const;
-     125             :         double getTau() const;
-     126             :         double getAlpha() const;
-     127             :         
-     128             :         std::string getDescription() const;
-     129             : };
-     130             : 
-     131             : /**
-     132             :  @class OneDimensionalCartesianShock
-     133             :  @brief Advection field in x-direction with shock at x = 0 and width lShock approximated by tanh() 
-     134             :                 with variable compression ratio vUp/vDown
-     135             :  */
-     136             : class OneDimensionalCartesianShock: public AdvectionField {
-     137             :         double compressionRatio; //compression ratio of shock
-     138             :         double vUp; //upstream velocity 
-     139             :         double lShock; //shock width
-     140             : public:
-     141             : /** Constructor
-     142             :         @param compressionRatio //compression ratio of shock
-     143             :         @param vUp //upstream velocity 
-     144             :         @param lShock //shock width
-     145             : */
-     146             :         OneDimensionalCartesianShock(double compressionRatio, double vUp, double lShock);
-     147             :         Vector3d getField(const Vector3d &position) const;
-     148             :         double getDivergence(const Vector3d &position) const;
-     149             : 
-     150             :         void setComp(double compressionRatio);
-     151             :         void setVup(double vUp);
-     152             :         void setShockwidth(double lShock);
-     153             : 
-     154             :         double getComp() const;
-     155             :         double getVup() const; 
-     156             :         double getShockwidth() const;
-     157             : 
-     158             :         std::string getDescription() const;
-     159             : };
-     160             : 
-     161             : /**
-     162             :  @class OneDimensionalSphericalShock
-     163             :  @brief Advection field in x-direction with shock at rShock and width lShock approximated by tanh() 
-     164             :                 with variable compression ratio ratio vUp/vDown
-     165             :  */
-     166             : class OneDimensionalSphericalShock: public AdvectionField {
-     167             :         double compressionRatio;        //compression ratio of shock
-     168             :         double vUp;     //upstream velocity 
-     169             :         double lShock;  //shock width
-     170             :         double rShock;  //shock radius
-     171             :         bool coolUpstream;      //flag for upstream cooling
-     172             : public:
-     173             : /** Constructor
-     174             :         @param compressionRatio //compression ratio of shock
-     175             :         @param vUp      //upstream velocity 
-     176             :         @param lShock   //shock width
-     177             :         @param rShock   //shock radius
-     178             :         @param coolUpstream //flag for upstream cooling
-     179             : */
-     180             :         OneDimensionalSphericalShock(double rShock, double vUp, double compressionRatio, double lShock, bool coolUpstream);
-     181             :         Vector3d getField(const Vector3d &position) const;
-     182             :         double getDivergence(const Vector3d &position) const;
-     183             : 
-     184             :         void setComp(double compressionRatio);
-     185             :         void setVup(double vUp);
-     186             :         void setShockwidth(double lShock);
-     187             :         void setShockRadius(double rShock);
-     188             :         void setCooling(bool coolUpstream);
-     189             : 
-     190             :         double getComp() const; 
-     191             :         double getVup() const;
-     192             :         double getShockwidth() const;
-     193             :         double getShockRadius() const;
-     194             :         bool getCooling() const;
-     195             : 
-     196             :         std::string getDescription() const;
-     197             : };
-     198             : 
-     199             : /**
-     200             :  @class ObliqueAdvectionShock
-     201             :  @brief Advection field in x-y-direction with shock at x = 0 and width x_sh approximated by tanh() 
-     202             :                 with variable compression ratio r_comp = vx_up/vx_down. The y component vy is not shocked 
-     203             :                 and remains constant. 
-     204             :  */
-     205             : class ObliqueAdvectionShock: public AdvectionField {
-     206             :         double compressionRatio; //compression ratio of shock
-     207             :         double vXUp; //upstream velocity x-component
-     208             :         double vY; //constant velocity y-component
-     209             :         double lShock; //shock width
-     210             :         
-     211             : public:
-     212             : /** Constructor
-     213             :         @param compressionRatio //compression ratio of shock
-     214             :         @param vXUp //upstream velocity x-component
-     215             :         @param vY //constant velocity y-component
-     216             :         @param lShock //shock width
-     217             :         
-     218             : */
-     219             :         ObliqueAdvectionShock(double compressionRatio, double vXUp, double vY, double lShock);
-     220             :         Vector3d getField(const Vector3d &position) const;
-     221             :         double getDivergence(const Vector3d &position) const;
-     222             : 
-     223             :         void setComp(double compressionRatio);
-     224             :         void setVup(double vXUp);
-     225             :         void setVy(double vY);
-     226             :         void setShockwidth(double lShock);
-     227             : 
-     228             :         double getComp() const; 
-     229             :         double getVup() const;
-     230             :         double getVy() const;
-     231             :         double getShockwidth() const;
-     232             :         
-     233             :         std::string getDescription() const;
-     234             : };
-     235             : 
-     236             : /**
-     237             :  @class SphericalAdvectionShock
-     238             :  @brief Spherical advection with a constant velocity for r<r_0
-     239             :         at the the shock the velocity drops to v_0/4. followed by
-     240             :         a decrease proportional to 1/r^2.
-     241             : */
-     242             : 
-     243           1 : class SphericalAdvectionShock: public AdvectionField {
-     244             :         Vector3d origin; // origin of the advection sphere
-     245             :         double r_0; // position of the shock
-     246             :         double v_0; // constant velocity
-     247             :         double lambda; //transition width
-     248             :         double r_rot; // normalization radius for rotation speed
-     249             :         double v_phi; // rotation speed at r_rot
-     250             : 
-     251             : public:
-     252             :         /** Constructor
-     253             :         @param origin   Origin of the advection sphere
-     254             :         @param r_0      Position of the shock
-     255             :         @param v_0      Constant velocity (r<<r_o)
-     256             :         @param lambda   Transition width / width of the shock
-     257             : */
-     258             :         SphericalAdvectionShock(const Vector3d origin, double r_0, double v_0, double lambda);
-     259             : 
-     260             :         Vector3d getField(const Vector3d &position) const;
-     261             :         double getDivergence(const Vector3d &position) const;
-     262             : 
-     263             :         double g(double R) const;
-     264             :         double g_prime(double R) const;
-     265             : 
-     266             :         void setOrigin(const Vector3d Origin);
-     267             :         void setR0(double r);
-     268             :         void setV0(double v);
-     269             :         void setLambda(double l);
-     270             :         void setRRot(double r);
-     271             :         void setAzimuthalSpeed(double vPhi);
-     272             : 
-     273             :         Vector3d getOrigin() const;
-     274             :         double getR0() const;
-     275             :         double getV0() const;
-     276             :         double getLambda() const;
-     277             :         /**
-     278             :          * @param r Normalization radius for rotation speed
-     279             :         */      
-     280             :         double getRRot() const;
-     281             :         /**
-     282             :          * @param vPhi  Rotation speed at r_rot
-     283             :         */      
-     284             :         double getAzimuthalSpeed() const;
-     285             : 
-     286             :         std::string getDescription() const;
-     287             : };
-     288             : 
-     289             : } // namespace crpropa
-     290             : 
-     291             : #endif // CRPROPA_ADVECTIONFIELD_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/advectionField/index-sort-f.html b/doc/coverageReport/include/crpropa/advectionField/index-sort-f.html deleted file mode 100644 index 4f7addbb4..000000000 --- a/doc/coverageReport/include/crpropa/advectionField/index-sort-f.html +++ /dev/null @@ -1,93 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/advectionField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.h -
100.0%
-
100.0 %5 / 5-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/advectionField/index-sort-l.html b/doc/coverageReport/include/crpropa/advectionField/index-sort-l.html deleted file mode 100644 index dd1aafc93..000000000 --- a/doc/coverageReport/include/crpropa/advectionField/index-sort-l.html +++ /dev/null @@ -1,93 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/advectionField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.h -
100.0%
-
100.0 %5 / 5-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/advectionField/index.html b/doc/coverageReport/include/crpropa/advectionField/index.html deleted file mode 100644 index b7333515c..000000000 --- a/doc/coverageReport/include/crpropa/advectionField/index.html +++ /dev/null @@ -1,93 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/advectionField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:55100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.h -
100.0%
-
100.0 %5 / 5-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/index-sort-f.html b/doc/coverageReport/include/crpropa/index-sort-f.html deleted file mode 100644 index 3e4666a0f..000000000 --- a/doc/coverageReport/include/crpropa/index-sort-f.html +++ /dev/null @@ -1,233 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropaHitTotalCoverage
Test:coverage.info.cleanedLines:40855473.6 %
Date:2024-04-08 14:58:22Functions:7716646.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Source.h -
77.8%77.8%
-
77.8 %14 / 180.0 %0 / 1
Geometry.h -
75.0%75.0%
-
75.0 %3 / 40.0 %0 / 1
Logging.h -
0.0%
-
0.0 %0 / 180.0 %0 / 6
Variant.h -
37.1%37.1%
-
37.1 %13 / 3525.0 %4 / 16
Vector3.h -
65.6%65.6%
-
65.6 %99 / 15139.0 %16 / 41
Grid.h -
88.7%88.7%
-
88.7 %173 / 19541.1 %23 / 56
Referenced.h -
73.2%73.2%
-
73.2 %41 / 5652.6 %10 / 19
PhotonBackground.h -
81.5%81.5%
-
81.5 %22 / 2789.5 %17 / 19
ParticleState.h -
100.0%
-
100.0 %1 / 1-0 / 0
Module.h -
25.0%25.0%
-
25.0 %2 / 8-0 / 0
Candidate.h -
100.0%
-
100.0 %1 / 1-0 / 0
EmissionMap.h -
100.0%
-
100.0 %1 / 1-0 / 0
Random.h -
87.5%87.5%
-
87.5 %7 / 8-0 / 0
Common.h -
100.0%
-
100.0 %10 / 10100.0 %2 / 2
AssocVector.h -
100.0%
-
100.0 %21 / 21100.0 %5 / 5
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/index-sort-l.html b/doc/coverageReport/include/crpropa/index-sort-l.html deleted file mode 100644 index f2d075e22..000000000 --- a/doc/coverageReport/include/crpropa/index-sort-l.html +++ /dev/null @@ -1,233 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropaHitTotalCoverage
Test:coverage.info.cleanedLines:40855473.6 %
Date:2024-04-08 14:58:22Functions:7716646.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Logging.h -
0.0%
-
0.0 %0 / 180.0 %0 / 6
Module.h -
25.0%25.0%
-
25.0 %2 / 8-0 / 0
Variant.h -
37.1%37.1%
-
37.1 %13 / 3525.0 %4 / 16
Vector3.h -
65.6%65.6%
-
65.6 %99 / 15139.0 %16 / 41
Referenced.h -
73.2%73.2%
-
73.2 %41 / 5652.6 %10 / 19
Geometry.h -
75.0%75.0%
-
75.0 %3 / 40.0 %0 / 1
Source.h -
77.8%77.8%
-
77.8 %14 / 180.0 %0 / 1
PhotonBackground.h -
81.5%81.5%
-
81.5 %22 / 2789.5 %17 / 19
Random.h -
87.5%87.5%
-
87.5 %7 / 8-0 / 0
Grid.h -
88.7%88.7%
-
88.7 %173 / 19541.1 %23 / 56
ParticleState.h -
100.0%
-
100.0 %1 / 1-0 / 0
Candidate.h -
100.0%
-
100.0 %1 / 1-0 / 0
EmissionMap.h -
100.0%
-
100.0 %1 / 1-0 / 0
Common.h -
100.0%
-
100.0 %10 / 10100.0 %2 / 2
AssocVector.h -
100.0%
-
100.0 %21 / 21100.0 %5 / 5
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/index.html b/doc/coverageReport/include/crpropa/index.html deleted file mode 100644 index e5683710b..000000000 --- a/doc/coverageReport/include/crpropa/index.html +++ /dev/null @@ -1,233 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropaHitTotalCoverage
Test:coverage.info.cleanedLines:40855473.6 %
Date:2024-04-08 14:58:22Functions:7716646.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AssocVector.h -
100.0%
-
100.0 %21 / 21100.0 %5 / 5
Candidate.h -
100.0%
-
100.0 %1 / 1-0 / 0
Common.h -
100.0%
-
100.0 %10 / 10100.0 %2 / 2
EmissionMap.h -
100.0%
-
100.0 %1 / 1-0 / 0
Geometry.h -
75.0%75.0%
-
75.0 %3 / 40.0 %0 / 1
Grid.h -
88.7%88.7%
-
88.7 %173 / 19541.1 %23 / 56
Logging.h -
0.0%
-
0.0 %0 / 180.0 %0 / 6
Module.h -
25.0%25.0%
-
25.0 %2 / 8-0 / 0
ParticleState.h -
100.0%
-
100.0 %1 / 1-0 / 0
PhotonBackground.h -
81.5%81.5%
-
81.5 %22 / 2789.5 %17 / 19
Random.h -
87.5%87.5%
-
87.5 %7 / 8-0 / 0
Referenced.h -
73.2%73.2%
-
73.2 %41 / 5652.6 %10 / 19
Source.h -
77.8%77.8%
-
77.8 %14 / 180.0 %0 / 1
Variant.h -
37.1%37.1%
-
37.1 %13 / 3525.0 %4 / 16
Vector3.h -
65.6%65.6%
-
65.6 %99 / 15139.0 %16 / 41
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html deleted file mode 100644 index afe0c0f07..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func-sort-c.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/GalacticMagneticField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - GalacticMagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3838100.0 %
Date:2024-04-08 14:58:22Functions:44100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22LogarithmicSpiralField11updatePhaseEv1
_ZN7crpropa22LogarithmicSpiralField16updatePitchAngleEv1
_ZNK7crpropa22LogarithmicSpiralField8getFieldENS_7Vector3IdEE1
_ZN7crpropa17ToroidalHaloField8getFieldENS_7Vector3IdEE2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html deleted file mode 100644 index d44a00d58..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.func.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/GalacticMagneticField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - GalacticMagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3838100.0 %
Date:2024-04-08 14:58:22Functions:44100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ToroidalHaloField8getFieldENS_7Vector3IdEE2
_ZN7crpropa22LogarithmicSpiralField11updatePhaseEv1
_ZN7crpropa22LogarithmicSpiralField16updatePitchAngleEv1
_ZNK7crpropa22LogarithmicSpiralField8getFieldENS_7Vector3IdEE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html deleted file mode 100644 index 6ae2c08a8..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/GalacticMagneticField.h.gcov.html +++ /dev/null @@ -1,210 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/GalacticMagneticField.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - GalacticMagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3838100.0 %
Date:2024-04-08 14:58:22Functions:44100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_GALACTICMAGNETICFIELD_H
-       2             : #define CRPROPA_GALACTICMAGNETICFIELD_H
-       3             : 
-       4             : #include "crpropa/magneticField/MagneticField.h"
-       5             : #include <cmath>
-       6             : 
-       7             : namespace crpropa {
-       8             : /**
-       9             :  * \addtogroup MagneticFields
-      10             :  * @{
-      11             :  */
-      12             : 
-      13             : /**
-      14             :  @class ToroidalHaloField
-      15             :  @brief Galactic halo field model from Prouza & Smida 2003 and Sun et al. 2008
-      16             :  */
-      17             : class ToroidalHaloField: public MagneticField {
-      18             :         double b0; // halo field strength
-      19             :         double z0; // vertical position
-      20             :         double z1; // vertical scale
-      21             :         double r0; // radial scale
-      22             : 
-      23             : public:
-      24             :         /**
-      25             :          * Constructor
-      26             :          * @param b0 halo field strength
-      27             :          * @param z0 vertical position
-      28             :          * @param z1 vertical scale
-      29             :          * @param r0 radial scale
-      30             :         */
-      31           1 :         ToroidalHaloField(double b0 = 1., double z0 = 1., double z1 = 1., double r0 = 1.) {
-      32             :                 setParameters(b0, z0, z1, r0);
-      33             :         }
-      34             : 
-      35             :         void setParameters(double b0, double z0, double z1, double r0) {
-      36           1 :                 this->b0 = b0;
-      37           1 :                 this->z0 = z0;
-      38           1 :                 this->z1 = z1;
-      39           1 :                 this->r0 = r0;
-      40             :         }
-      41             : 
-      42           2 :         Vector3d getField(Vector3d pos) {
-      43           2 :                 double r = sqrt(pos.x * pos.x + pos.y * pos.y) / r0; // in-plane radius in units of the radial scale
-      44           2 :                 double b = b0 / (1 + pow((std::fabs(pos.z) - z0) / z1, 2)) * r * exp(1 - r);
-      45           2 :                 double phi = pos.getPhi(); // azimuth
-      46           2 :                 return Vector3d(cos(phi), sin(phi), 0) * b;
-      47             :         }
-      48             : };
-      49             : /** @} */
-      50             : 
-      51             : /**
-      52             :  * \addtogroup MagneticFields
-      53             :  * @{
-      54             :  */
-      55             : 
-      56             : /**
-      57             :  @class LogarithmicSpiralField
-      58             :  @brief Galactic disk field model of axisymmetric (ASS) or bisymmetric (BSS) logarithmic spiral shape
-      59             :  */
-      60             : class LogarithmicSpiralField: public MagneticField {
-      61             : private:
-      62             :         bool isBSS;   // true for BSS, false for ASS
-      63             :         double b0;    // field strength
-      64             :         double pitch; // pitch angle [rad]
-      65             :         double rsol;  // distance of sun to galactic center
-      66             :         double rc;    // radius of central region with constant field strength
-      67             :         double d;     // distance to the first field reversal
-      68             :         double z0;    // vertical attenuation length
-      69             : 
-      70             :         double phase; // phase of the spiral arms
-      71             :         double cosPhase;
-      72             :         double sinPitch;
-      73             :         double cosPitch;
-      74             :         double tanPitch;
-      75             : 
-      76           1 :         void updatePitchAngle() {
-      77           1 :                 sinPitch = sin(pitch);
-      78           1 :                 cosPitch = cos(pitch);
-      79           1 :                 tanPitch = tan(pitch);
-      80           1 :         }
-      81             : 
-      82           1 :         void updatePhase() {
-      83           1 :                 phase = log(1 + d / rsol) / tanPitch - M_PI / 2;
-      84           1 :                 cosPhase = cos(phase);
-      85           1 :         }
-      86             : 
-      87             : public:
-      88             :         /**
-      89             :          * Constructor
-      90             :          * @param isBSS switch for the magnetic field model
-      91             :          *                              true for BSS, false for ASS
-      92             :          * @param b0    magnetic field strength
-      93             :          * @param pitch pitch angle [rad]
-      94             :          * @param rsol  distance of sun from Galactic center
-      95             :          * @param rc    radius of central region with constant field
-      96             :          * @param d             distance to first field reversal
-      97             :          * @param z0    vertical attenuation length
-      98             :         */
-      99             :         LogarithmicSpiralField(bool isBSS = true, double b0 = 1., double pitch = M_1_PI/4.,
-     100           1 :                 double rsol = 8.5*kpc, double rc = 3*kpc, double d = 5*kpc, double z0 = 3*kpc) {
-     101             :                 setParameters(isBSS, b0, pitch, rsol, rc, d, z0);
-     102             :         }
-     103             : 
-     104             :         void setParameters(bool isBSS, double b0, double pitch, double rsol,
-     105             :                         double rc, double d, double z0) {
-     106           1 :                 this->isBSS = isBSS;
-     107           1 :                 this->b0 = b0;
-     108           1 :                 this->pitch = pitch;
-     109           1 :                 this->rsol = rsol;
-     110           1 :                 this->rc = rc;
-     111           1 :                 this->d = d;
-     112           1 :                 this->z0 = z0;
-     113           1 :                 updatePitchAngle();
-     114           1 :                 updatePhase();
-     115             :         }
-     116             : 
-     117           1 :         Vector3d getField(Vector3d pos) const {
-     118           1 :                 double r = sqrt(pos.x * pos.x + pos.y * pos.y); // in-plane radius
-     119           1 :                 double b = b0 / cosPhase * rsol / std::max(r, rc);
-     120             : 
-     121           1 :                 double phi = pos.getPhi();
-     122           1 :                 double c = cos(phi - log(r / rsol) / tanPitch + phase);
-     123           1 :                 if (isBSS)
-     124           1 :                         c = std::fabs(c);
-     125           1 :                 b *= c * exp(-std::fabs(pos.z) / z0);
-     126             : 
-     127           1 :                 return Vector3d(cosPitch * cos(phi), sinPitch * sin(phi), 0) * b;
-     128             :         }
-     129             : };
-     130             : /** @} */
-     131             : 
-     132             : }// namespace crpropa
-     133             : 
-     134             : #endif // CRPROPA_GALACTICMAGNETICFIELD_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html deleted file mode 100644 index 841410136..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - MagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:121770.6 %
Date:2024-04-08 14:58:22Functions:3742.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MagneticFieldD0Ev0
_ZN7crpropa13MagneticFieldD2Ev0
_ZN7crpropa24RenormalizeMagneticFieldD0Ev0
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEE0
_ZN7crpropa24RenormalizeMagneticFieldD2Ev1
_ZNK7crpropa20UniformMagneticField8getFieldERKNS_7Vector3IdEE5760340
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEEd5760379
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html deleted file mode 100644 index 8ed4d10b3..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - MagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:121770.6 %
Date:2024-04-08 14:58:22Functions:3742.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MagneticFieldD0Ev0
_ZN7crpropa13MagneticFieldD2Ev0
_ZN7crpropa24RenormalizeMagneticFieldD0Ev0
_ZN7crpropa24RenormalizeMagneticFieldD2Ev1
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa13MagneticField8getFieldERKNS_7Vector3IdEEd5760379
_ZNK7crpropa20UniformMagneticField8getFieldERKNS_7Vector3IdEE5760340
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html deleted file mode 100644 index 2866a8501..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/MagneticField.h.gcov.html +++ /dev/null @@ -1,248 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticField.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - MagneticField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:121770.6 %
Date:2024-04-08 14:58:22Functions:3742.9 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_MAGNETICFIELD_H
-       2             : #define CRPROPA_MAGNETICFIELD_H
-       3             : 
-       4             : #include "crpropa/Units.h"
-       5             : #include "crpropa/Vector3.h"
-       6             : #include "crpropa/Referenced.h"
-       7             : 
-       8             : #ifdef CRPROPA_HAVE_MUPARSER
-       9             : #include "muParser.h"
-      10             : #endif
-      11             : 
-      12             : namespace crpropa {
-      13             : /**
-      14             :  * \addtogroup MagneticFields
-      15             :  * @{
-      16             :  */
-      17             : 
-      18             : /**
-      19             :  @class MagneticField
-      20             :  @brief Abstract base class for magnetic fields.
-      21             :  */
-      22           0 : class MagneticField: public Referenced {
-      23             : public:
-      24           0 :         virtual ~MagneticField() {
-      25           0 :         }
-      26           0 :         virtual Vector3d getField(const Vector3d &position) const {
-      27           0 :                 return Vector3d(0,0,0);
-      28             :         };
-      29     5760379 :         virtual Vector3d getField(const Vector3d &position, double z) const {
-      30     5760379 :                 return getField(position);
-      31             :         };
-      32             : };
-      33             : 
-      34             : /**
-      35             :  @class PeriodicMagneticField
-      36             :  @brief Magnetic field decorator implementing periodic fields.
-      37             : 
-      38             :  The periodic cube is defined by its origin (Vector3d) and an
-      39             :  extends parameter (Vector3d). All points x=(x_1, x_2, x_3) 
-      40             :  that are described by x_i = origin_i + epsilon * extend_i, 
-      41             :  with epsilon = 0...1 are within the base cube. Magnetic field
-      42             :  strengths for all positions outside of this cube are calculated 
-      43             :  based on the values in the base cube. 
-      44             :  This can be done periodically or reflectively.
-      45             : */
-      46             : 
-      47             : class PeriodicMagneticField: public MagneticField {
-      48             :         ref_ptr<MagneticField> field;
-      49             :         Vector3d origin, extends;
-      50             :         bool reflective;
-      51             : public:
-      52             :         /**
-      53             :          * Constructor
-      54             :          * @param field magnetic field reference pointer
-      55             :          * @param extends length, width, and height of the base cube 
-      56             :         */
-      57             :         PeriodicMagneticField(ref_ptr<MagneticField> field,
-      58             :                         const Vector3d &extends);
-      59             :         /**
-      60             :          * Constructor
-      61             :          * @param field magnetic field reference pointer
-      62             :          * @param extends length, width, and height of the base cube
-      63             :          * @param origin defines the reference position 
-      64             :          * @param reflective for periodic or reflective behavior  
-      65             :         */
-      66             :         PeriodicMagneticField(ref_ptr<MagneticField> field, const Vector3d &extends,
-      67             :                         const Vector3d &origin, bool reflective);
-      68             :         Vector3d &getOrigin();
-      69             :         void setOrigin(const Vector3d &origin);
-      70             :         Vector3d &getExtends();
-      71             :         void setExtends(const Vector3d &origin);
-      72             :         bool isReflective();
-      73             :         void setReflective(bool reflective);
-      74             :         Vector3d getField(const Vector3d &position) const;
-      75             : };
-      76             : 
-      77             : /**
-      78             :  @class MagneticFieldList
-      79             :  @brief Magnetic field decorator implementing a superposition of fields.
-      80             :  */
-      81           2 : class MagneticFieldList: public MagneticField {
-      82             :         std::vector<ref_ptr<MagneticField> > fields;
-      83             : public:
-      84             :         void addField(ref_ptr<MagneticField> field);
-      85             :         Vector3d getField(const Vector3d &position) const;
-      86             : };
-      87             : 
-      88             : /**
-      89             :  @class MagneticFieldEvolution
-      90             :  @brief Magnetic field decorator implementing an evolution of type (1+z)^m.
-      91             :  */
-      92           2 : class MagneticFieldEvolution: public MagneticField {
-      93             :         ref_ptr<MagneticField> field;
-      94             :         double m;
-      95             : public:
-      96             :         /**
-      97             :          * Constructor
-      98             :          * @param field magnetic field reference pointer
-      99             :          * @param m cosmic evolution parameter 
-     100             :         */
-     101             :         MagneticFieldEvolution(ref_ptr<MagneticField> field, double m);
-     102             :         Vector3d getField(const Vector3d &position, double z = 0) const;
-     103             : };
-     104             : 
-     105             : /**
-     106             :  @class UniformMagneticField
-     107             :  @brief Magnetic field with one B-field vector.
-     108             :  */
-     109             : class UniformMagneticField: public MagneticField {
-     110             :         Vector3d value;
-     111             : public:
-     112             :         /**
-     113             :          * Constructor
-     114             :          * @param value magnetic field strength
-     115             :         */
-     116          33 :         UniformMagneticField(const Vector3d &value) :
-     117          33 :                         value(value) {
-     118             :         }
-     119     5760340 :         Vector3d getField(const Vector3d &position) const {
-     120     5760340 :                 return value;
-     121             :         }
-     122             : };
-     123             : 
-     124             : /**
-     125             :  @class MagneticDipoleField
-     126             :  @brief Magnetic dipole field defined by the magnetic moment and the 'core' radius.
-     127             :  */
-     128           1 : class MagneticDipoleField: public MagneticField {
-     129             :         Vector3d origin;
-     130             :         Vector3d moment;
-     131             :         double radius;
-     132             : public:
-     133             :         /**
-     134             :          * Constructor
-     135             :          * @param origin        singularity of the dipole field
-     136             :          * @param moment        magnetic moment of the dipole field
-     137             :          * @param radius        inside a radius around the origin the 
-     138             :          *                                      magnetic field is constant: moment * 2 * mu0 / 3  
-     139             :         */
-     140           1 :         MagneticDipoleField(const Vector3d &origin, const Vector3d &moment, const double radius) :
-     141           1 :                         origin(origin), moment(moment), radius(radius) {
-     142             :         }
-     143             :         Vector3d getField(const Vector3d &position) const;
-     144             : };
-     145             : 
-     146             : #ifdef CRPROPA_HAVE_MUPARSER
-     147             : /**
-     148             :  @class RenormalizeMagneticField
-     149             :  @brief Renormalize strength of a given field by expression in which B is the strength variable.
-     150             :  */
-     151             : class RenormalizeMagneticField: public MagneticField {
-     152             :         ref_ptr<MagneticField> field;
-     153             :         std::string expression;
-     154             :         mu::Parser *p;
-     155             :         double Bmag;
-     156             : public:
-     157             :         /**
-     158             :          * Constructor
-     159             :          * @param field                 magnetic field reference pointer
-     160             :          * @param expression    muParser expression used to renormalize the field, 
-     161             :          *                                              e.g., "gauss". 
-     162             :         */
-     163             :         RenormalizeMagneticField(ref_ptr<MagneticField> field, std::string expression);
-     164           1 :         ~RenormalizeMagneticField() { delete p; }
-     165             :         Vector3d getField(const Vector3d &position);
-     166             : };
-     167             : #endif
-     168             : 
-     169             : /** @} */
-     170             : } // namespace crpropa
-     171             : 
-     172             : #endif // CRPROPA_MAGNETICFIELD_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html deleted file mode 100644 index 62ce25a19..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticFieldGrid.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - MagneticFieldGrid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html deleted file mode 100644 index 04a253ccc..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticFieldGrid.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - MagneticFieldGrid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html deleted file mode 100644 index 7d0df9558..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/MagneticFieldGrid.h.gcov.html +++ /dev/null @@ -1,139 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/MagneticFieldGrid.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField - MagneticFieldGrid.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_MAGNETICFIELDGRID_H
-       2             : #define CRPROPA_MAGNETICFIELDGRID_H
-       3             : 
-       4             : #include "crpropa/magneticField/MagneticField.h"
-       5             : #include "crpropa/Grid.h"
-       6             : 
-       7             : namespace crpropa {
-       8             : /**
-       9             :  * \addtogroup MagneticFields
-      10             :  * @{
-      11             :  */
-      12             : 
-      13             : /**
-      14             :  @class MagneticFieldGrid
-      15             :  @brief Magnetic field on a periodic (or reflective), cartesian grid with trilinear interpolation.
-      16             : 
-      17             :  This class wraps a Grid3f to serve as a MagneticField.
-      18             :  */
-      19             : class MagneticFieldGrid: public MagneticField {
-      20             :         ref_ptr<Grid3f> grid;
-      21             : public:
-      22             :         /**
-      23             :          *Constructor
-      24             :          @param grid Grid3f storing the magnetic field vectors
-      25             :         */
-      26             :         MagneticFieldGrid(ref_ptr<Grid3f> grid);
-      27             :         void setGrid(ref_ptr<Grid3f> grid);
-      28             :         ref_ptr<Grid3f> getGrid();
-      29             :         Vector3d getField(const Vector3d &position) const;
-      30             : };
-      31             : 
-      32             : /**
-      33             :  @class ModulatedMagneticFieldGrid
-      34             :  @brief Modulated magnetic field on a periodic grid.
-      35             : 
-      36             :  This class wraps a Grid3f to serve as a MagneticField.
-      37             :  The field is modulated on-the-fly with a Grid1f.
-      38             :  The Grid3f and Grid1f do not need to share the same origin, spacing or size.
-      39             :  */
-      40             : class ModulatedMagneticFieldGrid: public MagneticField {
-      41             :         ref_ptr<Grid3f> grid;
-      42             :         ref_ptr<Grid1f> modGrid;
-      43             : public:
-      44           0 :         ModulatedMagneticFieldGrid() {
-      45             :         }
-      46             :         /**
-      47             :          *Constructor
-      48             :          @param grid    Grid3f storing the magnetic field vectors
-      49             :          @param modGrid Grid1f used to scale the magnetic field strength
-      50             :                                         B^new_i = B^old_i * scale 
-      51             :         */
-      52             :         ModulatedMagneticFieldGrid(ref_ptr<Grid3f> grid, ref_ptr<Grid1f> modGrid);
-      53             :         void setGrid(ref_ptr<Grid3f> grid);
-      54             :         void setModulationGrid(ref_ptr<Grid1f> modGrid);
-      55             :         ref_ptr<Grid3f> getGrid();
-      56             :         ref_ptr<Grid1f> getModulationGrid();
-      57             :         void setReflective(bool gridReflective, bool modGridReflective);
-      58             :         Vector3d getField(const Vector3d &position) const;
-      59             : };
-      60             : /** @} */
-      61             : } // namespace crpropa
-      62             : 
-      63             : #endif // CRPROPA_MAGNETICFIELDGRID_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/index-sort-f.html b/doc/coverageReport/include/crpropa/magneticField/index-sort-f.html deleted file mode 100644 index 08da227af..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/index-sort-f.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:505689.3 %
Date:2024-04-08 14:58:22Functions:71163.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticField.h -
70.6%70.6%
-
70.6 %12 / 1742.9 %3 / 7
MagneticFieldGrid.h -
0.0%
-
0.0 %0 / 1-0 / 0
GalacticMagneticField.h -
100.0%
-
100.0 %38 / 38100.0 %4 / 4
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/index-sort-l.html b/doc/coverageReport/include/crpropa/magneticField/index-sort-l.html deleted file mode 100644 index 3a378c7d3..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/index-sort-l.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:505689.3 %
Date:2024-04-08 14:58:22Functions:71163.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticFieldGrid.h -
0.0%
-
0.0 %0 / 1-0 / 0
MagneticField.h -
70.6%70.6%
-
70.6 %12 / 1742.9 %3 / 7
GalacticMagneticField.h -
100.0%
-
100.0 %38 / 38100.0 %4 / 4
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/index.html b/doc/coverageReport/include/crpropa/magneticField/index.html deleted file mode 100644 index 9cd37eb4a..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/index.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:505689.3 %
Date:2024-04-08 14:58:22Functions:71163.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
GalacticMagneticField.h -
100.0%
-
100.0 %38 / 38100.0 %4 / 4
MagneticField.h -
70.6%70.6%
-
70.6 %12 / 1742.9 %3 / 7
MagneticFieldGrid.h -
0.0%
-
0.0 %0 / 1-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html deleted file mode 100644 index 3432fc3a9..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/GridTurbulence.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - GridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html deleted file mode 100644 index fd3be85af..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/GridTurbulence.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - GridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html deleted file mode 100644 index 29f802928..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/GridTurbulence.h.gcov.html +++ /dev/null @@ -1,151 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/GridTurbulence.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - GridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_GRIDTURBULENCE_H
-       2             : #define CRPROPA_GRIDTURBULENCE_H
-       3             : 
-       4             : #ifdef CRPROPA_HAVE_FFTW3F
-       5             : 
-       6             : #include "crpropa/Grid.h"
-       7             : #include "crpropa/magneticField/turbulentField/TurbulentField.h"
-       8             : 
-       9             : #include "fftw3.h"
-      10             : 
-      11             : namespace crpropa {
-      12             : /**
-      13             :  * \addtogroup MagneticFields
-      14             :  * @{
-      15             :  */
-      16             : 
-      17             : /**
-      18             :  @class GridTurbulence
-      19             :  @brief Turbulent grid-based magnetic field with a general energy spectrum
-      20             :  */
-      21           6 : class GridTurbulence : public TurbulentField {
-      22             :   protected:
-      23             :         unsigned int seed;
-      24             :         ref_ptr<Grid3f> gridPtr;
-      25             : 
-      26             :         void initGrid(const GridProperties &grid);
-      27             :         void initTurbulence();
-      28             : 
-      29             :   public:
-      30             :         /**
-      31             :          Create a random initialization of a turbulent field.
-      32             :          @param spectrum    TurbulenceSpectrum instance to define the spectrum of
-      33             :          turbulence
-      34             :          @param gridProp        GridProperties instance to define the underlying grid
-      35             :          @param seed     Random seed
-      36             :          */
-      37             :         GridTurbulence(const TurbulenceSpectrum &spectrum,
-      38             :                        const GridProperties &gridProp, unsigned int seed = 0);
-      39             : 
-      40             :         Vector3d getField(const Vector3d &pos) const;
-      41             : 
-      42             :         /** Return a const reference to the grid */
-      43             :         const ref_ptr<Grid3f> &getGrid() const;
-      44             : 
-      45             :         /* Helper functions for synthetic turbulent field models */
-      46             :         // Check the grid properties before the FFT procedure
-      47             :         static void checkGridRequirements(ref_ptr<Grid3f> grid, double lMin,
-      48             :                                           double lMax);
-      49             :         // Execute inverse discrete FFT in-place for a 3D grid, from complex to real
-      50             :         // space
-      51             :         static void executeInverseFFTInplace(ref_ptr<Grid3f> grid,
-      52             :                                              fftwf_complex *Bkx, fftwf_complex *Bky,
-      53             :                                              fftwf_complex *Bkz);
-      54             : 
-      55             :         // Usefull checks for a grid field
-      56             :         /** Evaluate the mean vector of all grid points */
-      57             :         Vector3f getMeanFieldVector() const;
-      58             :         /** Evaluate the mean of all grid points */
-      59             :         double getMeanFieldStrength() const;
-      60             :         /** Evaluate the RMS of all grid points */
-      61             :         double getRmsFieldStrength() const;
-      62             :         /** Evaluate the RMS of all grid points per axis */
-      63             :         std::array<float, 3> getRmsFieldStrengthPerAxis() const;
-      64             :         /** Evaluate generated power-spectrum */
-      65             :         std::vector<std::pair<int, float>> getPowerSpectrum() const;
-      66             :         /** Dump a Grid3f to a binary file */
-      67             :         void dumpToFile(std::string filename) const;
-      68             : };
-      69             : 
-      70             : /** @}*/
-      71             : } // namespace crpropa
-      72             : 
-      73             : #endif // CRPROPA_HAVE_FFTW3F
-      74             : 
-      75             : #endif // CRPROPA_GRIDTURBULENCE_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html deleted file mode 100644 index 0c515e402..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - HelicalGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21initHelicalTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html deleted file mode 100644 index b4ddcbe9c..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - HelicalGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21initHelicalTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html deleted file mode 100644 index f2108a9f4..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h.gcov.html +++ /dev/null @@ -1,147 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/HelicalGridTurbulence.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - HelicalGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:050.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_HELICALGRIDTURBULENCE_H
-       2             : #define CRPROPA_HELICALGRIDTURBULENCE_H
-       3             : 
-       4             : #ifdef CRPROPA_HAVE_FFTW3F
-       5             : 
-       6             : #include "crpropa/Grid.h"
-       7             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
-       8             : 
-       9             : #include "kiss/logger.h"
-      10             : #include "kiss/string.h"
-      11             : 
-      12             : namespace crpropa {
-      13             : /**
-      14             :  * \addtogroup MagneticFields
-      15             :  * @{
-      16             :  */
-      17             : 
-      18             : /**
-      19             :  @class HelicalGridTurbulence
-      20             :  @brief Turbulent grid-based magnetic field with a simple power-law spectrum
-      21             :  */
-      22             : class HelicalGridTurbulence : public SimpleGridTurbulence {
-      23             :   private:
-      24             :         double H;
-      25             : 
-      26             :   public:
-      27             :         /**
-      28             :          Create a random initialization of a turbulent field.
-      29             :          @param spectrum    TurbulenceSpectrum instance to define the spectrum of
-      30             :          turbulence
-      31             :          @param gridProp        GridProperties instance to define the underlying grid
-      32             :          @param H       Helicity
-      33             :          @param seed     Random seed
-      34             :          */
-      35             :         HelicalGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
-      36             :                               const GridProperties &gridProp, double H,
-      37             :                               unsigned int seed = 0);
-      38             : 
-      39             :         static void initTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
-      40             :                                    double lMax, double alpha, int seed, double H);
-      41             : };
-      42             : 
-      43             : // Compatibility with old functions from GridTurbulence:
-      44             : 
-      45             : /**
-      46             :  Create a random initialization of a turbulent field including helicity
-      47             :  @param grid    grid on which the turbulence is calculated
-      48             :  @param Brms    RMS field strength
-      49             :  @param lMin    Minimum wavelength of the turbulence
-      50             :  @param lMax    Maximum wavelength of the turbulence
-      51             :  @param alpha   Power law index of <B^2(k)> ~ k^alpha (alpha = -11/3 corresponds
-      52             :  to a Kolmogorov spectrum)
-      53             :  @param seed    Random seed
-      54             :  @param H               Helicity
-      55             : */
-      56           0 : void initHelicalTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
-      57             :                            double lMax, double alpha = -11 / 3., int seed = 0,
-      58             :                            double H = 0) {
-      59           0 :         KISS_LOG_WARNING
-      60             :             << "initTurbulence is deprecated and will be removed in the future. "
-      61           0 :                "Replace it with a more appropriate turbulent field model instance.";
-      62           0 :         HelicalGridTurbulence::initTurbulence(grid, Brms, lMin, lMax, alpha, seed,
-      63             :                                               H);
-      64           0 : }
-      65             : 
-      66             : /** @}*/
-      67             : } // namespace crpropa
-      68             : 
-      69             : #endif // CRPROPA_HAVE_FFTW3F
-      70             : 
-      71             : #endif // CRPROPA_HELICALGRIDTURBULENCE_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html deleted file mode 100644 index e3787874e..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - SimpleGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:172181.0 %
Date:2024-04-08 14:58:22Functions:4757.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa24SimpleTurbulenceSpectrumD0Ev0
_ZN7crpropa24SimpleTurbulenceSpectrumD2Ev0
_ZNK7crpropa24SimpleTurbulenceSpectrum20getCorrelationLengthEv0
_ZN7crpropa24SimpleTurbulenceSpectrum26turbulentCorrelationLengthEddd1
_ZN7crpropa26turbulentCorrelationLengthEddd1
_ZN7crpropa14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi4
_ZNK7crpropa24SimpleTurbulenceSpectrum14energySpectrumEd206961
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html deleted file mode 100644 index c913f5f27..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - SimpleGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:172181.0 %
Date:2024-04-08 14:58:22Functions:4757.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi4
_ZN7crpropa24SimpleTurbulenceSpectrum26turbulentCorrelationLengthEddd1
_ZN7crpropa24SimpleTurbulenceSpectrumD0Ev0
_ZN7crpropa24SimpleTurbulenceSpectrumD2Ev0
_ZN7crpropa26turbulentCorrelationLengthEddd1
_ZNK7crpropa24SimpleTurbulenceSpectrum14energySpectrumEd206961
_ZNK7crpropa24SimpleTurbulenceSpectrum20getCorrelationLengthEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html deleted file mode 100644 index 57422a4cb..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h.gcov.html +++ /dev/null @@ -1,192 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/SimpleGridTurbulence.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - SimpleGridTurbulence.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:172181.0 %
Date:2024-04-08 14:58:22Functions:4757.1 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_SIMPLEGRIDTURBULENCE_H
-       2             : #define CRPROPA_SIMPLEGRIDTURBULENCE_H
-       3             : 
-       4             : #ifdef CRPROPA_HAVE_FFTW3F
-       5             : 
-       6             : #include "crpropa/magneticField/turbulentField/GridTurbulence.h"
-       7             : 
-       8             : #include "kiss/logger.h"
-       9             : #include "kiss/string.h"
-      10             : 
-      11             : namespace crpropa {
-      12             : /**
-      13             :  * \addtogroup MagneticFields
-      14             :  * @{
-      15             :  */
-      16             : 
-      17             : /**
-      18             :  @class SimpleTurbulenceSpectrum
-      19             :  @brief Defines the energy spectrum of simple power-law turbulence
-      20             :  */
-      21             : class SimpleTurbulenceSpectrum : public TurbulenceSpectrum {
-      22             :         const int constScaleBendover = 1000;    // define the bandover scale as 1000 * lMax to ensure k * lBendover >> 1. The bendover scale is necessary for the implementation of PlaneWaveTurbulence. 
-      23             :   public:
-      24             :         /**
-      25             :          * The bend-over scale is set to 1000 times lMax to ensure to be in the inertial range. This should not be changed.
-      26             :          @param Brms            Root mean square field strength for generated field
-      27             :          @param lMin            Minimum physical scale of the turbulence
-      28             :          @param lMax            Maximum physical scale of the turbulence
-      29             :          @param sIndex          Spectral index of the energy spectrum in the inertial range
-      30             :         */
-      31             :         SimpleTurbulenceSpectrum(double Brms, double lMin, double lMax,
-      32             :                                  double sIndex = 5. / 3)
-      33           2 :             : TurbulenceSpectrum(Brms, lMin, lMax, constScaleBendover * lMax, sIndex, 0) {}
-      34           0 :         ~SimpleTurbulenceSpectrum() {}
-      35             : 
-      36             :         /**
-      37             :         General energy spectrum for synthetic turbulence models
-      38             :         */
-      39      206961 :         double energySpectrum(double k) const {
-      40      206961 :                 return std::pow(k, -getSindex() - 2);
-      41             :         }
-      42             : 
-      43             :         /**
-      44             :             @brief       compute the magnetic field coherence length according to
-      45             :            the formula in  Harari et al. JHEP03(2002)045
-      46             :             @return Lc   coherence length of the magnetic field
-      47             :         */
-      48           0 :         double getCorrelationLength() const {
-      49           0 :                 return turbulentCorrelationLength(getLmin(), getLmax(),
-      50           0 :                                                   getSindex());
-      51             :         }
-      52           1 :         static double turbulentCorrelationLength(double lMin, double lMax,
-      53             :                                                  double s) {
-      54           1 :                 double r = lMin / lMax;
-      55           1 :                 return lMax / 2 * (s - 1) / s * (1 - pow(r, s)) / (1 - pow(r, s - 1));
-      56             :         }
-      57             : };
-      58             : 
-      59             : /**
-      60             :  @class SimpleGridTurbulence
-      61             :  @brief Turbulent grid-based magnetic field with a simple power-law spectrum
-      62             :  */
-      63           3 : class SimpleGridTurbulence : public GridTurbulence {
-      64             :   public:
-      65             :         /**
-      66             :          Create a random initialization of a turbulent field.
-      67             :          @param spectrum    TurbulenceSpectrum instance to define the spectrum of
-      68             :          turbulence
-      69             :          @param gridProp        GridProperties instance to define the underlying grid
-      70             :          @param seed     Random seed
-      71             :          */
-      72             :         SimpleGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
-      73             :                              const GridProperties &gridProp, unsigned int seed = 0);
-      74             : 
-      75             :         static void initTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
-      76             :                                    double lMax, double alpha, int seed);
-      77             : };
-      78             : 
-      79             : // Compatibility with old functions from GridTurbulence:
-      80             : 
-      81             : /** Analytically calculate the correlation length of the simple model turbulent
-      82             :  * field */
-      83           1 : inline double turbulentCorrelationLength(double lMin, double lMax,
-      84             :                                          double alpha = -11 / 3.) {
-      85           2 :         KISS_LOG_WARNING
-      86             :             << "turbulentCorrelationLength is deprecated and will be "
-      87             :                "removed in the future. Replace it with a more appropriate "
-      88           1 :                "turbulent field model and call getCorrelationLength().";
-      89           1 :         return SimpleTurbulenceSpectrum::turbulentCorrelationLength(lMin, lMax,
-      90           1 :                                                                     -alpha - 2);
-      91             : }
-      92             : 
-      93             : /**
-      94             :  Create a random initialization of a turbulent field.
-      95             :  @param grid    grid on which the turbulence is calculated
-      96             :  @param lMin    Minimum wavelength of the turbulence
-      97             :  @param lMax    Maximum wavelength of the turbulence
-      98             :  @param alpha   Power law index of <B^2(k)> ~ k^alpha (alpha = -11/3 corresponds
-      99             :  to a Kolmogorov spectrum)
-     100             :  @param Brms    RMS field strength
-     101             :  @param seed    Random seed
-     102             :  */
-     103           4 : inline void initTurbulence(ref_ptr<Grid3f> grid, double Brms, double lMin,
-     104             :                            double lMax, double alpha = -11 / 3., int seed = 0) {
-     105           8 :         KISS_LOG_WARNING
-     106             :             << "initTurbulence is deprecated and will be removed in the future. "
-     107           4 :                "Replace it with a more appropriate turbulent field model instance.";
-     108           4 :         SimpleGridTurbulence::initTurbulence(grid, Brms, lMin, lMax, alpha, seed);
-     109           1 : }
-     110             : 
-     111             : /** @}*/
-     112             : } // namespace crpropa
-     113             : 
-     114             : #endif // CRPROPA_HAVE_FFTW3F
-     115             : 
-     116             : #endif // CRPROPA_SIMPLEGRIDTURBULENCE_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html deleted file mode 100644 index e588a9cfb..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func-sort-c.html +++ /dev/null @@ -1,108 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/TurbulentField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - TurbulentField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:253278.1 %
Date:2024-04-08 14:58:22Functions:4944.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14TurbulentFieldD0Ev0
_ZN7crpropa14TurbulentFieldD2Ev0
_ZN7crpropa18TurbulenceSpectrumD2Ev0
_ZNK7crpropa14TurbulentField20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum21spectrumNormalizationEv1
_ZN7crpropa18TurbulenceSpectrumD0Ev2
_ZN7crpropa18TurbulenceSpectrumC2Edddddd9
_ZNK7crpropa18TurbulenceSpectrum14energySpectrumEd208128
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html deleted file mode 100644 index 6e9224a7c..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.func.html +++ /dev/null @@ -1,108 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/TurbulentField.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - TurbulentField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:253278.1 %
Date:2024-04-08 14:58:22Functions:4944.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14TurbulentFieldD0Ev0
_ZN7crpropa14TurbulentFieldD2Ev0
_ZN7crpropa18TurbulenceSpectrumC2Edddddd9
_ZN7crpropa18TurbulenceSpectrumD0Ev2
_ZN7crpropa18TurbulenceSpectrumD2Ev0
_ZNK7crpropa14TurbulentField20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum14energySpectrumEd208128
_ZNK7crpropa18TurbulenceSpectrum20getCorrelationLengthEv0
_ZNK7crpropa18TurbulenceSpectrum21spectrumNormalizationEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html deleted file mode 100644 index dd676ef0c..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/TurbulentField.h.gcov.html +++ /dev/null @@ -1,195 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField/TurbulentField.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentField - TurbulentField.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:253278.1 %
Date:2024-04-08 14:58:22Functions:4944.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_TURBULENTFIELD_H
-       2             : #define CRPROPA_TURBULENTFIELD_H
-       3             : 
-       4             : #include "crpropa/magneticField/MagneticField.h"
-       5             : #include <cmath>
-       6             : 
-       7             : namespace crpropa {
-       8             : /**
-       9             :  * \addtogroup MagneticFields
-      10             :  * @{
-      11             :  */
-      12             : 
-      13             : /**
-      14             :  @class TurbulenceSpectrum
-      15             :  @brief Defines the energy spectrum of turbulence parametrizied by A(k) ~ k^q /(1 + k^2)^{(s + q)/2 + 1}
-      16             :  */
-      17             : class TurbulenceSpectrum : public Referenced {
-      18             :   private:
-      19             :         const double Brms; /**< Brms value of the turbulent field (normalization) */
-      20             :         const double sIndex; /**< Spectral index for the inertial range, for example
-      21             :                           s=5/3 for Kolmogorov spectrum; in some parts of the code this
-      22             :                           parameter is referred by alpha which is the total 3D isotropic
-      23             :                           spectrum with additional k^2 and the minus sign, e.g.,
-      24             :                           for Kolmogorov: alpha = -(s + 2) */
-      25             :         const double qIndex; /**< Spectral index for the injection range, for
-      26             :                           example q=4 for 3D homogeneous turbulence */
-      27             :         const double lBendover;  /**< the bend-over scale */
-      28             :         const double lMin, lMax; /**< Min and Max scale of turbulence */
-      29             : 
-      30             :   protected:
-      31             :         /**
-      32             :         Normalization for the below defined Lc
-      33             :         */
-      34           1 :         double spectrumNormalization() const {
-      35           1 :                 return std::tgamma((sIndex + qIndex) / 2.0) /
-      36           1 :                        (2.0 * std::tgamma((sIndex - 1) / 2.0) *
-      37           1 :                         std::tgamma((qIndex + 1) / 2.0));
-      38             :         }
-      39             : 
-      40             :   public:
-      41             :         /**
-      42             :          * @param Brms         root mean square field strength for generated field
-      43             :          * @param lMin   Minimum physical scale of the turbulence
-      44             :          * @param lMax   Maximum physical scale of the turbulence
-      45             :          * @param lBendover        the bend-over scale
-      46             :          * @param sIndex         Spectral index of the energy spectrum in the inertial range
-      47             :          * @param qIndex         Spectral index of the energy spectrum in the energy range
-      48             :         */
-      49           9 :         TurbulenceSpectrum(double Brms, double lMin, double lMax,
-      50             :                            double lBendover = 1, double sIndex = (5. / 3.),
-      51             :                            double qIndex = 4)
-      52           9 :             : Brms(Brms), lMin(lMin), lMax(lMax), lBendover(lBendover),
-      53           9 :               sIndex(sIndex), qIndex(qIndex) {
-      54           9 :                 if (lMin > lMax) {
-      55           0 :                         throw std::runtime_error("TurbulenceSpectrum: lMin > lMax");
-      56             :                 }
-      57           9 :                 if (lMin <= 0) {
-      58           0 :                         throw std::runtime_error("TurbulenceSpectrum: lMin <= 0");
-      59             :                 }
-      60           9 :         }
-      61             : 
-      62           7 :         ~TurbulenceSpectrum() {}
-      63             : 
-      64          31 :         double getBrms() const { return Brms; }
-      65          19 :         double getLmin() const { return lMin; }
-      66          19 :         double getLmax() const { return lMax; }
-      67          22 :         double getLbendover() const { return lBendover; }
-      68           5 :         double getSindex() const { return sIndex; }
-      69           2 :         double getQindex() const { return qIndex; }
-      70             :         
-      71             :         /**
-      72             :         General energy spectrum for synthetic turbulence models (not normalized!)
-      73             :         with normalized ^k = k*lBendover
-      74             :         */
-      75      208128 :         virtual double energySpectrum(double k) const {
-      76      208128 :                 double kHat = k * lBendover;
-      77      208128 :                 return std::pow(kHat, qIndex) /
-      78      208128 :                                        std::pow(1.0 + kHat * kHat,
-      79      208128 :                                         (sIndex + qIndex) / 2.0 + 1.0);
-      80             :         }
-      81             : 
-      82             :         /**
-      83             :   Computes the magnetic field coherence length
-      84             :         Obtained from the definition of \f$l_c = 1/B_{\rm rms}^2 \int_0^\infty dr\langleB(0)B^*(r)\rangle \f$
-      85             :         Approximates the true value correctly as long as lBendover <= lMax/8 (~5%
-      86             :   error) (for the true value the above integral should go from lMin to lMax)
-      87             :         */
-      88           0 :         virtual double getCorrelationLength() const {
-      89           1 :                 return 4 * M_PI / ((sIndex + 2.0) * sIndex) * spectrumNormalization() *
-      90           1 :                        lBendover;
-      91             :         }
-      92             : };
-      93             : 
-      94             : /**
-      95             :  @class TurbulentField
-      96             :  @brief An abstract base class for different models of turbulent magnetic fields
-      97             : 
-      98             :  This module provides common methods for all turbulent (synthetic) magnetic
-      99             :  fields. Does not actually implement any turbulent field.
-     100             :  */
-     101             : class TurbulentField : public MagneticField {
-     102             :   protected:
-     103             :         const TurbulenceSpectrum &spectrum;
-     104             : 
-     105             :   public:
-     106           8 :         TurbulentField(const TurbulenceSpectrum &spectrum) : spectrum(spectrum) {}
-     107           0 :         virtual ~TurbulentField() {}
-     108             : 
-     109           0 :         double getBrms() const { return spectrum.getBrms(); }
-     110           0 :         virtual double getCorrelationLength() const {
-     111           0 :                 return spectrum.getCorrelationLength();
-     112             :         }
-     113             : };
-     114             : 
-     115             : /** @}*/
-     116             : 
-     117             : } // namespace crpropa
-     118             : 
-     119             : #endif // CRPROPA_TURBULENTFIELD_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html deleted file mode 100644 index 297188998..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-f.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:435972.9 %
Date:2024-04-08 14:58:22Functions:81747.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.h -
0.0%
-
0.0 %0 / 50.0 %0 / 1
TurbulentField.h -
78.1%78.1%
-
78.1 %25 / 3244.4 %4 / 9
SimpleGridTurbulence.h -
81.0%81.0%
-
81.0 %17 / 2157.1 %4 / 7
GridTurbulence.h -
100.0%
-
100.0 %1 / 1-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html deleted file mode 100644 index 133acd288..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index-sort-l.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:435972.9 %
Date:2024-04-08 14:58:22Functions:81747.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.h -
0.0%
-
0.0 %0 / 50.0 %0 / 1
TurbulentField.h -
78.1%78.1%
-
78.1 %25 / 3244.4 %4 / 9
SimpleGridTurbulence.h -
81.0%81.0%
-
81.0 %17 / 2157.1 %4 / 7
GridTurbulence.h -
100.0%
-
100.0 %1 / 1-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html b/doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html deleted file mode 100644 index c75493324..000000000 --- a/doc/coverageReport/include/crpropa/magneticField/turbulentField/index.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticField/turbulentField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:435972.9 %
Date:2024-04-08 14:58:22Functions:81747.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
GridTurbulence.h -
100.0%
-
100.0 %1 / 1-0 / 0
HelicalGridTurbulence.h -
0.0%
-
0.0 %0 / 50.0 %0 / 1
SimpleGridTurbulence.h -
81.0%81.0%
-
81.0 %17 / 2157.1 %4 / 7
TurbulentField.h -
78.1%78.1%
-
78.1 %25 / 3244.4 %4 / 9
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html deleted file mode 100644 index 1aa082456..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func-sort-c.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/MagneticLens.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - MagneticLens.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:204247.6 %
Date:2024-04-08 14:58:22Functions:4666.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLensC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa8LensPartC2Ev0
_ZN7crpropa12MagneticLensC2Eh3
_ZN7crpropa12MagneticLensD2Ev3
_ZN7crpropa8LensPartC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd3
_ZN7crpropa8LensPartD2Ev3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html deleted file mode 100644 index 41eba5bb7..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.func.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/MagneticLens.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - MagneticLens.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:204247.6 %
Date:2024-04-08 14:58:22Functions:4666.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLensC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa12MagneticLensC2Eh3
_ZN7crpropa12MagneticLensD2Ev3
_ZN7crpropa8LensPartC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd3
_ZN7crpropa8LensPartC2Ev0
_ZN7crpropa8LensPartD2Ev3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html b/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html deleted file mode 100644 index 1a6c474df..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/MagneticLens.h.gcov.html +++ /dev/null @@ -1,352 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/MagneticLens.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - MagneticLens.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:204247.6 %
Date:2024-04-08 14:58:22Functions:4666.7 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : //----------------------------------------------------------------------
-       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
-       3             : // a parametrized simulation engine for cosmic rays.
-       4             : //
-       5             : // Copyright (C) 2011   Martin Erdmann, Peter Schiffer, Tobias Winchen
-       6             : //                                                                               RWTH Aachen University, Germany
-       7             : // Contact: winchen@physik.rwth-aachen.de
-       8             : //
-       9             : //      This program is free software: you can redistribute it and/or
-      10             : //      modify it under the terms of the GNU General Public License as
-      11             : //      published by the Free Software Foundation, either version 3 of
-      12             : //      the License, or (at your option) any later version.
-      13             : //
-      14             : //      This program is distributed in the hope that it will be useful,
-      15             : //      but WITHOUT ANY WARRANTY; without even the implied warranty of
-      16             : //      MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.    See the
-      17             : //      GNU General Public License for more details.
-      18             : //
-      19             : //      You should have received a copy of the GNU General Public License
-      20             : //      along with this program. If not, see <http://www.gnu.org/licenses/>.
-      21             : //----------------------------------------------------------------------
-      22             : 
-      23             : #ifndef MAGNETICLENS_HH
-      24             : #define MAGNETICLENS_HH
-      25             : 
-      26             : #include "crpropa/magneticLens/ModelMatrix.h"
-      27             : #include "crpropa/magneticLens/Pixelization.h"
-      28             : #include "crpropa/Units.h"
-      29             : #include "crpropa/Vector3.h"
-      30             : 
-      31             : #include <vector>
-      32             : #include <string>
-      33             : #include <stdexcept>
-      34             : #include <fstream>
-      35             : #include <sstream>
-      36             : #include <iostream>
-      37             : #include <stdint.h>
-      38             : 
-      39             : 
-      40             : namespace crpropa
-      41             : {
-      42             : 
-      43             : /// Holds one matrix for the lens and information about the rigidity range
-      44             : class LensPart
-      45             : {
-      46             :         string _filename;
-      47             :         double _rigidityMin;
-      48             :         double _rigidityMax;
-      49             :         ModelMatrixType M;
-      50             :         double _maximumSumOfColumns;
-      51             :         bool _maximumSumOfColumns_calculated;
-      52             : 
-      53             : public:
-      54           0 :         LensPart()
-      55           0 :         {
-      56           0 :         }
-      57             :         /// File containing the matrix to be used in the range rigidityMin,
-      58             :         /// rigidityMax in Joule
-      59           3 :         LensPart(const std::string &filename, double rigidityMin, double rigidityMax) :
-      60           3 :                         _filename(filename), _rigidityMin(rigidityMin), _rigidityMax(rigidityMax), _maximumSumOfColumns_calculated(
-      61           3 :                                         false), _maximumSumOfColumns(0)
-      62             :         {
-      63           3 :         }
-      64             : 
-      65           3 :         ~LensPart()
-      66             :         {
-      67           3 :         }
-      68             : 
-      69             :         /// Loads the matrix from file
-      70             :         void loadMatrixFromFile()
-      71             :         {
-      72           0 :                 deserialize(_filename, M);
-      73           0 :         }
-      74             : 
-      75             :         /// Returns the filename of the matrix
-      76             :         const std::string& getFilename()
-      77             :         {
-      78             :                 return _filename;
-      79             :         }
-      80             : 
-      81             :         /// Calculates the maximum of the sums of columns for the matrix
-      82             :         double getMaximumOfSumsOfColumns()
-      83             :         {
-      84           0 :                 if (!_maximumSumOfColumns_calculated)
-      85             :                 { // lazy calculation of maximum
-      86           0 :                         _maximumSumOfColumns = maximumOfSumsOfColumns(M);
-      87           0 :                         _maximumSumOfColumns_calculated = true;
-      88             :                 }
-      89           0 :                 return _maximumSumOfColumns;
-      90             :         }
-      91             : 
-      92             :         /// Returns the minimum of the rigidity range for the lenspart in eV
-      93             :         double getMinimumRigidity()
-      94             :         {
-      95       12293 :                 return _rigidityMin / eV;
-      96             :         }
-      97             : 
-      98             :         /// Returns the maximum of the rigidity range for the lenspart in eV
-      99             :         double getMaximumRigidity()
-     100             :         {
-     101       12292 :                 return _rigidityMax / eV;
-     102             :         }
-     103             : 
-     104             :         /// Returns the modelmatrix
-     105             :         ModelMatrixType& getMatrix()
-     106             :         {
-     107           0 :                 return M;
-     108             :         }
-     109             : 
-     110             :         /// Sets the modelmatrix
-     111             :         void setMatrix(const ModelMatrixType& m)
-     112             :         {
-     113           3 :                 M = m;
-     114           0 :         }
-     115             : 
-     116             : 
-     117             : };
-     118             : 
-     119             : /// Function to calculate the mean deflection [rad] of the matrix M, given a pixelization
-     120             : //double calculateMeanDeflection(const ModelMatrix &M,
-     121             : //              const Pixelization &pixelization)
-     122             : //{
-     123             : //      double totalDeflection = 0;
-     124             : //      double weightSum = 0;
-     125             : //      for (const_i2_t it1 = M.begin2(); it1 != (M.end2()); it1++)
-     126             : //      {
-     127             : //              for (const_i1_t it2 = it1.begin(); it2 != it1.end(); it2++)
-     128             : //              {
-     129             : //                      totalDeflection+= pixelization.angularDistance(it2.index1(),
-     130             : //                                      it2.index2()) * (*it2) ;
-     131             : //                      weightSum+= (*it2);
-     132             : //              }
-     133             : //      }
-     134             : //      return totalDeflection / weightSum;
-     135             : //}
-     136             : 
-     137             : typedef std::vector<LensPart*>::iterator LensPartIter;
-     138             : typedef std::vector<LensPart*>::const_iterator const_LensPartIter;
-     139             : 
-     140             : /**
-     141             :  * \addtogroup MagneticLenses 
-     142             :  * @{
-     143             :  */
-     144             : 
-     145             : /// The lens for the galactic magnetic field.
-     146             : /// Note that the energies refer to protons (Z=1). To be used with other particles with a different charge number please select the rigidity accordingly.
-     147             : class MagneticLens
-     148             : {
-     149             : 
-     150             :         void updateRigidityBounds(double rigidityMin, double rigidityMax);
-     151             : 
-     152             :         /// Loads part of a lens (one matrix) from file to use it in given rigidity range.
-     153             :         void loadLensPart(const string &filename, double rigidityMin,
-     154             :                         double rigidityMax);
-     155             : 
-     156             :         // Stores the individual lenses
-     157             :         std::vector<LensPart*> _lensParts;
-     158             :         Pixelization* _pixelization;
-     159             :         // Checks Matrix, raises Errors if not ok - also generate
-     160             :         // _pixelization if called first time
-     161             :         void _checkMatrix(const ModelMatrixType &M);
-     162             :         // minimum / maximum rigidity that is covered by the lens [Joule]
-     163             :         double _minimumRigidity;
-     164             :         double _maximumRigidity;
-     165             :         static bool _randomSeeded;
-     166             :         double _norm;
-     167             : 
-     168             : public:
-     169             :         /// Default constructor
-     170           0 :         MagneticLens() :
-     171           0 :                         _pixelization(NULL), _minimumRigidity(DBL_MAX), _maximumRigidity(DBL_MIN), _norm(1)
-     172             :         {
-     173             :         }
-     174             : 
-     175             :         /// Constructs lens with predefined healpix order
-     176           3 :         MagneticLens(uint8_t healpixorder) :
-     177           3 :                         _pixelization(NULL), _minimumRigidity(DBL_MAX), _maximumRigidity(DBL_MIN)
-     178             :         {
-     179           3 :                 _pixelization = new Pixelization(healpixorder);
-     180           3 :         }
-     181             : 
-     182             :         /// Construct lens and load lens from file
-     183           0 :         MagneticLens(const string &filename) :
-     184           0 :                         _pixelization(NULL), _minimumRigidity(DBL_MAX), _maximumRigidity(DBL_MIN)
-     185             :         {
-     186           0 :                 loadLens(filename);
-     187           0 :         }
-     188             : 
-     189             :         /// Returns the pixelization used
-     190             :         const Pixelization& getPixelization() const
-     191             :         {
-     192           0 :                 return (*_pixelization);
-     193             :         }
-     194             : 
-     195             :         /// Default destructor
-     196           3 :         ~MagneticLens()
-     197             :         {
-     198           3 :                 if (_pixelization)
-     199           3 :                         delete _pixelization;
-     200           3 :                 for (std::vector<LensPart*>::iterator iter = _lensParts.begin();
-     201           6 :                                 iter != _lensParts.end(); iter++)
-     202             :                 {
-     203           3 :                         delete (*iter);
-     204             :                 }
-     205             :                 _lensParts.clear();
-     206           3 :         }
-     207             : 
-     208             :         /// Try to transform the comsic ray to a new direction.
-     209             :         /// Returns false and does not change phi and theta if the cosmic ray is
-     210             :         /// lost due to conservation of cosmic ray flux.
-     211             :         /// Rigidity is given in Joule, phi and theta in rad
-     212             :         bool transformCosmicRay(double rigidity, double& phi, double& theta);
-     213             : 
-     214             :         /// Tries transform a cosmic ray with momentum vector p
-     215             :         bool transformCosmicRay(double rigidity, Vector3d &p);
-     216             : 
-     217             :         /// transforms the model array assuming that model points to an array of the
-     218             :         /// correct size. Rigidity is given in Joule
-     219             :         void transformModelVector(double* model, double rigidity) const;
-     220             : 
-     221             :         /// Loads M as part of a lens and use it in given rigidity range with
-     222             :         /// rigidities given in Joule
-     223             :         void setLensPart(const ModelMatrixType &M, double rigidityMin, double rigidityMax);
-     224             : 
-     225             :         /// Loads a lens from a given file, containing lines like
-     226             :         /// lensefile.MLDAT rigidityMin rigidityMax
-     227             :         /// rigidities are given in logarithmic units [log10(E / eV)]
-     228             :         void loadLens(const string &filename);
-     229             : 
-     230             :         /// Normalizes the lens parts to the maximum of sums of columns of
-     231             :         /// every lenspart. By doing this, the lens won't distort the spectrum
-     232             :         void normalizeLens();
-     233             : 
-     234             :         /// Normalizes the lens parts individually. Normalized this way, the
-     235             :         /// lens generally distorts the spectrum of the sources, but deflects
-     236             :         /// the UHECR more efficiently.
-     237             :         void normalizeLensparts();
-     238             : 
-     239             :         /// Checks if rigidity [Joule] is covered by lens
-     240             :         bool rigidityCovered(double rigidity) const;
-     241             : 
-     242             :         /// Normalizes all matrix columns - the lens will then create fake
-     243             :         /// anisotropies, but won't drop particles
-     244             :         void normalizeMatrixColumns();
-     245             : 
-     246             :         /// Returns minimum rigidity covered by lens, in eV
-     247             :         double getMinimumRigidity() const
-     248             :         {
-     249           0 :                 return _minimumRigidity / eV;
-     250             :         }
-     251             :         /// Returns maximum rigidity covered by lens, in eV
-     252             :         double getMaximumRigidity() const
-     253             :         {
-     254           0 :                 return _maximumRigidity / eV;
-     255             :         }
-     256             : 
-     257             :         //      returns the norm used for the lenses
-     258             :         double getNorm()
-     259             :         {
-     260           0 :                 return _norm;
-     261             :         }
-     262             : 
-     263             :         /// Returns iterator to the lens part with rigidity Joule
-     264             :         LensPart* getLensPart(double rigidity) const;
-     265             : 
-     266             :         /// Returns all lens parts
-     267             :         const std::vector<LensPart*>& getLensParts() const
-     268             :         {
-     269           0 :                 return _lensParts;
-     270             :         }
-     271             : };
-     272             : 
-     273             : /** @}*/
-     274             : } // namespace
-     275             : 
-     276             : #endif // MAGNETICLENS_HH
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html deleted file mode 100644 index 907daed16..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/ParticleMapsContainer.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - ParticleMapsContainer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21020.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer9getWeightEid0
_ZN7crpropa21ParticleMapsContainerC2Edd2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html deleted file mode 100644 index 1197e3fa1..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/ParticleMapsContainer.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - ParticleMapsContainer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21020.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer9getWeightEid0
_ZN7crpropa21ParticleMapsContainerC2Edd2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html b/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html deleted file mode 100644 index b652fe992..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/ParticleMapsContainer.h.gcov.html +++ /dev/null @@ -1,221 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/ParticleMapsContainer.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - ParticleMapsContainer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21020.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_PARTICLEMAPSCONTAINER_HH
-       2             : #define CRPROPA_PARTICLEMAPSCONTAINER_HH
-       3             : 
-       4             : #include <map>
-       5             : #include <vector>
-       6             : #include "crpropa/magneticLens/Pixelization.h"
-       7             : #include "crpropa/magneticLens/MagneticLens.h"
-       8             : 
-       9             : #include "crpropa/Vector3.h"
-      10             : 
-      11             : namespace crpropa {
-      12             : /**
-      13             :  * \addtogroup MagneticLenses 
-      14             :  * @{
-      15             :  */
-      16             : 
-      17             : /** 
-      18             :  @class ParticleMapsContainer
-      19             :  @brief A container for particle maps
-      20             : 
-      21             :  The maps are stored with discrete energies on a logarithmic scale. The
-      22             :  default energy width is 0.02 with an energy bin from 10**17.99 - 10**18.01 eV.
-      23             :  */
-      24             : class ParticleMapsContainer {
-      25             : private:
-      26             :         std::map<int, std::map <int, double*> > _data;
-      27             :         Pixelization _pixelization;
-      28             :         double _deltaLogE;
-      29             :         double _bin0lowerEdge;
-      30             : 
-      31             :         // get the bin number of the energy
-      32             :         int energy2Idx(double energy) const;
-      33             :         double idx2Energy(int idx) const;
-      34             : 
-      35             :         // weights of the particles
-      36             :         double _sumOfWeights;
-      37             :         std::map<int, double > _weightsPID;
-      38             :         std::map<int, map<int, double> > _weights_pidEnergy;
-      39             : 
-      40             :         // lazy update of weights
-      41             :         bool _weightsUpToDate;
-      42             :         void _updateWeights();
-      43             : 
-      44             : public:
-      45             :         /** Constructor.
-      46             :          @param deltaLogE               width of logarithmic energy bin [in eV]
-      47             :          @param bin0lowerEdge   logarithm of energy of the lower edge of first bin [in log(eV)]
-      48             :          */
-      49           2 :         ParticleMapsContainer(double deltaLogE = 0.02, double bin0lowerEdge = 17.99) : _deltaLogE(deltaLogE), _bin0lowerEdge(bin0lowerEdge), _pixelization(6), _weightsUpToDate(false), _sumOfWeights(0) {
-      50           2 :         }
-      51             :         /** Destructor.
-      52             :          */
-      53             :         ~ParticleMapsContainer();
-      54             : 
-      55             :         size_t getNumberOfPixels() {
-      56           0 :                 return _pixelization.getNumberOfPixels();
-      57             :         }
-      58             : 
-      59             :         /** Get the map for the particleId with the given energy.
-      60             :          @param particleId              id of the particle following the PDG numbering scheme
-      61             :          @param energy                  the energy of the particle [in Joules]
-      62             :          @returns The map for a given particleId with a given energy
-      63             :          */
-      64             :         double *getMap(const int particleId, double energy);
-      65             : 
-      66             :         /** Adds a particle to the map container.
-      67             :          @param particleId                      id of the particle following the PDG numbering scheme
-      68             :          @param energy                          the energy of the particle [in Joules]
-      69             :          @param galacticLongitude       galactic longitude [radians]
-      70             :          @param galacticLatitude        galactic latitude [radians]
-      71             :          @param weight                          relative weight for the specific particle
-      72             :         */
-      73             :         void addParticle(const int particleId, double energy, double galacticLongitude, double galacticLatitude, double weight = 1);
-      74             :         /** Adds a particle to the map container.
-      75             :          @param particleId                      id of the particle following the PDG numbering scheme
-      76             :          @param energy                          the energy of the particle [in Joules]
-      77             :          @param v                                       vector containing the arrival directions of a particle
-      78             :          @param weight                          relative weight for the specific particle
-      79             :         */
-      80             :         void addParticle(const int particleId, double energy, const Vector3d &v, double weight = 1);
-      81             : 
-      82             :         /** Get all particle ids in the map.
-      83             :          @returns Vector of all ids.
-      84             :          */
-      85             :         std::vector<int> getParticleIds();
-      86             : 
-      87             :         /** Get energies in map.
-      88             :          @param pid     id of the particle following the PDG numbering scheme
-      89             :          @returns Energies are returned in units of eV (unlike in other CRPropa modules) for performance reasons
-      90             :          */
-      91             :         std::vector<double> getEnergies(int pid);
-      92             : 
-      93             :         void applyLens(MagneticLens &lens);;
-      94             : 
-      95             :         /** Get random particles from map.
-      96             :          The arguments are the vectors where the information will be stored.
-      97             :          @param N                                       number of particles to be selected
-      98             :          @param particleId                      id of the particle following the PDG numbering scheme
-      99             :          @param energy                          energy of interest [in eV]
-     100             :          @param galacticLongitudes      longitude in the interval [-pi, pi] [in radians]
-     101             :          @param galacticLatitudes       latitude in the interval [-pi/2, pi/2] [in radians]
-     102             :          */
-     103             :         void getRandomParticles(size_t N, vector<int> &particleId,
-     104             :                 vector<double> &energy, vector<double> &galacticLongitudes,
-     105             :                 vector<double> &galacticLatitudes);
-     106             : 
-     107             :         /** Places a particle with given id and energy according to the  probability maps. 
-     108             :          @param pid                                     id of the particle following the PDG numbering scheme
-     109             :          @param energy                          energy of interest [in eV]
-     110             :          @param galacticLongitude       longitude in the interval [-pi, pi] [in radians]
-     111             :          @param galacticLatitude        latitude in the interval [-pi/2, pi/2] [in radians]
-     112             :          @returns Returns false if operation not possible; true otherwise.
-     113             :          */
-     114             :         bool placeOnMap(int pid, double energy, double &galacticLongitude, double &galacticLatitude);
-     115             : 
-     116             :         /** Force weight update prior to getting random particles. 
-     117             :          Only necessary when reusing pointer to maps after calculating weights.
-     118             :         */
-     119             :         void forceWeightUpdate();
-     120             : 
-     121             :         /** Get sum of weights of the maps.
-     122             :          @returns Sum of all weights.
-     123             :          */
-     124             :         double getSumOfWeights() {
-     125           0 :                 if (!_weightsUpToDate)
-     126           0 :                         _updateWeights();
-     127           0 :                 return _sumOfWeights;
-     128             :         }
-     129             : 
-     130             :         /** Get weight for a given particle and energy
-     131             :          @param pid                                     id of the particle following the PDG numbering scheme
-     132             :          @param energy                          energy of interest [in eV]
-     133             :          @returns Weight for the chosen particle and energy.
-     134             :          */
-     135           0 :         double getWeight(int pid, double energy) {
-     136           0 :                 if (!_weightsUpToDate)
-     137           0 :                         _updateWeights();
-     138           0 :                 return _weights_pidEnergy[pid][energy2Idx(energy)];
-     139             :         }
-     140             : };
-     141             : /** @}*/
-     142             : 
-     143             : } // namespace crpropa
-     144             : 
-     145             : #endif // CRPROPA_PARTICLEMAPSCONTAINER_HH
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html deleted file mode 100644 index 728ad5e1e..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func-sort-c.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/Pixelization.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - Pixelization.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81844.4 %
Date:2024-04-08 14:58:22Functions:1333.3 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization15getPixelsInConeEdddRSt6vectorIiSaIiEE0
_ZN7crpropa12PixelizationC2Ev0
_ZN7crpropa12PixelizationC2Eh10
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html deleted file mode 100644 index cc5239816..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.func.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/Pixelization.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - Pixelization.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81844.4 %
Date:2024-04-08 14:58:22Functions:1333.3 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization15getPixelsInConeEdddRSt6vectorIiSaIiEE0
_ZN7crpropa12PixelizationC2Eh10
_ZN7crpropa12PixelizationC2Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html b/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html deleted file mode 100644 index 370ed122b..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/Pixelization.h.gcov.html +++ /dev/null @@ -1,217 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens/Pixelization.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLens - Pixelization.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:81844.4 %
Date:2024-04-08 14:58:22Functions:1333.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : //----------------------------------------------------------------------
-       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
-       3             : // a parametrized simulation engine for cosmic rays.
-       4             : //
-       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
-       6             : //                     RWTH Aachen University, Germany
-       7             : // Contact: winchen@physik.rwth-aachen.de
-       8             : //
-       9             : //  This program is free software: you can redistribute it and/or
-      10             : //  modify it under the terms of the GNU General Public License as
-      11             : //  published by the Free Software Foundation, either version 3 of
-      12             : //  the License, or (at your option) any later version.
-      13             : //
-      14             : //  This program is distributed in the hope that it will be useful,
-      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      17             : //  GNU General Public License for more details.
-      18             : //
-      19             : //  You should have received a copy of the GNU General Public License
-      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
-      21             : //----------------------------------------------------------------------
-      22             : 
-      23             : 
-      24             : #ifndef PIXELIZATION_HH
-      25             : #define PIXELIZATION_HH
-      26             : 
-      27             : #include "healpix_base/healpix_base.h"
-      28             : #include <cmath>
-      29             : #include <stdint.h>
-      30             : 
-      31             : namespace crpropa
-      32             : {
-      33             : /**
-      34             :  * \addtogroup MagneticLenses
-      35             :  * @{
-      36             :  */
-      37             : 
-      38             : /// Helpers to makes work with Healpix smooth
-      39             : const uint8_t _nOrder_max = 13;
-      40             : const uint32_t _nPix[] =
-      41             : {
-      42             :                 48,
-      43             :                 192,
-      44             :                 768,
-      45             :                 3072,
-      46             :                 12288,
-      47             :                 49152,
-      48             :                 196608,
-      49             :                 786432,
-      50             :                 3145728,
-      51             :                 12582912,
-      52             :                 50331648,
-      53             :                 201326592,
-      54             :                 805306368
-      55             : };
-      56             : 
-      57             : /// Every communication with healpix is done through this class to avoid
-      58             : /// bugs with missmatching coordinates (and make python hooks easier)
-      59             : class Pixelization
-      60             : {
-      61             : public:
-      62           0 :         Pixelization()
-      63           0 :         {
-      64           0 :                 _healpix = new healpix::T_Healpix_Base<int>(6, healpix::RING);
-      65           0 :         }
-      66             : 
-      67             :         /// Constructor creating Pixelization with healpix order 6 (about
-      68             :         /// 50000 pixels)
-      69          10 :         Pixelization(uint8_t order)
-      70          10 :         {
-      71          10 :                 _healpix = new healpix::T_Healpix_Base<int>(order, healpix::RING);
-      72          10 :         }
-      73             : 
-      74             :         ~Pixelization()
-      75             :         {
-      76          10 :                 delete _healpix;
-      77          10 :         }
-      78             : 
-      79             :         /// Returns the number of the pixel which includes the direction (phi,theta)
-      80             :         /// phi in [-pi, pi], theta in [-pi/2, pi/2]
-      81             :         uint32_t direction2Pix(double longitude, double latitude) const;
-      82             : 
-      83             :         /// Returns the number of pixels of the pixelization
-      84             :         uint32_t nPix() const
-      85             :         {
-      86       86026 :                 return _healpix->Npix();
-      87             :         }
-      88             : 
-      89             :         /// Returns the number of pixels given by healpix order
-      90             :         static uint32_t nPix(uint8_t order);
-      91             : 
-      92             :         /// Returns the number of pixels of the pixelization
-      93             :         int getNumberOfPixels()
-      94             :         {
-      95    10317737 :                 return _healpix->Npix();
-      96             :         }
-      97             : 
-      98             :         /// Returns the order, a given pixel number corresponds to. 0 if no
-      99             :         /// match!
-     100             :         static uint8_t pix2Order(uint32_t pix);
-     101             : 
-     102             :         /// Gives the center of pixel i in longitude [rad] and latitude [rad]
-     103             :         void pix2Direction(uint32_t i, double &longitude, double &latitude) const;
-     104             : 
-     105             :         /// Calculate the angle [rad] between the vectors pointing to pixels i and j
-     106             :         double angularDistance(uint32_t i, uint32_t j) const;
-     107             : 
-     108             :         /// Returns the maximum possible pixelization order
-     109             :         uint8_t getMaxOrder() const
-     110             :         {
-     111             :                 return _nOrder_max;
-     112             :         }
-     113             : 
-     114             :   /// Returns healpix order
-     115             :   uint8_t getOrder() const
-     116             :   {
-     117           0 :     return _healpix->Order();
-     118             :   }
-     119             : 
-     120             :         void getRandomDirectionInPixel(uint32_t pixel, double &longitude, double &latitude);
-     121             : 
-     122           0 :         void getPixelsInCone(double longitude, double latitude,double radius, std::vector<int>& listpix)
-     123             :         {
-     124             :                 healpix::vec3 v;
-     125           0 :                 spherCo2Vec(longitude, latitude, v);
-     126             :                 healpix::pointing p;
-     127           0 :                 p.from_vec3(v);
-     128           0 :                 _healpix->query_disc(p, radius, listpix);
-     129           0 :         }
-     130             : 
-     131             : private:
-     132             :         void spherCo2Vec(double phi, double theta, healpix::vec3 &V) const;
-     133             :         void vec2SphereCo(double &phi , double &theta, const healpix::vec3 &V) const;
-     134             :         healpix::T_Healpix_Base<int> *_healpix;
-     135             :         static healpix::T_Healpix_Base<healpix::int64> _healpix_nest;
-     136             : };
-     137             : 
-     138             : 
-     139             : /** @}*/
-     140             : } // namespace
-     141             : #endif // PIXELIZATION_HH
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html b/doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html deleted file mode 100644 index 6f02276e0..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/index-sort-f.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:307042.9 %
Date:2024-04-08 14:58:22Functions:61154.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Pixelization.h -
44.4%44.4%
-
44.4 %8 / 1833.3 %1 / 3
ParticleMapsContainer.h -
20.0%20.0%
-
20.0 %2 / 1050.0 %1 / 2
MagneticLens.h -
47.6%47.6%
-
47.6 %20 / 4266.7 %4 / 6
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html b/doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html deleted file mode 100644 index 053630cae..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/index-sort-l.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:307042.9 %
Date:2024-04-08 14:58:22Functions:61154.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ParticleMapsContainer.h -
20.0%20.0%
-
20.0 %2 / 1050.0 %1 / 2
Pixelization.h -
44.4%44.4%
-
44.4 %8 / 1833.3 %1 / 3
MagneticLens.h -
47.6%47.6%
-
47.6 %20 / 4266.7 %4 / 6
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/magneticLens/index.html b/doc/coverageReport/include/crpropa/magneticLens/index.html deleted file mode 100644 index 279e0695b..000000000 --- a/doc/coverageReport/include/crpropa/magneticLens/index.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/magneticLens - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:307042.9 %
Date:2024-04-08 14:58:22Functions:61154.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticLens.h -
47.6%47.6%
-
47.6 %20 / 4266.7 %4 / 6
ParticleMapsContainer.h -
20.0%20.0%
-
20.0 %2 / 1050.0 %1 / 2
Pixelization.h -
44.4%44.4%
-
44.4 %8 / 1833.3 %1 / 3
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html deleted file mode 100644 index 2d2c7d39b..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Cordes.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Cordes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html deleted file mode 100644 index 8ec13117b..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Cordes.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Cordes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html deleted file mode 100644 index 0ec8b1bff..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Cordes.h.gcov.html +++ /dev/null @@ -1,121 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Cordes.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Cordes.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_CORDES_H
-       2             : #define CRPROPA_CORDES_H
-       3             : 
-       4             : #include "crpropa/massDistribution/Density.h"
-       5             : 
-       6             : #include <cmath>
-       7             : #include <string>
-       8             : 
-       9             : namespace crpropa {
-      10             : /**
-      11             :         @class Cordes
-      12             :         @brief Cylindrical symetrical model of the density of ionised hydrogen (HII) of the Milky Way
-      13             :         Cordes et al., 1991, Nature 353,737
-      14             :         */
-      15           1 : class Cordes: public Density {
-      16             : private:
-      17             :         // DO NOT CHANGE model type!
-      18             :         bool isforHI = false;
-      19             :         bool isforHII = true;
-      20             :         bool isforH2 = false;
-      21             : 
-      22             : public:
-      23             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      24             :          @return density in parts/m^3 */
-      25             :         double getDensity(const Vector3d &position) const;
-      26             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      27             :          @return density of ionised hydrogen in parts/m^3, equal getDensity thus no other type is included for Cordes */
-      28             :         double getHIIDensity(const Vector3d &position) const;
-      29             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      30             :          @return density of nucleons in parts/m^3, equal getDensity thus only HII is included for Cordes */
-      31             :         double getNucleonDensity(const Vector3d &position) const;
-      32             : 
-      33             :         /** @return activation status of HI */
-      34             :         bool getIsForHI();
-      35             :         /** @return activation status of HII */
-      36             :         bool getIsForHII();
-      37             :         /** @return activation status of H2 */
-      38             :         bool getIsForH2();
-      39             : 
-      40             :         std::string getDescription();
-      41             : };
-      42             : 
-      43             : }  // namespace crpropa
-      44             : 
-      45             : #endif  // CRPROPA_CORDES_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html deleted file mode 100644 index 61d743401..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Density.h.func-sort-c.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Density.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Density.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Density10getIsForH2Ev0
_ZN7crpropa7Density10getIsForHIEv0
_ZN7crpropa7Density11getIsForHIIEv0
_ZN7crpropa7Density14getDescriptionB5cxx11Ev0
_ZN7crpropa7DensityD0Ev0
_ZN7crpropa7DensityD2Ev0
_ZNK7crpropa7Density10getDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getH2DensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getHIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density13getHIIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density17getNucleonDensityERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html deleted file mode 100644 index f9ed0dff3..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Density.h.func.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Density.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Density.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Density10getIsForH2Ev0
_ZN7crpropa7Density10getIsForHIEv0
_ZN7crpropa7Density11getIsForHIIEv0
_ZN7crpropa7Density14getDescriptionB5cxx11Ev0
_ZN7crpropa7DensityD0Ev0
_ZN7crpropa7DensityD2Ev0
_ZNK7crpropa7Density10getDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getH2DensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density12getHIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density13getHIIDensityERKNS_7Vector3IdEE0
_ZNK7crpropa7Density17getNucleonDensityERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html deleted file mode 100644 index 5b9e5404b..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Density.h.gcov.html +++ /dev/null @@ -1,134 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Density.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Density.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_DENSITY_H
-       2             : #define CRPROPA_DENSITY_H
-       3             : 
-       4             : #include "crpropa/Units.h"
-       5             : #include "crpropa/Vector3.h"
-       6             : #include "crpropa/Referenced.h"
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10             : /**
-      11             :  @class Density
-      12             :  @brief Abstract base class for target densities
-      13             :  */
-      14           0 : class Density: public Referenced {
-      15             : public:
-      16           0 :         virtual ~Density() {
-      17           0 :         }
-      18             : 
-      19           0 :         virtual double getDensity(const Vector3d &position) const {  // sum of all densities
-      20           0 :                 return 0;
-      21             :         }
-      22             : 
-      23           0 :         virtual double getHIDensity(const Vector3d &position) const {
-      24           0 :                 return 0;
-      25             :         }
-      26             : 
-      27           0 :         virtual double getHIIDensity(const Vector3d &position) const {
-      28           0 :                 return 0;
-      29             :         }
-      30             : 
-      31           0 :         virtual double getH2Density(const Vector3d &position) const {
-      32           0 :                 return 0;
-      33             :         }
-      34             : 
-      35           0 :         virtual double getNucleonDensity(const Vector3d &position) const {  // sum of nucleons (H2 with factor 2)
-      36           0 :                 return 0;
-      37             :         }
-      38             : 
-      39           0 :         virtual bool getIsForHI() {
-      40           0 :                 return false;
-      41             :         }
-      42             : 
-      43           0 :         virtual bool getIsForHII() {
-      44           0 :                 return false;
-      45             :         }
-      46             : 
-      47           0 :         virtual bool getIsForH2() {
-      48           0 :                 return false;
-      49             :         }
-      50             : 
-      51           0 :         virtual std::string getDescription() {
-      52           0 :                 return "Abstract Density Module\n";
-      53             :         }
-      54             : };
-      55             : 
-      56             : }  // namespace crpropa
-      57             : 
-      58             : #endif  // CRPROPA_DENSITY_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html deleted file mode 100644 index 7bb1afb24..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Ferriere.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Ferriere.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html deleted file mode 100644 index 9357468f5..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Ferriere.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Ferriere.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html deleted file mode 100644 index f69801f4a..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Ferriere.h.gcov.html +++ /dev/null @@ -1,153 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Ferriere.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Ferriere.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_FERRIERE_H
-       2             : #define CRPROPA_FERRIERE_H
-       3             : 
-       4             : #include "crpropa/massDistribution/Density.h"
-       5             : 
-       6             : #include <cmath>
-       7             : #include <string>
-       8             : 
-       9             : namespace crpropa {
-      10             : /**
-      11             :  @class Ferriere
-      12             :  @brief model of the distribution of hydrogen in the Milky Way
-      13             :   Here in model Ferriere 2007
-      14             :   seperated in 2 regions (inner, outer). The border is for R=3 kpc in galactocentric radius.
-      15             :   model is discribed in
-      16             : outer: ApJ, 497, 759
-      17             : inner:  arxiv:  astro-ph/0702532
-      18             : */
-      19           2 : class Ferriere: public Density {
-      20             : private:
-      21             :         // standard for all types of distribution
-      22             :         bool isforHI = true;
-      23             :         bool isforHII = true;
-      24             :         bool isforH2 = true;
-      25             :         double Rsun = 8.5 * kpc;  // distance sun-galactic center
-      26             : 
-      27             : public:
-      28             :         /** Coordinate transformation for the CentralMolecularZone region. Rotation arround z-axis such that X is the major axis and Y is the minor axis
-      29             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      30             :         @return position in local coordinates for the CMZ region
-      31             :         */
-      32             :         Vector3d CMZTransformation(const Vector3d &position) const;
-      33             :         
-      34             :         /** Coordinate transformation for the galactic bulge disk region in galactic center. Rotation arround the x-axis, the y'-axis and the x''-axis. Difened with X along the major axis, Y along the minor axis and Z along the northern normal
-      35             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      36             :         @return position in local coordinates for the GB disk region
-      37             :         */
-      38             :         Vector3d DiskTransformation(const Vector3d &position) const;
-      39             : 
-      40             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      41             :          @return density in parts/m^3, only acitvated parts are summed up */
-      42             :         double getDensity(const Vector3d &position) const;
-      43             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      44             :          @return density of atomic hydrogen in parts/m^3 */
-      45             :         double getHIDensity(const Vector3d &position) const;
-      46             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      47             :          @return density of ionised hydrogen in parts/m^3 */
-      48             :         double getHIIDensity(const Vector3d &position) const;
-      49             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      50             :          @return density of molecular hydrogen in parts/m^3 */
-      51             :         double getH2Density(const Vector3d &position) const;
-      52             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      53             :          @return nucleon density in parts/m^3, only activated parts are summed up and H2 is weighted twice */
-      54             :         double getNucleonDensity(const Vector3d &position) const;
-      55             : 
-      56             :         /** changes activation status for atomic hydrogen */
-      57             :         void setIsForHI(bool HI);
-      58             :         /** changes activation status for ionised hydrogen */
-      59             :         void setIsForHII(bool HII);
-      60             :         /** changes activation status for molecular hydrogen */
-      61             :         void setIsForH2(bool H2);
-      62             : 
-      63             :         /** @return activation status for atomic hydrogen */
-      64             :         bool getIsForHI();
-      65             :         /** @return activation status for ionised hydrogen */
-      66             :         bool getIsForHII();
-      67             :         /** @return activation status for molecular hydrogen */
-      68             :         bool getIsForH2();
-      69             : 
-      70             :         std::string getDescription();
-      71             : };
-      72             : 
-      73             : }  // namespace crpropa
-      74             : 
-      75             : #endif  // CRPROPA_FERRIERE_H
-      76             : 
-      77             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html deleted file mode 100644 index f746939ad..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Massdistribution.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Massdistribution.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html deleted file mode 100644 index af406a149..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Massdistribution.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Massdistribution.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html deleted file mode 100644 index a34abbae2..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Massdistribution.h.gcov.html +++ /dev/null @@ -1,212 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Massdistribution.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Massdistribution.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_MASSDISTRIBUTION_H
-       2             : #define CRPROPA_MASSDISTRIBUTION_H
-       3             : 
-       4             : #include "crpropa/massDistribution/Density.h"
-       5             : #include "crpropa/Vector3.h"
-       6             : #include "crpropa/Grid.h"
-       7             : 
-       8             : #include "kiss/logger.h"
-       9             : 
-      10             : #include <vector>
-      11             : 
-      12             : namespace crpropa {
-      13             : 
-      14             : /**
-      15             :  @class DensityList
-      16             :  @brief Superposition of density models.
-      17             :  The addDensity function adds a new density to the list.
-      18             :  The getDensity function handles the activated types in loaded densities, whereas get(type)Density disregards the activation state.
-      19             : */
-      20           2 : class DensityList: public Density {
-      21             : private:
-      22             :         std::vector<ref_ptr<Density> > DensityList ;
-      23             : 
-      24             : public:
-      25             :         /** Add new density to list.
-      26             :          @param density density to add
-      27             :         */
-      28             :         void addDensity(ref_ptr<Density> density);
-      29             : 
-      30             :         /** Get density at a given position.
-      31             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      32             :          @returns Density in particles/m^3, sum up densities from added densities 
-      33             :         */
-      34             :         double getDensity(const Vector3d &position) const;
-      35             :         /** Get HI density at a given position.
-      36             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      37             :          @returns Density of HI at given position in particles/m^3, sum up all HI densities from added densities
-      38             :          */
-      39             :         double getHIDensity(const Vector3d &position) const;
-      40             :         /** Get HII density at a given position.
-      41             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      42             :          @returns Density of HII at given position in particles/m^3, sum up all HII densities from added densities 
-      43             :          */
-      44             :         double getHIIDensity(const Vector3d &position) const;
-      45             :         /** Get H2 density at a given position.
-      46             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      47             :          @returns Density of H2 at given position in particles/m^3, sum up all H2 densities from added densities 
-      48             :          */
-      49             :         double getH2Density(const Vector3d &position) const;
-      50             :         /** Get the density of nucleons.
-      51             :          This is the number of nucleons per volume, summed up all activated density and weight molecular hydrogyen twice
-      52             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      53             :          @returns Density of nucleons at given position in particles/m^3, sum up all nucleon densities from added densities 
-      54             :          */
-      55             :         double getNucleonDensity(const Vector3d &position) const;
-      56             : 
-      57             :         std::string getDescription();
-      58             : };
-      59             : 
-      60             : /**
-      61             :  @class DensityGrid
-      62             :  @brief Wrapper to use a Grid1f for a density
-      63             : 
-      64             :  The DensityGrid uses a given grid for the chosen density type. More than one type can be chosen to follow the same distribution.
-      65             :  If no type is chosen a warning will be raised and all densities are 0.
-      66             : */
-      67           4 : class DensityGrid: public Density {
-      68             : private: 
-      69             :         ref_ptr<Grid1f> grid; //< Grid with data
-      70             :         bool isForHI, isForHII, isForH2; 
-      71             :         void checkAndWarn(); //< raise a warning if all density types are deactivated.
-      72             : 
-      73             : public:
-      74             :         DensityGrid(ref_ptr<Grid1f> grid, bool isForHI = false, bool isForHII = false, bool isForH2 = false);
-      75             :         
-      76             :         /** Get HI density at a given position.
-      77             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      78             :          @returns Density of HI at given position in particles/m^3, sum up all HI densities from added densities
-      79             :          */
-      80             :         double getHIDensity(const Vector3d &position) const;
-      81             :         
-      82             :         /** Get HII density at a given position.
-      83             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      84             :          @returns Density of HII at given position in particles/m^3, sum up all HII densities from added densities 
-      85             :          */
-      86             :         double getHIIDensity(const Vector3d &position) const;
-      87             :         
-      88             :         /** Get H2 density at a given position.
-      89             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      90             :          @returns Density of H2 at given position in particles/m^3, sum up all H2 densities from added densities 
-      91             :          */
-      92             :         double getH2Density(const Vector3d &position) const;
-      93             : 
-      94             :         /** Get density at a given position.
-      95             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-      96             :          @returns Density in particles/m^3, sum up densities from added densities 
-      97             :         */
-      98             :         double getDensity(const Vector3d &position) const;
-      99             :         
-     100             :         /** Get the density of nucleons.
-     101             :          This is the number of nucleons per volume, summed up all activated density and weight molecular hydrogyen twice
-     102             :          @param position position in Galactic coordinates with Earth at (-8.5 kpc, 0, 0)
-     103             :          @returns Density of nucleons at given position in particles/m^3, sum up all nucleon densities from added densities 
-     104             :          */
-     105             :         double getNucleonDensity(const Vector3d &position) const;
-     106             : 
-     107             :         bool getIsForHI();
-     108             :         bool getIsForHII();
-     109             :         bool getIsForH2();
-     110             : 
-     111             :         /* set if the density is for HI type. 
-     112             :          @param b if True the density is used for HI
-     113             :         */
-     114             :         void setIsForHI(bool b);
-     115             : 
-     116             :         /* set if the density is for HII type. 
-     117             :          @param b if True the density is used for HII
-     118             :         */
-     119             :         void setIsForHII(bool b);
-     120             : 
-     121             :         /* set if the density is for H2 type. 
-     122             :          @param b if True the density is used for H2
-     123             :         */
-     124             :         void setIsForH2(bool b);
-     125             :         
-     126             :         /* Change the grid for the density
-     127             :          @param grid (Grid1f) new grid for the density. 
-     128             :         */
-     129             :         void setGrid(ref_ptr<Grid1f> grid);
-     130             : 
-     131             :         std::string getDescription();
-     132             : };
-     133             : 
-     134             : }  // namespace crpropa
-     135             : 
-     136             : #endif  // CRPROPA_MASSDISTRIBUTION_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html deleted file mode 100644 index 6bb472b29..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Nakanishi.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Nakanishi.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html deleted file mode 100644 index 4a26d7662..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Nakanishi.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Nakanishi.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html b/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html deleted file mode 100644 index b3dc30cd8..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/Nakanishi.h.gcov.html +++ /dev/null @@ -1,150 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution/Nakanishi.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistribution - Nakanishi.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_NAKANISHI_H
-       2             : #define CRPROPA_NAKANISHI_H
-       3             : 
-       4             : #include "crpropa/massDistribution/Density.h"
-       5             : 
-       6             : #include <cmath>
-       7             : #include <string>
-       8             : 
-       9             : namespace crpropa {
-      10             : /**
-      11             :  @class Nakanishi
-      12             :  @brief Cylindrical symetrical model of the density distribution of the Milky Way for atomic (HI) and molecular (H2) hydrogen
-      13             :         Modell for HI arXiv:astro-ph/0304338
-      14             :         Modell for H2 arxiv:astro-ph/0610769
-      15             :         fit of the models given in arXiv:1607.07886
-      16             : */
-      17           1 : class Nakanishi: public Density {
-      18             : private:
-      19             :         bool isforHI = true;
-      20             :         bool isforHII = false;
-      21             :         bool isforH2 = true;
-      22             : 
-      23             : public:
-      24             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      25             :          @returns density in parts/m^3, only activated parts are summed up */
-      26             :         double getDensity(const Vector3d &position) const;
-      27             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      28             :          @returns density of atomic hydrogen in parts/m^3 */
-      29             :         double getHIDensity(const Vector3d &position) const;
-      30             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      31             :          @returns density of molecular hydrogen in parts/m^3 */
-      32             :         double getH2Density(const Vector3d &position) const;
-      33             :         /** @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      34             :          @returns nucleon density in parts/m^3, only activated parts are summed up and H2 is weighted twice */
-      35             :         double getNucleonDensity(const Vector3d &position) const;
-      36             : 
-      37             :         /** the scale height over the galactic plane of atomic hydrogen is fitted by polynom of degree 3
-      38             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      39             :         @returns scale height at given position */
-      40             :         double getHIScaleheight(const Vector3d &position)const;
-      41             :         /** the plane density is fittet by two exponential components with e^-R and e^-(R^2)
-      42             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      43             :         @returns plane density in parts/m^3 */
-      44             :         double getHIPlanedensity(const Vector3d &position)const;
-      45             : 
-      46             :         /** the scale height over the galactic plane of molecular hydrogen is fitted by exponential function
-      47             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      48             :         @returns scale height at given position */
-      49             :         double getH2Scaleheight(const Vector3d &position)const;
-      50             :         /** the plane density is fitted by two exponential components
-      51             :         @param position position in galactic coordinates with Earth at (-8.5kpc, 0, 0)
-      52             :         @returns plane density in parts/m^3 */
-      53             :         double getH2Planedensity(const Vector3d &position)const;
-      54             : 
-      55             :         /** changes activation status for atomic hydrogen */
-      56             :         void setIsForHI(bool HI);
-      57             :         /** changes activation status for molecular hydrogen */
-      58             :         void setIsForH2(bool H2);
-      59             : 
-      60             :         /** @returns activation status for atomic hydrogen */
-      61             :         bool getIsForHI();
-      62             :         /** @returns activation status for ionised hydrogen */
-      63             :         bool getIsForHII();
-      64             :         /** @returns activation status for molecular hydrogen */
-      65             :         bool getIsForH2();
-      66             :         std::string getDescription();
-      67             : };
-      68             : 
-      69             : }  // namespace crpropa
-      70             : 
-      71             : #endif  // CRPROPA_NAKANISHI_H
-      72             : 
-      73             : 
-      74             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html b/doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html deleted file mode 100644 index 3be7402d0..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/index-sort-f.html +++ /dev/null @@ -1,133 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:52619.2 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Density.h -
0.0%
-
0.0 %0 / 210.0 %0 / 11
Nakanishi.h -
100.0%
-
100.0 %1 / 1-0 / 0
Cordes.h -
100.0%
-
100.0 %1 / 1-0 / 0
Ferriere.h -
100.0%
-
100.0 %1 / 1-0 / 0
Massdistribution.h -
100.0%
-
100.0 %2 / 2-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html b/doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html deleted file mode 100644 index 5bc81ca8e..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/index-sort-l.html +++ /dev/null @@ -1,133 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:52619.2 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Density.h -
0.0%
-
0.0 %0 / 210.0 %0 / 11
Nakanishi.h -
100.0%
-
100.0 %1 / 1-0 / 0
Cordes.h -
100.0%
-
100.0 %1 / 1-0 / 0
Ferriere.h -
100.0%
-
100.0 %1 / 1-0 / 0
Massdistribution.h -
100.0%
-
100.0 %2 / 2-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/massDistribution/index.html b/doc/coverageReport/include/crpropa/massDistribution/index.html deleted file mode 100644 index b39e47962..000000000 --- a/doc/coverageReport/include/crpropa/massDistribution/index.html +++ /dev/null @@ -1,133 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/massDistribution - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:52619.2 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Cordes.h -
100.0%
-
100.0 %1 / 1-0 / 0
Density.h -
0.0%
-
0.0 %0 / 210.0 %0 / 11
Ferriere.h -
100.0%
-
100.0 %1 / 1-0 / 0
Massdistribution.h -
100.0%
-
100.0 %2 / 2-0 / 0
Nakanishi.h -
100.0%
-
100.0 %1 / 1-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html deleted file mode 100644 index e449df2d8..000000000 --- a/doc/coverageReport/include/crpropa/module/Boundary.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Boundary.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Boundary.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:66100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Boundary.h.func.html b/doc/coverageReport/include/crpropa/module/Boundary.h.func.html deleted file mode 100644 index 18325e255..000000000 --- a/doc/coverageReport/include/crpropa/module/Boundary.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Boundary.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Boundary.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:66100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html b/doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html deleted file mode 100644 index 2eb065210..000000000 --- a/doc/coverageReport/include/crpropa/module/Boundary.h.gcov.html +++ /dev/null @@ -1,283 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Boundary.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Boundary.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:66100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_BOUNDARY_H
-       2             : #define CRPROPA_BOUNDARY_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : 
-       6             : namespace crpropa {
-       7             : /**
-       8             :  * \addtogroup Condition
-       9             :  * @{
-      10             :  */
-      11             : 
-      12             : /**
-      13             :  @class PeriodicBox
-      14             :  @brief Rectangular box with periodic boundaries.
-      15             : 
-      16             :  If a particle passes on of the sides it is placed at the opposite side and its initial (source) position changed accordingly.
-      17             :  This implements periodic boundaries, that keep the particle inside the box and instead move the source away periodically.
-      18             :  Particles can overshoot (be outside of the box during the step) since the step size is not limited by this module.
-      19             :  */
-      20           2 : class PeriodicBox: public Module {
-      21             : private:
-      22             :         Vector3d origin;
-      23             :         Vector3d size;
-      24             : 
-      25             : public:
-      26             :         /** Default constructor
-      27             :          */
-      28             :         PeriodicBox();
-      29             :         /** Constructor
-      30             :          @param origin  vector corresponding to the lower box corner
-      31             :          @param size    vector corresponding to the box sizes along each direction
-      32             :          */
-      33             :         PeriodicBox(Vector3d origin, Vector3d size);
-      34             :         void process(Candidate *candidate) const;
-      35             :         void setOrigin(Vector3d origin);
-      36             :         void setSize(Vector3d size);
-      37             :         std::string getDescription() const;
-      38             : };
-      39             : 
-      40             : /**
-      41             :  @class ReflectiveBox
-      42             :  @brief Rectangular box with reflective boundaries.
-      43             : 
-      44             :  If a particle passes on of the sides it is reflected back inside (position and velocity) and its initial position changed as if the particle had come from that side.
-      45             :  This implements periodic boundaries, that keep the particle inside the box and instead move the source away reflectively.
-      46             :  Particles can overshoot (be outside of the box during the step) since the step size is not limited by this module.
-      47             :  */
-      48           1 : class ReflectiveBox: public Module {
-      49             : private:
-      50             :         Vector3d origin;
-      51             :         Vector3d size;
-      52             : 
-      53             : public:
-      54             :         /** Default constructor
-      55             :          */
-      56             :         ReflectiveBox();
-      57             :         /** Constructor
-      58             :          @param origin  vector corresponding to the lower box corner
-      59             :          @param size    vector corresponding to the box sizes along each direction
-      60             :          */
-      61             :         ReflectiveBox(Vector3d origin, Vector3d size);
-      62             :         void process(Candidate *candidate) const;
-      63             :         void setOrigin(Vector3d origin);
-      64             :         void setSize(Vector3d size);
-      65             :         std::string getDescription() const;
-      66             : };
-      67             : 
-      68             : /**
-      69             :  @class CubicBoundary
-      70             :  @brief Flags a particle when exiting the cube.
-      71             : 
-      72             :  The particle is made inactive and flagged as "Rejected".
-      73             :  By default the module prevents overshooting the boundary by more than a margin of 0.1 kpc.
-      74             :  This corresponds to the default minimum step size of the propagation modules (PropagationCK and SimplePropagation).
-      75             :  */
-      76           4 : class CubicBoundary: public AbstractCondition {
-      77             : private:
-      78             :         Vector3d origin;
-      79             :         double size;
-      80             :         double margin;
-      81             :         bool limitStep;
-      82             : 
-      83             : public:
-      84             :         /** Default constructor
-      85             :          */
-      86             :         CubicBoundary();
-      87             :         /** Constructor
-      88             :          @param origin  vector corresponding to the lower box corner
-      89             :          @param size    vector corresponding to the box sizes along each direction
-      90             :          */
-      91             :         CubicBoundary(Vector3d origin, double size);
-      92             :         void process(Candidate *candidate) const;
-      93             :         void setOrigin(Vector3d origin);
-      94             :         void setSize(double size);
-      95             :         void setMargin(double margin);
-      96             :         void setLimitStep(bool limitStep);
-      97             :         std::string getDescription() const;
-      98             : };
-      99             : 
-     100             : /**
-     101             :  @class SphericalBoundary
-     102             :  @brief Flag a particle when leaving the sphere.
-     103             : 
-     104             :  The particle is made inactive and flagged as "Rejected".
-     105             :  By default the module prevents overshooting the boundary by more than a margin of 0.1 kpc.
-     106             :  This corresponds to the default minimum step size of the propagation modules (PropagationCK and SimplePropagation).
-     107             :  */
-     108           3 : class SphericalBoundary: public AbstractCondition {
-     109             : private:
-     110             :         Vector3d center;
-     111             :         double radius;
-     112             :         double margin;
-     113             :         bool limitStep;
-     114             : 
-     115             : public:
-     116             :         /** Default constructor
-     117             :          */
-     118             :         SphericalBoundary();
-     119             :         /** Constructor
-     120             :          @param center          vector containing the coordinates of the center of the sphere
-     121             :          @param radius          radius of the sphere
-     122             :          */
-     123             :         SphericalBoundary(Vector3d center, double radius);
-     124             :         void process(Candidate *candidate) const;
-     125             :         void setCenter(Vector3d center);
-     126             :         void setRadius(double size);
-     127             :         void setMargin(double margin);
-     128             :         void setLimitStep(bool limitStep);
-     129             :         std::string getDescription() const;
-     130             : };
-     131             : 
-     132             : /**
-     133             :  @class EllipsoidalBoundary
-     134             :  @brief Flags a particle when leaving the ellipsoid.
-     135             : 
-     136             :  This module flags particles when outside of the ellipsoid, defined by two focal points and a major axis (length).
-     137             :  The particle is made inactive and flagged as "Rejected".
-     138             :  By default the module prevents overshooting the boundary by more than a margin of 0.1 kpc.
-     139             :  This corresponds to the default minimum step size of the propagation modules (PropagationCK and SimplePropagation).
-     140             :  */
-     141           3 : class EllipsoidalBoundary: public AbstractCondition {
-     142             : private:
-     143             :         Vector3d focalPoint1;
-     144             :         Vector3d focalPoint2;
-     145             :         double majorAxis;
-     146             :         double margin;
-     147             :         bool limitStep;
-     148             : 
-     149             : public:
-     150             :         /** Default constructor
-     151             :          */
-     152             :         EllipsoidalBoundary();
-     153             :         /** Constructor
-     154             :          @param focalPoint1             one of the foci of the ellipsoid
-     155             :          @param focalPoint2             the other foci of the ellipsoid
-     156             :          @param majorAxis               length of the major axis of the ellipsoid
-     157             :          */
-     158             :         EllipsoidalBoundary(Vector3d focalPoint1, Vector3d focalPoint2,
-     159             :                         double majorAxis);
-     160             :         void process(Candidate *candidate) const;
-     161             :         void setFocalPoints(Vector3d focalPoint1, Vector3d focalPoint2);
-     162             :         void setMajorAxis(double size);
-     163             :         void setMargin(double margin);
-     164             :         void setLimitStep(bool limitStep);
-     165             :         std::string getDescription() const;
-     166             : };
-     167             : 
-     168             : 
-     169             : /**
-     170             :  @class CylindricalBoundary
-     171             :  @brief Flags a particle when leaving the cylinder whose axis is along the z-axis.
-     172             :  This module flags particles when outside of the cylinder, defined by a radius and a height.
-     173             :  The particle is made inactive and by default is flagged "OutOfBounds".
-     174             :  Optionally the module can ensure the candidate does not overshoot the boundary by more than a set margin.
-     175             :  */
-     176           3 : class CylindricalBoundary: public AbstractCondition {
-     177             : private:
-     178             :         Vector3d origin;
-     179             :         double height;
-     180             :         double radius;
-     181             :         double margin;
-     182             :         bool limitStep;
-     183             : 
-     184             : public:
-     185             :         /** Default constructor
-     186             :          */
-     187             :         CylindricalBoundary();
-     188             :         /** Constructor
-     189             :          @param origin  vector corresponding to the lower part of the cylinder axis
-     190             :          @param height  height of the cylinder
-     191             :          @param radius  radius of the cylinder
-     192             :          */
-     193             :         CylindricalBoundary(Vector3d origin, double height,
-     194             :                         double radius);
-     195             :         void process(Candidate *candidate) const;
-     196             :         void setOrigin(Vector3d origin);
-     197             :         void setHeight(double height);
-     198             :         void setRadius(double radius);
-     199             :         void setMargin(double margin);
-     200             :         void setLimitStep(bool limitStep);
-     201             :         std::string getDescription() const;
-     202             : };
-     203             : /** @}*/
-     204             : 
-     205             : } // namespace crpropa
-     206             : 
-     207             : #endif // CRPROPA_BOUNDARY_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html deleted file mode 100644 index 5eddfe368..000000000 --- a/doc/coverageReport/include/crpropa/module/BreakCondition.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/BreakCondition.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - BreakCondition.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:44100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html b/doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html deleted file mode 100644 index bcf7545eb..000000000 --- a/doc/coverageReport/include/crpropa/module/BreakCondition.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/BreakCondition.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - BreakCondition.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:44100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html b/doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html deleted file mode 100644 index 58e693670..000000000 --- a/doc/coverageReport/include/crpropa/module/BreakCondition.h.gcov.html +++ /dev/null @@ -1,221 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/BreakCondition.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - BreakCondition.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:44100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_BREAKCONDITION_H
-       2             : #define CRPROPA_BREAKCONDITION_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : 
-       6             : namespace crpropa {
-       7             : /**
-       8             :  * \addtogroup Condition 
-       9             :  * @{
-      10             :  */
-      11             : 
-      12             : /**
-      13             :  @class MaximumTrajectoryLength
-      14             :  @brief Deactivates the candidate beyond a maximum trajectory length
-      15             : 
-      16             :  This module deactivates the candidate at a given maximum trajectory length.
-      17             :  In that case the property ("Deactivated", module::description) is set.
-      18             :  It also limits the candidates next step size to ensure the maximum trajectory length is not exceeded.
-      19             :  */
-      20             : class MaximumTrajectoryLength: public AbstractCondition {
-      21             :         double maxLength;
-      22             :         std::vector<Vector3d> observerPositions;
-      23             : public:
-      24             :         MaximumTrajectoryLength(double length = 0);
-      25             :         void setMaximumTrajectoryLength(double length);
-      26             :         double getMaximumTrajectoryLength() const;
-      27             :         void addObserverPosition(const Vector3d &position);
-      28             :         const std::vector<Vector3d>& getObserverPositions() const;
-      29             :         std::string getDescription() const;
-      30             :         void process(Candidate *candidate) const;
-      31             : };
-      32             : 
-      33             : /**
-      34             :  @class MinimumEnergy
-      35             :  @brief Deactivates the candidate below a minimum energy
-      36             : 
-      37             :  This module deactivates the candidate below a given minimum energy.
-      38             :  In that case the property ("Deactivated", module::description) is set.
-      39             :  */
-      40           1 : class MinimumEnergy: public AbstractCondition {
-      41             :         double minEnergy;
-      42             : public:
-      43             :         MinimumEnergy(double minEnergy = 0);
-      44             :         void setMinimumEnergy(double energy);
-      45             :         double getMinimumEnergy() const;
-      46             :         std::string getDescription() const;
-      47             :         void process(Candidate *candidate) const;
-      48             : };
-      49             : 
-      50             : 
-      51             : /**
-      52             :  @class MinimumRigidity
-      53             :  @brief Deactivates the candidate below a minimum rigidity
-      54             : 
-      55             :  This module deactivates the candidate below a given minimum rigidity (E/Z in EeV).
-      56             :  In that case the property ("Deactivated", module::description) is set.
-      57             :  */
-      58             : class MinimumRigidity: public AbstractCondition {
-      59             :         double minRigidity;
-      60             : public:
-      61             :         MinimumRigidity(double minRigidity = 0);
-      62             :         void setMinimumRigidity(double minRigidity);
-      63             :         double getMinimumRigidity() const;
-      64             :         std::string getDescription() const;
-      65             :         void process(Candidate *candidate) const;
-      66             : };
-      67             : 
-      68             : /**
-      69             :  @class MinimumRedshift
-      70             :  @brief Deactivates the candidate below a minimum redshift
-      71             : 
-      72             :  This module deactivates the candidate below a given minimum redshift.
-      73             :  In that case the property ("Deactivated", module::description) is set.
-      74             :  */
-      75           1 : class MinimumRedshift: public AbstractCondition {
-      76             :         double zmin;
-      77             : public:
-      78             :         MinimumRedshift(double zmin = 0);
-      79             :         void setMinimumRedshift(double z);
-      80             :         double getMinimumRedshift();
-      81             :         std::string getDescription() const;
-      82             :         void process(Candidate *candidate) const;
-      83             : };
-      84             : 
-      85             : /**
-      86             :  @class MinimumChargeNumber
-      87             :  @brief Deactivates the candidate below a minimum number
-      88             : 
-      89             :  This module deactivates the candidate below a given minimum charge number.
-      90             :  A minimum charge number of 26 deactivates all (anti-) isotopes which 
-      91             :  are ranked in the periodic table before iron (Fe). 
-      92             :  In that case the property ("Deactivated", module::description) is set.
-      93             :  */
-      94           1 : class MinimumChargeNumber: public AbstractCondition {
-      95             :         int minChargeNumber;
-      96             : public:
-      97             :         MinimumChargeNumber(int minChargeNumber = 0);
-      98             :         void setMinimumChargeNumber(int chargeNumber);
-      99             :         int getMinimumChargeNumber() const;
-     100             :         std::string getDescription() const;
-     101             :         void process(Candidate *candidate) const;
-     102             : };
-     103             : 
-     104             : /**
-     105             :  @class MinimumEnergyPerParticleId
-     106             :  @brief Deactivates the candidate below a minimum energy for specific particle Ids.
-     107             : 
-     108             :  This module deactivates the candidate below a given minimum energy for specific particle types.
-     109             :  In that case the property ("Deactivated", module::description) is set.
-     110             :  All particles whose minimum energy is not specified follow the more general minEnergyOthers condition.
-     111             :  */
-     112             : class MinimumEnergyPerParticleId: public AbstractCondition {
-     113             :         std::vector<double> minEnergies;
-     114             :         std::vector<int> particleIds;
-     115             :         double minEnergyOthers;
-     116             : public:
-     117             :         MinimumEnergyPerParticleId(double minEnergyOthers = 0);
-     118             :         void setMinimumEnergyOthers(double energy);
-     119             :         double getMinimumEnergyOthers() const;
-     120             :         void add(int id, double energy);
-     121             :         std::string getDescription() const;
-     122             :         void process(Candidate *candidate) const;
-     123             : };
-     124             : 
-     125             : 
-     126             : /**
-     127             :  @class DetectionLength
-     128             :  @brief Detects the candidate at a given trajectoryLength
-     129             :  
-     130             :  This break condition can be used for non-regular time observation of the particle density. See also ObserverTimeEvolution.
-     131             :  */
-     132           1 : class DetectionLength: public AbstractCondition {
-     133             :         double detLength;
-     134             : public:
-     135             :         DetectionLength(double length = 0);
-     136             :         void setDetectionLength(double length);
-     137             :         double getDetectionLength() const;
-     138             :         std::string getDescription() const;
-     139             :         void process(Candidate *candidate) const;
-     140             : };
-     141             : /** @}*/
-     142             : 
-     143             : } // namespace crpropa
-     144             : 
-     145             : #endif // CRPROPA_BREAKCONDITION_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html deleted file mode 100644 index 6be660edc..000000000 --- a/doc/coverageReport/include/crpropa/module/HDF5Output.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/HDF5Output.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - HDF5Output.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html b/doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html deleted file mode 100644 index b0f0e622a..000000000 --- a/doc/coverageReport/include/crpropa/module/HDF5Output.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/HDF5Output.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - HDF5Output.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html b/doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html deleted file mode 100644 index 1db93380e..000000000 --- a/doc/coverageReport/include/crpropa/module/HDF5Output.h.gcov.html +++ /dev/null @@ -1,217 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/HDF5Output.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - HDF5Output.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifdef CRPROPA_HAVE_HDF5
-       2             : 
-       3             : #ifndef CRPROPA_HDF5OUTPUT_H
-       4             : #define CRPROPA_HDF5OUTPUT_H
-       5             : 
-       6             : 
-       7             : #include "crpropa/module/Output.h"
-       8             : #include <stdint.h>
-       9             : #include <ctime>
-      10             : 
-      11             : #include <H5Ipublic.h>
-      12             : 
-      13             : namespace crpropa {
-      14             : 
-      15             : const size_t propertyBufferSize = 1024;
-      16             : 
-      17             : /**
-      18             :  * \addtogroup Output
-      19             :  * @{
-      20             :  */
-      21             : 
-      22             : /**
-      23             :  @class HDF5Output
-      24             :  @brief Output to HDF5 Format.
-      25             : The base class gives an overview of possible columns
-      26             : 
-      27             : HDF5 structure:
-      28             : ```
-      29             : HDF5 "FILENAME.h5" {
-      30             : GROUP "/" {
-      31             : DATASET "OUTPUTTYPE" {
-      32             :   DATATYPE  H5T_COMPOUND {
-      33             :   ...
-      34             :  }
-      35             :  DATASPACE  SIMPLE { ( 1 ) / ( H5S_UNLIMITED ) }
-      36             :  DATA {
-      37             :   ...
-      38             :  }
-      39             :   ATTRIBUTE "Version" {
-      40             :   DATATYPE  H5T_STRING {
-      41             :       STRSIZE 100;
-      42             :       STRPAD H5T_STR_NULLTERM;
-      43             :       CSET H5T_CSET_ASCII;
-      44             :       CTYPE H5T_C_S1;
-      45             :       }
-      46             :   DATASPACE  SCALAR
-      47             :   DATA { (0): "VERSION" }
-      48             :  }
-      49             : } } }
-      50             : ```
-      51             : 
-      52             :  */
-      53             : class HDF5Output: public Output {
-      54             : 
-      55           0 :         typedef struct OutputRow {
-      56             :                 double D;
-      57             :                 double z;
-      58             :                 uint64_t SN;
-      59             :                 int32_t ID;
-      60             :                 double E;
-      61             :                 double X;
-      62             :                 double Y;
-      63             :                 double Z;
-      64             :                 double Px;
-      65             :                 double Py;
-      66             :                 double Pz;
-      67             :                 uint64_t SN0;
-      68             :                 int32_t ID0;
-      69             :                 double E0;
-      70             :                 double X0;
-      71             :                 double Y0;
-      72             :                 double Z0;
-      73             :                 double P0x;
-      74             :                 double P0y;
-      75             :                 double P0z;
-      76             :                 uint64_t SN1;
-      77             :                 int32_t ID1;
-      78             :                 double E1;
-      79             :                 double X1;
-      80             :                 double Y1;
-      81             :                 double Z1;
-      82             :                 double P1x;
-      83             :                 double P1y;
-      84             :                 double P1z;
-      85             :                 double weight;
-      86             :                 std::string tag;
-      87             :                 unsigned char propertyBuffer[propertyBufferSize];
-      88             :         } OutputRow;
-      89             : 
-      90             :         std::string filename;
-      91             : 
-      92             :         hid_t file, sid;
-      93             :         hid_t dset, dataspace;
-      94             :         mutable std::vector<OutputRow> buffer;
-      95             : 
-      96             :         time_t lastFlush;
-      97             :         unsigned int flushLimit;
-      98             :         unsigned int candidatesSinceFlush;
-      99             : public:
-     100             :         /** Default constructor.
-     101             :                 Does not run from scratch.
-     102             :             At least open() has to be called in addition.
-     103             :                 Units of energy and length are, by default, EeV and Mpc.
-     104             :                 This can be changed with setEnergyScale and setLengthScale.
-     105             :          */
-     106             :         HDF5Output();
-     107             :         /** Constructor with the default OutputType (everything).
-     108             :                 @param filename string containing name of output hdf5 file
-     109             :          */
-     110             :         HDF5Output(const std::string &filename);
-     111             :         /** Constructor
-     112             :                 @param outputtype       type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
-     113             :                 @param filename string containing name of output hdf5 file
-     114             :          */
-     115             :         HDF5Output(const std::string &filename, OutputType outputtype);
-     116             :         ~HDF5Output();
-     117             : 
-     118             :         void process(Candidate *candidate) const;
-     119             :         herr_t insertStringAttribute(const std::string &key, const std::string &value);
-     120             :         herr_t insertDoubleAttribute(const std::string &key, const double &value);
-     121             :         std::string getDescription() const;
-     122             : 
-     123             :         /// Force flush after N events. In long running applications with scarse
-     124             :         /// output this can be set to 1 or 0 to avoid data corruption. In applications
-     125             :         /// with frequent output this should be set to a high number (default)
-     126             :         void setFlushLimit(unsigned int N);
-     127             : 
-     128             :         /** Create and prepare a file as HDF5-file.
-     129             :          */
-     130             :         void open(const std::string &filename);
-     131             :         void close();
-     132             :         void flush() const;
-     133             : 
-     134             : };
-     135             : /** @}*/
-     136             : 
-     137             : } // namespace crpropa
-     138             : 
-     139             : #endif // CRPROPA_HDF5OUTPUT_H
-     140             : 
-     141             : #endif // CRPROPA_HAVE_HDF5
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html deleted file mode 100644 index 7c09d8ac5..000000000 --- a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/NuclearDecay.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - NuclearDecay.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html deleted file mode 100644 index ffb262df7..000000000 --- a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/NuclearDecay.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - NuclearDecay.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html b/doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html deleted file mode 100644 index 9bd7d125c..000000000 --- a/doc/coverageReport/include/crpropa/module/NuclearDecay.h.gcov.html +++ /dev/null @@ -1,163 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/NuclearDecay.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - NuclearDecay.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_NUCLEARDECAY_H
-       2             : #define CRPROPA_NUCLEARDECAY_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : 
-       6             : #include <vector>
-       7             : 
-       8             : namespace crpropa {
-       9             : /**
-      10             :  * \addtogroup EnergyLosses
-      11             :  * @{
-      12             :  */
-      13             : 
-      14             : /**
-      15             :  @class NuclearDecay
-      16             :  @brief Nuclear decay of unstable nuclei.
-      17             : 
-      18             :  This module simulates the nuclear decay of unstable nuclei using data from NuDat2.
-      19             :  All decay modes are considered: alpha, beta+- and gamma decay, as well as proton- and neutron dripping.
-      20             :  The resulting non-hadronic secondary particles (e+, e-, neutrinos, gamma) can optionally be created.
-      21             : 
-      22             :  For details on the preprocessing of the NuDat2 data refer to "CRPropa3-data/calc_decay.py".
-      23             :  */
-      24             : class NuclearDecay: public Module {
-      25             : private:
-      26             :         double limit;
-      27             :         bool haveElectrons;
-      28             :         bool havePhotons;
-      29             :         bool haveNeutrinos;
-      30        1800 :         struct DecayMode {
-      31             :                 int channel; // (#beta- #beta+ #alpha #proton #neutron)
-      32             :                 double rate; // decay rate in [1/m]
-      33             :                 std::vector<double> energy; // photon energies of ensuing gamma decays
-      34             :                 std::vector<double> intensity; // probabilities of ensuing gamma decays
-      35             :         };
-      36             :         std::vector<std::vector<DecayMode> > decayTable; // decayTable[Z * 31 + N] = vector<DecayMode>
-      37             :         std::string interactionTag = "ND";
-      38             : 
-      39             : public:
-      40             :         /** Constructor.
-      41             :          @param electrons               if true, add secondary photons as candidates
-      42             :          @param photons                 if true, add secondary photons as candidates
-      43             :          @param neutrinos               if true, add secondary neutrinos as candidates
-      44             :          @param limit                   step size limit as fraction of mean free path
-      45             :          */
-      46             :         NuclearDecay(bool electrons = false, bool photons = false, bool neutrinos = false, double limit = 0.1);
-      47             : 
-      48             :         /** Limit the propagation step to a fraction of the mean free path
-      49             :          * @param limit fraction of the mean free path
-      50             :          */
-      51             :         void setLimit(double limit);
-      52             : 
-      53             :         // decide if secondary electrons are added to the simulation    
-      54             :         void setHaveElectrons(bool b);
-      55             : 
-      56             :         // decide if secondary photons are added to the simulation      
-      57             :         void setHavePhotons(bool b);
-      58             : 
-      59             :         // decide if secondary neutrinos are added to the simulation    
-      60             :         void setHaveNeutrinos(bool b);
-      61             : 
-      62             :         /** set a custom interaction tag to trace back this interaction
-      63             :          * @param tag string that will be added to the candidate and output
-      64             :          */
-      65             :         void setInteractionTag(std::string tag);
-      66             :         std::string getInteractionTag() const;
-      67             : 
-      68             :         void process(Candidate *candidate) const;
-      69             :         void performInteraction(Candidate *candidate, int channel) const;
-      70             :         void gammaEmission(Candidate *candidate, int channel) const;
-      71             :         void betaDecay(Candidate *candidate, bool isBetaPlus) const;
-      72             :         void nucleonEmission(Candidate *candidate, int dA, int dZ) const;
-      73             : 
-      74             :         /**
-      75             :          Return the mean free path.
-      76             :          This is not used in the simulation.
-      77             :          @param id      PDG particle id
-      78             :          @param gamma   Lorentz factor of particle
-      79             :          @returns The mean free path [in meters]
-      80             :          */
-      81             :         double meanFreePath(int id, double gamma);
-      82             : };
-      83             : /** @}*/
-      84             : 
-      85             : } // namespace crpropa
-      86             : 
-      87             : #endif // CRPROPA_NUCLEARDECAY_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html deleted file mode 100644 index 9075a3567..000000000 --- a/doc/coverageReport/include/crpropa/module/Observer.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Observer.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Observer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3837.5 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Observer.h.func.html b/doc/coverageReport/include/crpropa/module/Observer.h.func.html deleted file mode 100644 index 9f9969a72..000000000 --- a/doc/coverageReport/include/crpropa/module/Observer.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Observer.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Observer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3837.5 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Observer.h.gcov.html b/doc/coverageReport/include/crpropa/module/Observer.h.gcov.html deleted file mode 100644 index 216df472e..000000000 --- a/doc/coverageReport/include/crpropa/module/Observer.h.gcov.html +++ /dev/null @@ -1,351 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Observer.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Observer.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:3837.5 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_OBSERVER_H
-       2             : #define CRPROPA_OBSERVER_H
-       3             : 
-       4             : #include <fstream>
-       5             : #include <limits>
-       6             : #include <string>
-       7             : #include <vector>
-       8             : 
-       9             : #include "../Candidate.h"
-      10             : #include "../Module.h"
-      11             : #include "../Referenced.h"
-      12             : #include "../Vector3.h"
-      13             : #include "../Geometry.h"
-      14             : 
-      15             : namespace crpropa {
-      16             : 
-      17             : enum DetectionState {
-      18             :         DETECTED, VETO, NOTHING
-      19             : };
-      20             : 
-      21             : /** \addtogroup Observer
-      22             :  * @{
-      23             :  */
-      24             : 
-      25             : 
-      26             : /**
-      27             :  @class ObserverFeature
-      28             :  @brief Abstract base class for features of observers
-      29             :  */
-      30           1 : class ObserverFeature: public Referenced {
-      31             : protected:
-      32             :         std::string description;
-      33             : public:
-      34             :         virtual DetectionState checkDetection(Candidate *candidate) const;
-      35             :         virtual void onDetection(Candidate *candidate) const;
-      36             :         virtual std::string getDescription() const;
-      37             : };
-      38             : 
-      39             : 
-      40             : /**
-      41             :  @class Observer
-      42             :  @brief General particle observer
-      43             :  */
-      44             : class Observer: public Module {
-      45             :         std::string flagKey;
-      46             :         std::string flagValue;
-      47             : private:
-      48             :         std::vector<ref_ptr<ObserverFeature> > features;
-      49             :         ref_ptr<Module> detectionAction;
-      50             :         bool clone;
-      51             :         bool makeInactive;
-      52             : public:
-      53             :         /** Default observer constructor
-      54             :          */
-      55             :         Observer();
-      56             :         /** Add a feature to the observer
-      57             :          @param feature         observer feature to be added to the Observer object
-      58             :          */
-      59             :         void add(ObserverFeature *feature);
-      60             :         /** Perform some specific actions upon detection of candidate
-      61             :          @param action          module that performs a given action when candidate is detected
-      62             :          @param clone           if true, clone candidate
-      63             :          */
-      64             :         void onDetection(Module *action, bool clone = false);
-      65             :         void process(Candidate *candidate) const;
-      66             :         std::string getDescription() const;
-      67             :         void setFlag(std::string key, std::string value);
-      68             :         /** Determine whether candidate should be deactivated on detection
-      69             :          @param deactivate      if true, deactivate detected particles; if false, continue tracking them
-      70             :          */
-      71             :         void setDeactivateOnDetection(bool deactivate);
-      72             : };
-      73             : 
-      74             : 
-      75             : /**
-      76             :  @class ObserverDetectAll
-      77             :  @brief Detects all particles
-      78             :  */
-      79           2 : class ObserverDetectAll: public ObserverFeature {
-      80             : public:
-      81             :         DetectionState checkDetection(Candidate *candidate) const;
-      82             :         std::string getDescription() const;
-      83             : };
-      84             : 
-      85             : 
-      86             : /**
-      87             :  @class ObserverSurface
-      88             :  @brief Detects particles crossing the boundaries of a defined surface (see, e.g., `Geometry` module)
-      89             :  */
-      90             : class ObserverSurface: public ObserverFeature {
-      91             : private:
-      92             :         ref_ptr<Surface> surface;
-      93             : public:
-      94             :         /** Constructor
-      95             :          @param surface         object with some specific geometric (see Geometry.h)
-      96             :         */
-      97             :         ObserverSurface(Surface* surface);
-      98             :         DetectionState checkDetection(Candidate *candidate) const;
-      99             :         std::string getDescription() const;
-     100             : };
-     101             : 
-     102             : 
-     103             : /**
-     104             :  @class ObserverTracking
-     105             :  @brief Tracks particles inside a sphere
-     106             :  */
-     107             : class ObserverTracking: public ObserverFeature {
-     108             : private:
-     109             :         Vector3d center;
-     110             :         double radius;
-     111             :     double stepSize;
-     112             : public:
-     113             :         /** Constructor
-     114             :          @param center          vector containing the coordinates of the center of the sphere
-     115             :          @param radius          radius of the sphere
-     116             :          @param stepSize        observer will keep track of particles at every step with this size
-     117             :         */
-     118             :         ObserverTracking(Vector3d center, double radius, double stepSize = 0);
-     119             :         DetectionState checkDetection(Candidate *candidate) const;
-     120             :         std::string getDescription() const;
-     121             : };
-     122             : 
-     123             : 
-     124             : /**
-     125             :  @class Observer1D
-     126             :  @brief Detects particles when reaching x = 0
-     127             : 
-     128             :  This module detects particles when reaching x = 0 and also limits the next step size to prevent candidates from overshooting.
-     129             :  */
-     130           3 : class Observer1D: public ObserverFeature {
-     131             : public:
-     132             :         DetectionState checkDetection(Candidate *candidate) const;
-     133             :         std::string getDescription() const;
-     134             : };
-     135             : 
-     136             : 
-     137             : /**
-     138             :  @class ObserverRedshiftWindow
-     139             :  @brief Detects particles in a given redshift window
-     140             : 
-     141             :  When added to an observer, this feature generalizes it to four dimensions.
-     142             :  The fourth dimension is the redshift, a proxy for time. This is particularly
-     143             :  useful in "4D" studies, including either time-dependence (e.g. flaring objects),
-     144             :  or in 3D studies including cosmological evolution.
-     145             :  Note that redshifts should be assigned to sources when using this feature.
-     146             :  This can be done with: SourceRedshift, SourceRedshift1D, SourceUniformRedshift,
-     147             :  and SourceRedshiftEvolution.
-     148             :  */
-     149             : class ObserverRedshiftWindow: public ObserverFeature {
-     150             : private:
-     151             :         double zmin, zmax;
-     152             : public:
-     153             :         /** Constructor
-     154             :          @param zmin    lower bound of redshift interval
-     155             :          @param zmax    upper bound of redshift interval
-     156             :          */
-     157             :         ObserverRedshiftWindow(double zmin = 0, double zmax = 0.1);
-     158             :         DetectionState checkDetection(Candidate *candidate) const;
-     159             :         std::string getDescription() const;
-     160             : };
-     161             : 
-     162             : 
-     163             : /**
-     164             :  @class ObserverInactiveVeto
-     165             :  @brief Veto for inactive candidates
-     166             :  */
-     167           0 : class ObserverInactiveVeto: public ObserverFeature {
-     168             : public:
-     169             :         DetectionState checkDetection(Candidate *candidate) const;
-     170             :         std::string getDescription() const;
-     171             : };
-     172             : 
-     173             : 
-     174             : /**
-     175             :  @class ObserverNucleusVeto
-     176             :  @brief Veto for nuclei (including protons and neutrons)
-     177             :  */
-     178           0 : class ObserverNucleusVeto: public ObserverFeature {
-     179             : public:
-     180             :         DetectionState checkDetection(Candidate *candidate) const;
-     181             :         std::string getDescription() const;
-     182             : };
-     183             : 
-     184             : 
-     185             : /**
-     186             :  @class ObserverNeutrinoVeto
-     187             :  @brief Veto for neutrinos
-     188             :  */
-     189           0 : class ObserverNeutrinoVeto: public ObserverFeature {
-     190             : public:
-     191             :         DetectionState checkDetection(Candidate *candidate) const;
-     192             :         std::string getDescription() const;
-     193             : };
-     194             : 
-     195             : 
-     196             : /**
-     197             :  @class ObserverPhotonVeto
-     198             :  @brief Veto for photons
-     199             :  */
-     200           0 : class ObserverPhotonVeto: public ObserverFeature {
-     201             : public:
-     202             :         DetectionState checkDetection(Candidate *candidate) const;
-     203             :         std::string getDescription() const;
-     204             : };
-     205             : 
-     206             : 
-     207             : /**
-     208             :  @class ObserverElectronVeto
-     209             :  @brief Veto for electrons and positrons
-     210             :  */
-     211           0 : class ObserverElectronVeto: public ObserverFeature {
-     212             : public:
-     213             :         DetectionState checkDetection(Candidate *candidate) const;
-     214             :         std::string getDescription() const;
-     215             : };
-     216             : 
-     217             : 
-     218             : /**
-     219             :  @class ObserverParticleIdVeto
-     220             :  @brief Custom veto for user-defined particle types
-     221             :  Vetoes for more than one type of particle can be added by calling this
-     222             :  feature multiple times.
-     223             :  */
-     224             : class ObserverParticleIdVeto: public ObserverFeature {
-     225             : private:
-     226             :         int vetoParticleId;
-     227             : public:
-     228             :         /** Constructor
-     229             :          @param id              id of the particle following the PDG numbering scheme
-     230             :          */
-     231             :         ObserverParticleIdVeto(int id);
-     232             :         DetectionState checkDetection(Candidate *candidate) const;
-     233             :         std::string getDescription() const;
-     234             : };
-     235             : 
-     236             : 
-     237             : /**
-     238             :  @class ObserverTimeEvolution
-     239             :  @brief Observes the time evolution of the candidates (phase-space elements)
-     240             :  This observer is very useful if the time evolution of the particle density is needed. It detects all candidates in lin-spaced, log-spaced, or user-defined time intervals and limits the nextStep of candidates to prevent overshooting of detection intervals.
-     241             :  */
-     242             : class ObserverTimeEvolution: public ObserverFeature {
-     243             : private:
-     244             :         std::vector<double> detList;
-     245             : public:
-     246             :         /** Default constructor
-     247             :          */
-     248             :         ObserverTimeEvolution();
-     249             :         /** Constructor
-     250             :          @param min             minimum time
-     251             :          @param dist    time interval for detection
-     252             :          @param numb    number of time intervals
-     253             :          */
-     254             :         ObserverTimeEvolution(double min, double dist, double numb);
-     255             :         /** Constructor
-     256             :          @param min             minimum time
-     257             :          @param max         maximum time
-     258             :          @param numb    number of time intervals
-     259             :          @param log     log (input: true) or lin (input: false) scaling between min and max with numb steps
-     260             :          */
-     261             :         ObserverTimeEvolution(double min, double max, double numb, bool log);
-     262             :         // Add a new time step to the detection time list of the observer
-     263             :         void addTime(const double &position);
-     264             :         // Using log or lin spacing of times in the range between min and
-     265             :         // max for observing particles
-     266             :         void addTimeRange(double min, double max, double numb, bool log = false);
-     267             :         const std::vector<double>& getTimes() const;
-     268             :         DetectionState checkDetection(Candidate *candidate) const;
-     269             :         std::string getDescription() const;
-     270             : };
-     271             : /** @} */
-     272             : 
-     273             : }
-     274             : 
-     275             : #endif // CRPROPA_OBSERVER_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html deleted file mode 100644 index 743d7dacc..000000000 --- a/doc/coverageReport/include/crpropa/module/OutputShell.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/OutputShell.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - OutputShell.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:030.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/OutputShell.h.func.html b/doc/coverageReport/include/crpropa/module/OutputShell.h.func.html deleted file mode 100644 index 2db467b91..000000000 --- a/doc/coverageReport/include/crpropa/module/OutputShell.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/OutputShell.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - OutputShell.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:030.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html b/doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html deleted file mode 100644 index c24dcbcbf..000000000 --- a/doc/coverageReport/include/crpropa/module/OutputShell.h.gcov.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/OutputShell.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - OutputShell.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:030.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_OUTPUTSHELL_H
-       2             : #define CRPROPA_OUTPUTSHELL_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : #include "crpropa/AssocVector.h"
-       6             : #include "crpropa/Variant.h"
-       7             : 
-       8             : namespace crpropa {
-       9             : /**
-      10             :  * \addtogroup Output
-      11             :  * @{
-      12             :  */
-      13             : 
-      14             : /**
-      15             :  @class ShellOutput
-      16             :  @brief Show the trajectory in the shell.
-      17             :  */
-      18           0 : class ShellOutput: public Module {
-      19             : public:
-      20             :         void process(Candidate *candidate) const;
-      21             :         std::string getDescription() const;
-      22             : };
-      23             : 
-      24             : /**
-      25             :  @class ShellOutput1D
-      26             :  @brief Show the trajectory in the shell.
-      27             :  */
-      28           0 : class ShellOutput1D: public Module {
-      29             : public:
-      30             :         void process(Candidate *candidate) const;
-      31             :         std::string getDescription() const;
-      32             : };
-      33             : 
-      34             : /**
-      35             :  @class ShellPropertyOutput
-      36             :  @brief Show the candidate properties in the shell.
-      37             :  */
-      38           0 : class ShellPropertyOutput: public Module {
-      39             : public:
-      40             :         typedef Loki::AssocVector<std::string, Variant> PropertyMap;
-      41             :         void process(Candidate *candidate) const;
-      42             :         std::string getDescription() const;
-      43             : };
-      44             : /** @}*/
-      45             : 
-      46             : } // namespace cprpropa
-      47             : 
-      48             : #endif // CRPROPA_OUTPUTSHELL_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html deleted file mode 100644 index 182218a99..000000000 --- a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PhotoDisintegration.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PhotoDisintegration.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html deleted file mode 100644 index fa9ee8229..000000000 --- a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PhotoDisintegration.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PhotoDisintegration.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html b/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html deleted file mode 100644 index 04ff87a36..000000000 --- a/doc/coverageReport/include/crpropa/module/PhotoDisintegration.h.gcov.html +++ /dev/null @@ -1,167 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PhotoDisintegration.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PhotoDisintegration.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_PHOTODISINTEGRATION_H
-       2             : #define CRPROPA_PHOTODISINTEGRATION_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : #include "crpropa/PhotonBackground.h"
-       6             : 
-       7             : #include <vector>
-       8             : #include <map>
-       9             : 
-      10             : namespace crpropa {
-      11             : /**
-      12             :  * \addtogroup EnergyLosses
-      13             :  * @{
-      14             :  */
-      15             :  
-      16             : /**
-      17             :  @class PhotoDisintegration
-      18             :  @brief Photodisintegration of nuclei by background photons.
-      19             :  */
-      20             : class PhotoDisintegration: public Module {
-      21             : private:
-      22             :         ref_ptr<PhotonField> photonField;
-      23             :         double limit; // fraction of mean free path for limiting the next step
-      24             :         bool havePhotons;
-      25             :         std::string interactionTag = "PD";
-      26             : 
-      27      203566 :         struct Branch {
-      28             :                 int channel; // number of emitted (n, p, H2, H3, He3, He4)
-      29             :                 std::vector<double> branchingRatio; // branching ratio as function of nucleus Lorentz factor
-      30             :         };
-      31             : 
-      32      858506 :         struct PhotonEmission {
-      33             :                 double energy; // energy of emitted photon [J]
-      34             :                 std::vector<double> emissionProbability; // emission probability as function of nucleus Lorentz factor
-      35             :         };
-      36             : 
-      37             :         std::vector<std::vector<double> > pdRate; // pdRate[Z * 31 + N] = total interaction rate
-      38             :         std::vector<std::vector<Branch> > pdBranch; // pdTable[Z * 31 + N] = branching ratios
-      39             :         mutable std::map<int, std::vector<PhotonEmission> > pdPhoton; // map of emitted photon energies and photon emission probabilities
-      40             : 
-      41             :         static const double lgmin; // minimum log10(Lorentz-factor)
-      42             :         static const double lgmax; // maximum log10(Lorentz-factor)
-      43             :         static const size_t nlg; // number of Lorentz-factor steps
-      44             : 
-      45             : public:
-      46             :         /** Constructor.
-      47             :          @param photonField             target photon field
-      48             :          @param havePhotons             if true, add secondary photons as candidates
-      49             :          @param limit                   step size limit as fraction of mean free path
-      50             :          */
-      51             :         PhotoDisintegration(ref_ptr<PhotonField> photonField, bool havePhotons = false, double limit = 0.1);
-      52             : 
-      53             :         // set the target photon field
-      54             :         void setPhotonField(ref_ptr<PhotonField> photonField);
-      55             : 
-      56             :         // decide if secondary photons are added to the simulation
-      57             :         void setHavePhotons(bool havePhotons);
-      58             : 
-      59             :         /** Limit the propagation step to a fraction of the mean free path
-      60             :          * @param limit fraction of the mean free path
-      61             :          */
-      62             :         void setLimit(double limit);
-      63             : 
-      64             :         /** set a custom interaction tag to trace back this interaction
-      65             :          * @param tag string that will be added to the candidate and output
-      66             :          */
-      67             :         void setInteractionTag(std::string tag);
-      68             :         std::string getInteractionTag() const;
-      69             : 
-      70             :         void initRate(std::string filename);
-      71             :         void initBranching(std::string filename);
-      72             :         void initPhotonEmission(std::string filename);
-      73             : 
-      74             :         void process(Candidate *candidate) const;
-      75             :         void performInteraction(Candidate *candidate, int channel) const;
-      76             : 
-      77             :         /**
-      78             :          Calculates the loss length E dx/dE in [m] physical distance.
-      79             :          This is not used in the simulation.
-      80             :          @param id              PDG particle id
-      81             :          @param gamma   Lorentz factor of particle
-      82             :          @param z               redshift
-      83             :          @returns E dx/dE [in meters]
-      84             :          */
-      85             :         double lossLength(int id, double gamma, double z = 0);
-      86             : };
-      87             : 
-      88             : /** @}*/
-      89             : } // namespace crpropa
-      90             : 
-      91             : #endif // CRPROPA_PHOTODISINTEGRATION_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html deleted file mode 100644 index b51198676..000000000 --- a/doc/coverageReport/include/crpropa/module/PropagationBP.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PropagationBP.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PropagationBP.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html b/doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html deleted file mode 100644 index dbb675695..000000000 --- a/doc/coverageReport/include/crpropa/module/PropagationBP.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PropagationBP.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PropagationBP.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html b/doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html deleted file mode 100644 index c1056913b..000000000 --- a/doc/coverageReport/include/crpropa/module/PropagationBP.h.gcov.html +++ /dev/null @@ -1,225 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PropagationBP.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PropagationBP.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_PROPAGATIONBP_H
-       2             : #define CRPROPA_PROPAGATIONBP_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : #include "crpropa/Units.h"
-       6             : #include "crpropa/magneticField/MagneticField.h"
-       7             : #include "kiss/logger.h"
-       8             : 
-       9             : namespace crpropa {
-      10             : /**
-      11             :  * \addtogroup Propagation
-      12             :  * @{
-      13             :  */
-      14             : 
-      15             : /**
-      16             :  @class PropagationBP
-      17             :  @brief Propagation through magnetic fields using the Boris method.
-      18             : 
-      19             :  This module solves the equations of motion of a relativistic charged particle when propagating through a magnetic field.\n
-      20             :  It uses the Boris push integration method.\n
-      21             :  It can be used with a fixed step size or an adaptive version which supports the step size control.
-      22             :  The step size control tries to keep the relative error close to, but smaller than the designated tolerance.
-      23             :  Additionally a minimum and maximum size for the steps can be set.
-      24             :  For neutral particles a rectilinear propagation is applied and a next step of the maximum step size proposed.
-      25             :  */
-      26             : class PropagationBP: public Module {
-      27             : 
-      28             : public:
-      29          84 :         class Y {
-      30             :         public:
-      31             :                 Vector3d x, u; /*< phase-point: position and direction */
-      32             : 
-      33             :                 Y() {
-      34             :                 }
-      35             : 
-      36          37 :                 Y(const Vector3d &x, const Vector3d &u) :
-      37             :                                 x(x), u(u) {
-      38             :                 }
-      39             : 
-      40             :                 Y(double f) :
-      41             :                                 x(Vector3d(f, f, f)), u(Vector3d(f, f, f)) {
-      42             :                 }
-      43             : 
-      44             :                 Y operator *(double f) const {
-      45             :                         return Y(x * f, u * f);
-      46             :                 }
-      47             : 
-      48             :                 Y &operator +=(const Y &y) {
-      49             :                         x += y.x;
-      50             :                         u += y.u;
-      51             :                         return *this;
-      52             :                 }
-      53             :         };
-      54             : 
-      55             : private:
-      56             :         ref_ptr<MagneticField> field;
-      57             :         double tolerance; /** target relative error of the numerical integration */
-      58             :         double minStep; /** minimum step size of the propagation */
-      59             :         double maxStep; /** maximum step size of the propagation */
-      60             : 
-      61             : public:
-      62             :         /** Default constructor for the Boris push. It is constructed with a fixed step size.
-      63             :          * @param field
-      64             :          * @param fixedStep 
-      65             :          */
-      66             :         PropagationBP(ref_ptr<MagneticField> field = NULL, double fixedStep = 1. * kpc);
-      67             : 
-      68             :         /** Constructor for the adaptive Boris push.
-      69             :          * @param field
-      70             :          * @param tolerance      tolerance is criterion for step adjustment. Step adjustment takes place only if minStep < maxStep
-      71             :          * @param minStep          minStep/c_light is the minimum integration time step
-      72             :          * @param maxStep          maxStep/c_light is the maximum integration time step. 
-      73             :          */
-      74             :     PropagationBP(ref_ptr<MagneticField> field, double tolerance, double minStep, double maxStep);
-      75             : 
-      76             :         /** Propagates the particle. Is called once per iteration.
-      77             :          * @param candidate      The Candidate is a passive object, that holds the information about the state of the cosmic ray and the simulation itself. */
-      78             :         void process(Candidate *candidate) const;
-      79             : 
-      80             :         /** Calculates the new position and direction of the particle based on the solution of the Lorentz force
-      81             :          * @param pos   current position of the candidate
-      82             :          * @param dir   current direction of the candidate
-      83             :          * @param step  current step size of the candidate
-      84             :          * @param z             current redshift is needed to calculate the magnetic field
-      85             :          * @param q             current charge of the candidate
-      86             :          * @param m             current mass of the candidate
-      87             :          * @return        return the new calculated position and direction of the candidate 
-      88             :          */
-      89             :         Y dY(Vector3d  pos, Vector3d  dir, double step, double z, double q, double m) const;
-      90             : 
-      91             :         /** comparison of the position after one step with the position after two steps with step/2.
-      92             :          * @param x1    position after one step of size step
-      93             :          * @param x2    position after two steps of size step/2
-      94             :          * @param step  current step size
-      95             :          * @return        measurement of the error of the step 
-      96             :          */
-      97             :         double errorEstimation(const Vector3d x1, const Vector3d x2, double step) const;
-      98             : 
-      99             :         /** Get magnetic field vector at current candidate position
-     100             :          * @param pos   current position of the candidate
-     101             :          * @param z      current redshift is needed to calculate the magnetic field
-     102             :          * @return        magnetic field vector at the position pos 
-     103             :          */
-     104             :         Vector3d getFieldAtPosition(Vector3d pos, double z) const;
-     105             : 
-     106             :         /** Adapt step size if required and calculates the new position and direction of the particle with the usage of the function dY
-     107             :          * @param y              current position and direction of candidate
-     108             :          * @param out      position and direction of candidate after the step
-     109             :          * @param error  error for the current step
-     110             :          * @param h              current step size
-     111             :          * @param p              current particle state
-     112             :          * @param z              current red shift
-     113             :          * @param q              current charge of the candidate 
-     114             :          * @param m              current mass of the candidate
-     115             :          */
-     116             :         void tryStep(const Y &y, Y &out, Y &error, double h, ParticleState &p, double z, double q, double m) const;
-     117             : 
-     118             :         /** Set functions for the parameters of the class PropagationBP */
-     119             : 
-     120             :         /** Set a specific magnetic field
-     121             :          * @param field  specific magnetic field 
-     122             :          */
-     123             :         void setField(ref_ptr<MagneticField> field);
-     124             :         /** Set a specific tolerance for the step size adaption
-     125             :          * @param tolerance      tolerance is criterion for step adjustment. Step adjustment takes place only if minStep < maxStep. 
-     126             :          */
-     127             :         void setTolerance(double tolerance);
-     128             :         /** Set the minimum step for the Boris push
-     129             :          * @param minStep          minStep/c_light is the minimum integration time step 
-     130             :          */
-     131             :         void setMinimumStep(double minStep);
-     132             :         /** Set the maximum step for the Boris push
-     133             :          * @param maxStep          maxStep/c_light is the maximum integration time step 
-     134             :          */
-     135             :         void setMaximumStep(double maxStep);
-     136             : 
-     137             :         /** Get functions for the parameters of the class PropagationBP, similar to the set functions */
-     138             : 
-     139             :         ref_ptr<MagneticField> getField() const;
-     140             :         double getTolerance() const;
-     141             :         double getMinimumStep() const;
-     142             :         double getMaximumStep() const;
-     143             :         std::string getDescription() const;
-     144             : };
-     145             : /** @}*/
-     146             : 
-     147             : } // namespace crpropa
-     148             : 
-     149             : #endif // PROPAGATIONBP_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html deleted file mode 100644 index bd00cdf4d..000000000 --- a/doc/coverageReport/include/crpropa/module/PropagationCK.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PropagationCK.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PropagationCK.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html b/doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html deleted file mode 100644 index 80cd4d8d7..000000000 --- a/doc/coverageReport/include/crpropa/module/PropagationCK.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PropagationCK.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PropagationCK.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html b/doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html deleted file mode 100644 index 1703a86ae..000000000 --- a/doc/coverageReport/include/crpropa/module/PropagationCK.h.gcov.html +++ /dev/null @@ -1,178 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/PropagationCK.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - PropagationCK.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:22100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_PROPAGATIONCK_H
-       2             : #define CRPROPA_PROPAGATIONCK_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : #include "crpropa/Units.h"
-       6             : #include "crpropa/magneticField/MagneticField.h"
-       7             : #include "kiss/logger.h"
-       8             : 
-       9             : namespace crpropa {
-      10             : /**
-      11             :  * \addtogroup Propagation 
-      12             :  * @{
-      13             :  */
-      14             : 
-      15             : /**
-      16             :  @class PropagationCK
-      17             :  @brief Rectilinear propagation through magnetic fields using the Cash-Karp method.
-      18             : 
-      19             :  This module solves the equations of motion of a relativistic charged particle when propagating through a magnetic field.\n
-      20             :  It uses the Runge-Kutta integration method with Cash-Karp coefficients.\n
-      21             :  The step size control tries to keep the relative error close to, but smaller than the designated tolerance.
-      22             :  Additionally a minimum and maximum size for the steps can be set.
-      23             :  For neutral particles a rectilinear propagation is applied and a next step of the maximum step size proposed.
-      24             :  */
-      25             : class PropagationCK: public Module {
-      26             : public:
-      27         286 :         class Y {
-      28             :         public:
-      29             :                 Vector3d x, u; /*< phase-point: position and direction */
-      30             : 
-      31             :                 Y() {
-      32             :                 }
-      33             : 
-      34          34 :                 Y(const Vector3d &x, const Vector3d &u) :
-      35             :                                 x(x), u(u) {
-      36             :                 }
-      37             : 
-      38             :                 Y(double f) :
-      39             :                                 x(Vector3d(f, f, f)), u(Vector3d(f, f, f)) {
-      40             :                 }
-      41             : 
-      42             :                 Y operator *(double f) const {
-      43             :                         return Y(x * f, u * f);
-      44             :                 }
-      45             : 
-      46             :                 Y &operator +=(const Y &y) {
-      47             :                         x += y.x;
-      48             :                         u += y.u;
-      49             :                         return *this;
-      50             :                 }
-      51             :         };
-      52             : 
-      53             : private:
-      54             :         std::vector<double> a, b, bs; /*< Cash-Karp coefficients */
-      55             :         ref_ptr<MagneticField> field;
-      56             :         double tolerance; /*< target relative error of the numerical integration */
-      57             :         double minStep; /*< minimum step size of the propagation */
-      58             :         double maxStep; /*< maximum step size of the propagation */
-      59             : 
-      60             : public:
-      61             :         /** Constructor for the adaptive Kash Carp.
-      62             :          * @param field
-      63             :          * @param tolerance      tolerance is criterion for step adjustment. Step adjustment takes place only if minStep < maxStep
-      64             :          * @param minStep          minStep/c_light is the minimum integration time step
-      65             :          * @param maxStep          maxStep/c_light is the maximum integration time step. 
-      66             :          */
-      67             :     PropagationCK(ref_ptr<MagneticField> field = NULL, double tolerance = 1e-4,
-      68             :                         double minStep = (0.1 * kpc), double maxStep = (1 * Gpc));
-      69             : 
-      70             :         void process(Candidate *candidate) const;
-      71             : 
-      72             :         // derivative of phase point, dY/dt = d/dt(x, u) = (v, du/dt)
-      73             :         // du/dt = q*c^2/E * (u x B)
-      74             :         Y dYdt(const Y &y, ParticleState &p, double z) const;
-      75             : 
-      76             :         void tryStep(const Y &y, Y &out, Y &error, double t,
-      77             :                         ParticleState &p, double z) const;
-      78             : 
-      79             :         void setField(ref_ptr<MagneticField> field);
-      80             :         void setTolerance(double tolerance);
-      81             :         void setMinimumStep(double minStep);
-      82             :         void setMaximumStep(double maxStep);
-      83             : 
-      84             :          /** get functions for the parameters of the class PropagationCK, similar to the set functions */
-      85             :         ref_ptr<MagneticField> getField() const;
-      86             :         
-      87             :         /** get magnetic field vector at current candidate position
-      88             :          * @param pos   current position of the candidate
-      89             :          * @param z      current redshift is needed to calculate the magnetic field
-      90             :          * @return        magnetic field vector at the position pos */
-      91             :         Vector3d getFieldAtPosition(Vector3d pos, double z) const;
-      92             : 
-      93             :         double getTolerance() const;
-      94             :         double getMinimumStep() const;
-      95             :         double getMaximumStep() const;
-      96             :         std::string getDescription() const;
-      97             : };
-      98             : /** @}*/
-      99             : 
-     100             : } // namespace crpropa
-     101             : 
-     102             : #endif // CRPROPA_PROPAGATIONCK_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html deleted file mode 100644 index 3041fd90b..000000000 --- a/doc/coverageReport/include/crpropa/module/Redshift.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Redshift.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Redshift.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1250.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Redshift.h.func.html b/doc/coverageReport/include/crpropa/module/Redshift.h.func.html deleted file mode 100644 index b7380b3ff..000000000 --- a/doc/coverageReport/include/crpropa/module/Redshift.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Redshift.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Redshift.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1250.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html b/doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html deleted file mode 100644 index 9cbeaec26..000000000 --- a/doc/coverageReport/include/crpropa/module/Redshift.h.gcov.html +++ /dev/null @@ -1,111 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Redshift.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Redshift.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:1250.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_REDSHIFT_H
-       2             : #define CRPROPA_REDSHIFT_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : 
-       6             : namespace crpropa {
-       7             : /**
-       8             :  * \addtogroup EnergyLosses
-       9             :  * @{
-      10             :  */
-      11             : 
-      12             : /**
-      13             :  @class Redshift
-      14             :  @brief Updates redshift and applies adiabatic energy loss according to the traveled distance.
-      15             :  */
-      16           5 : class Redshift: public Module {
-      17             : public:
-      18             :         void process(Candidate *candidate) const;
-      19             :         std::string getDescription() const;
-      20             : };
-      21             : 
-      22             : /**
-      23             :  @class FutureRedshift
-      24             :  @brief Updates redshift and applies adiabatic energy loss according to the traveled distance. Extends to negative redshift values to allow for symmetric time windows around z=0.
-      25             :  */
-      26           0 : class FutureRedshift: public Module {
-      27             : public:
-      28             :         void process(Candidate *candidate) const;
-      29             :         std::string getDescription() const;
-      30             : };
-      31             : 
-      32             : /** @}*/
-      33             : } // namespace crpropa
-      34             : 
-      35             : #endif // CRPROPA_REDSHIFT_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html deleted file mode 100644 index 487472bfc..000000000 --- a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/SimplePropagation.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - SimplePropagation.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html deleted file mode 100644 index 340e30412..000000000 --- a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/SimplePropagation.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - SimplePropagation.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html b/doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html deleted file mode 100644 index 5cd3cb7b6..000000000 --- a/doc/coverageReport/include/crpropa/module/SimplePropagation.h.gcov.html +++ /dev/null @@ -1,115 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/SimplePropagation.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - SimplePropagation.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11100.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef SIMPLEPROPAGATION_H
-       2             : #define SIMPLEPROPAGATION_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : #include "crpropa/Units.h"
-       6             : 
-       7             : namespace crpropa {
-       8             : /**
-       9             :  * \addtogroup Propagation 
-      10             :  * @{
-      11             :  */
-      12             : 
-      13             : /**
-      14             :  @class SimplePropagation
-      15             :  @brief Simple rectilinear propagation in absence of magnetic fields.
-      16             : 
-      17             :  This module implements rectilinear propagation.
-      18             :  The step size is guaranteed to be larger than minStep and smaller than maxStep.
-      19             :  It always proposes a next step size of maxStep.
-      20             :  */
-      21           1 : class SimplePropagation: public Module {
-      22             : private:
-      23             :         double minStep, maxStep;
-      24             : 
-      25             : public:
-      26             :         SimplePropagation(double minStep = (0.1 * kpc), double maxStep = (1 * Gpc));
-      27             :         void process(Candidate *candidate) const;
-      28             :         void setMinimumStep(double minStep);
-      29             :         void setMaximumStep(double maxStep);
-      30             :         double getMinimumStep() const;
-      31             :         double getMaximumStep() const;
-      32             :         std::string getDescription() const;
-      33             : };
-      34             : /** @}*/
-      35             : 
-      36             : } // namespace crpropa
-      37             : 
-      38             : #endif // SIMPLEPROPAGATION_H
-      39             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html deleted file mode 100644 index a060bcffd..000000000 --- a/doc/coverageReport/include/crpropa/module/TextOutput.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/TextOutput.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - TextOutput.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/TextOutput.h.func.html b/doc/coverageReport/include/crpropa/module/TextOutput.h.func.html deleted file mode 100644 index 52ca0025f..000000000 --- a/doc/coverageReport/include/crpropa/module/TextOutput.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/TextOutput.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - TextOutput.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html b/doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html deleted file mode 100644 index e9fc25846..000000000 --- a/doc/coverageReport/include/crpropa/module/TextOutput.h.gcov.html +++ /dev/null @@ -1,155 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/TextOutput.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - TextOutput.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:010.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_TEXTOUTPUT_H
-       2             : #define CRPROPA_TEXTOUTPUT_H
-       3             : 
-       4             : #include "crpropa/module/Output.h"
-       5             : #include "crpropa/module/ParticleCollector.h"
-       6             : 
-       7             : #include <fstream>
-       8             : 
-       9             : namespace crpropa {
-      10             : /**
-      11             :  * \addtogroup Output
-      12             :  * @{
-      13             :  */
-      14             : 
-      15             : /**
-      16             :  @class TextOutput
-      17             :  @brief Configurable plain text output for particle information.
-      18             :  This type of output can also be used to generate a .tar.gz file if
-      19             :  the library zlib is available. For details see:
-      20             :         http://zlib.net/
-      21             :  */
-      22             : class TextOutput: public Output {
-      23             : protected:
-      24             :         std::ostream *out;
-      25             :         std::ofstream outfile;
-      26             :         std::string filename;
-      27             :         bool storeRandomSeeds;
-      28             :         
-      29             :         void printHeader() const;
-      30             : 
-      31             : public:
-      32             :         /** Default constructor
-      33             :          */
-      34             :         TextOutput();
-      35             :         /** Constructor
-      36             :          @param outputType      type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
-      37             :          */
-      38             :         TextOutput(OutputType outputType);
-      39             :         /** Constructor
-      40             :          @param out                     output stream
-      41             :          */
-      42             :         TextOutput(std::ostream &out);
-      43             :         /** Constructor
-      44             :          @param out                     output stream
-      45             :          @param outputType      type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
-      46             :          */
-      47             :         TextOutput(std::ostream &out, OutputType outputType);
-      48             :         /** Constructor with the default OutputType (everything).
-      49             :          @param filename        string containing name of output text file
-      50             :          */
-      51             :         TextOutput(const std::string &filename);
-      52             :         /** Constructor
-      53             :          @param filename        string containing name of output text file
-      54             :          @param outputType      type of output: Trajectory1D, Trajectory3D, Event1D, Event3D, Everything
-      55             :          */
-      56             :         TextOutput(const std::string &filename, OutputType outputType);
-      57             :         /** Destructor
-      58             :          */
-      59             :         ~TextOutput();
-      60             :         /** Whether to store the random seeds used in the simulation.
-      61             :          This enables reproducibility of each realisation of the simulation.
-      62             :          */
-      63           0 :         void enableRandomSeeds() {storeRandomSeeds = true;};
-      64             :         void close();
-      65             :         void gzip();
-      66             :         void process(Candidate *candidate) const;
-      67             :         /** Loads a file to a particle collector.
-      68             :          This is useful for analysis involving, e.g., magnetic lenses.
-      69             :          @param filename        string containing the name of the file to be loaded
-      70             :          @param collector       object of type ParticleCollector that will store the information
-      71             :          */
-      72             :         static void load(const std::string &filename, ParticleCollector *collector);
-      73             :         std::string getDescription() const;
-      74             : };
-      75             : /** @}*/
-      76             : 
-      77             : } // namespace crpropa
-      78             : 
-      79             : #endif // CRPROPA_TEXTOUTPUT_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html b/doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html deleted file mode 100644 index 4ce957e1c..000000000 --- a/doc/coverageReport/include/crpropa/module/Tools.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Tools.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Tools.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Tools.h.func.html b/doc/coverageReport/include/crpropa/module/Tools.h.func.html deleted file mode 100644 index d4f77327f..000000000 --- a/doc/coverageReport/include/crpropa/module/Tools.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Tools.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Tools.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/Tools.h.gcov.html b/doc/coverageReport/include/crpropa/module/Tools.h.gcov.html deleted file mode 100644 index ff73e05a6..000000000 --- a/doc/coverageReport/include/crpropa/module/Tools.h.gcov.html +++ /dev/null @@ -1,150 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module/Tools.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/module - Tools.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef CRPROPA_MODULETOOLS_H
-       2             : #define CRPROPA_MODULETOOLS_H
-       3             : 
-       4             : #include "crpropa/Module.h"
-       5             : #include "crpropa/EmissionMap.h"
-       6             : 
-       7             : #include <vector>
-       8             : #include <set>
-       9             : 
-      10             : namespace crpropa {
-      11             : /**
-      12             :  * \addtogroup Tools
-      13             :  * @{
-      14             :  */
-      15             : 
-      16             : /**
-      17             :  @class PerformanceModule
-      18             :  @brief Module to monitor the simulation performance
-      19             : 
-      20             :  Add modules under investigation to this module instead of the ModuleList.
-      21             :  */
-      22           0 : class PerformanceModule: public Module {
-      23             : private:
-      24           0 :         struct _module_info {
-      25             :                 double time;
-      26             :                 ref_ptr<Module> module;
-      27             :         };
-      28             : 
-      29             :         mutable std::vector<_module_info> modules;
-      30             :         mutable size_t calls;
-      31             : 
-      32             : public:
-      33             :         ~PerformanceModule();
-      34             :         void add(Module* module);
-      35             :         void process(Candidate* candidate) const;
-      36             :         std::string getDescription() const;
-      37             : };
-      38             : 
-      39             : /**
-      40             :   @class ParticleFilter
-      41             :   @brief Reject Particles not listed in filter.
-      42             : */
-      43             : class ParticleFilter: public AbstractCondition {
-      44             :         std::set<int> ids;
-      45             : 
-      46             : public:
-      47             :         ParticleFilter();
-      48             :         ParticleFilter(const std::set<int> &ids);
-      49             :         void addId(int id);
-      50             :         void removeId(int remove);
-      51             :         std::set<int> &getIds();
-      52             : 
-      53             :         void process(Candidate* candidate) const;
-      54             :         std::string getDescription() const;
-      55             : };
-      56             : 
-      57             : 
-      58             : /**
-      59             :   @class EmissionMapFiller
-      60             :   @brief Fill EmissionMap with source particle state
-      61             : */
-      62             : class EmissionMapFiller: public Module {
-      63             :         ref_ptr<EmissionMap> emissionMap;
-      64             : public:
-      65             :         EmissionMapFiller(EmissionMap *emissionMap);
-      66             :         void setEmissionMap(EmissionMap *emissionMap);
-      67             :         void process(Candidate* candidate) const;
-      68             :         std::string getDescription() const;
-      69             : };
-      70             : 
-      71             : /** @}*/
-      72             : } // namespace crpropa
-      73             : 
-      74             : #endif // CRPROPA_MODULETOOLS_H
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/index-sort-f.html b/doc/coverageReport/include/crpropa/module/index-sort-f.html deleted file mode 100644 index 14233aa5e..000000000 --- a/doc/coverageReport/include/crpropa/module/index-sort-f.html +++ /dev/null @@ -1,213 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:223562.9 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
OutputShell.h -
0.0%
-
0.0 %0 / 3-0 / 0
TextOutput.h -
0.0%
-
0.0 %0 / 1-0 / 0
SimplePropagation.h -
100.0%
-
100.0 %1 / 1-0 / 0
BreakCondition.h -
100.0%
-
100.0 %4 / 4-0 / 0
Boundary.h -
100.0%
-
100.0 %6 / 6-0 / 0
PhotoDisintegration.h -
100.0%
-
100.0 %2 / 2-0 / 0
Tools.h -
0.0%
-
0.0 %0 / 2-0 / 0
PropagationCK.h -
100.0%
-
100.0 %2 / 2-0 / 0
PropagationBP.h -
100.0%
-
100.0 %2 / 2-0 / 0
HDF5Output.h -
0.0%
-
0.0 %0 / 1-0 / 0
Observer.h -
37.5%37.5%
-
37.5 %3 / 8-0 / 0
NuclearDecay.h -
100.0%
-
100.0 %1 / 1-0 / 0
Redshift.h -
50.0%50.0%
-
50.0 %1 / 2-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/index-sort-l.html b/doc/coverageReport/include/crpropa/module/index-sort-l.html deleted file mode 100644 index 5ff9027ea..000000000 --- a/doc/coverageReport/include/crpropa/module/index-sort-l.html +++ /dev/null @@ -1,213 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:223562.9 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
TextOutput.h -
0.0%
-
0.0 %0 / 1-0 / 0
HDF5Output.h -
0.0%
-
0.0 %0 / 1-0 / 0
Tools.h -
0.0%
-
0.0 %0 / 2-0 / 0
OutputShell.h -
0.0%
-
0.0 %0 / 3-0 / 0
Observer.h -
37.5%37.5%
-
37.5 %3 / 8-0 / 0
Redshift.h -
50.0%50.0%
-
50.0 %1 / 2-0 / 0
SimplePropagation.h -
100.0%
-
100.0 %1 / 1-0 / 0
NuclearDecay.h -
100.0%
-
100.0 %1 / 1-0 / 0
PhotoDisintegration.h -
100.0%
-
100.0 %2 / 2-0 / 0
PropagationCK.h -
100.0%
-
100.0 %2 / 2-0 / 0
PropagationBP.h -
100.0%
-
100.0 %2 / 2-0 / 0
BreakCondition.h -
100.0%
-
100.0 %4 / 4-0 / 0
Boundary.h -
100.0%
-
100.0 %6 / 6-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/include/crpropa/module/index.html b/doc/coverageReport/include/crpropa/module/index.html deleted file mode 100644 index 5483b4fa7..000000000 --- a/doc/coverageReport/include/crpropa/module/index.html +++ /dev/null @@ -1,213 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - include/crpropa/module - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - include/crpropa/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:223562.9 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Boundary.h -
100.0%
-
100.0 %6 / 6-0 / 0
BreakCondition.h -
100.0%
-
100.0 %4 / 4-0 / 0
HDF5Output.h -
0.0%
-
0.0 %0 / 1-0 / 0
NuclearDecay.h -
100.0%
-
100.0 %1 / 1-0 / 0
Observer.h -
37.5%37.5%
-
37.5 %3 / 8-0 / 0
OutputShell.h -
0.0%
-
0.0 %0 / 3-0 / 0
PhotoDisintegration.h -
100.0%
-
100.0 %2 / 2-0 / 0
PropagationBP.h -
100.0%
-
100.0 %2 / 2-0 / 0
PropagationCK.h -
100.0%
-
100.0 %2 / 2-0 / 0
Redshift.h -
50.0%50.0%
-
50.0 %1 / 2-0 / 0
SimplePropagation.h -
100.0%
-
100.0 %1 / 1-0 / 0
TextOutput.h -
0.0%
-
0.0 %0 / 1-0 / 0
Tools.h -
0.0%
-
0.0 %0 / 2-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/index-sort-f.html b/doc/coverageReport/index-sort-f.html deleted file mode 100644 index 2f53c4197..000000000 --- a/doc/coverageReport/index-sort-f.html +++ /dev/null @@ -1,293 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top levelHitTotalCoverage
Test:coverage.info.cleanedLines:87351426261.2 %
Date:2024-04-08 14:58:22Functions:1124206954.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Directory Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
include/crpropa/massDistribution -
19.2%19.2%
-
19.2 %5 / 260.0 %0 / 11
libs/healpix_base/include/healpix_base -
19.1%19.1%
-
19.1 %33 / 1738.1 %5 / 62
libs/healpix_base -
14.1%14.1%
-
14.1 %112 / 7929.4 %10 / 106
libs/kiss/include/kiss -
57.9%57.9%
-
57.9 %11 / 1920.9 %14 / 67
src/magneticField -
18.2%18.2%
-
18.2 %166 / 91021.0 %29 / 138
libs/HepPID/src -
11.4%11.4%
-
11.4 %50 / 44022.9 %11 / 48
libs/kiss/src -
28.1%28.1%
-
28.1 %34 / 12139.1 %9 / 23
include/crpropa -
73.6%73.6%
-
73.6 %408 / 55446.4 %77 / 166
include/crpropa/magneticField/turbulentField -
72.9%72.9%
-
72.9 %43 / 5947.1 %8 / 17
src/magneticLens -
45.7%45.7%
-
45.7 %147 / 32251.2 %21 / 41
src/advectionField -
42.5%42.5%
-
42.5 %131 / 30852.4 %44 / 84
include/crpropa/magneticLens -
42.9%42.9%
-
42.9 %30 / 7054.5 %6 / 11
src/magneticField/turbulentField -
71.1%71.1%
-
71.1 %187 / 26357.9 %11 / 19
src -
50.3%50.3%
-
50.3 %1361 / 270758.5 %251 / 429
src/module -
63.4%63.4%
-
63.4 %2250 / 354759.0 %286 / 485
include/crpropa/magneticField -
89.3%89.3%
-
89.3 %50 / 5663.6 %7 / 11
src/massDistribution -
83.9%83.9%
-
83.9 %349 / 41690.8 %69 / 76
test -
97.9%97.9%
-
97.9 %3320 / 339196.7 %264 / 273
include/crpropa/module -
62.9%62.9%
-
62.9 %22 / 35-0 / 0
include/crpropa/advectionField -
100.0%
-
100.0 %5 / 5-0 / 0
/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy -
43.8%43.8%
-
43.8 %21 / 48100.0 %2 / 2
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/index-sort-l.html b/doc/coverageReport/index-sort-l.html deleted file mode 100644 index ae168257c..000000000 --- a/doc/coverageReport/index-sort-l.html +++ /dev/null @@ -1,293 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top levelHitTotalCoverage
Test:coverage.info.cleanedLines:87351426261.2 %
Date:2024-04-08 14:58:22Functions:1124206954.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Directory Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
libs/HepPID/src -
11.4%11.4%
-
11.4 %50 / 44022.9 %11 / 48
libs/healpix_base -
14.1%14.1%
-
14.1 %112 / 7929.4 %10 / 106
src/magneticField -
18.2%18.2%
-
18.2 %166 / 91021.0 %29 / 138
libs/healpix_base/include/healpix_base -
19.1%19.1%
-
19.1 %33 / 1738.1 %5 / 62
include/crpropa/massDistribution -
19.2%19.2%
-
19.2 %5 / 260.0 %0 / 11
libs/kiss/src -
28.1%28.1%
-
28.1 %34 / 12139.1 %9 / 23
src/advectionField -
42.5%42.5%
-
42.5 %131 / 30852.4 %44 / 84
include/crpropa/magneticLens -
42.9%42.9%
-
42.9 %30 / 7054.5 %6 / 11
/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy -
43.8%43.8%
-
43.8 %21 / 48100.0 %2 / 2
src/magneticLens -
45.7%45.7%
-
45.7 %147 / 32251.2 %21 / 41
src -
50.3%50.3%
-
50.3 %1361 / 270758.5 %251 / 429
libs/kiss/include/kiss -
57.9%57.9%
-
57.9 %11 / 1920.9 %14 / 67
include/crpropa/module -
62.9%62.9%
-
62.9 %22 / 35-0 / 0
src/module -
63.4%63.4%
-
63.4 %2250 / 354759.0 %286 / 485
src/magneticField/turbulentField -
71.1%71.1%
-
71.1 %187 / 26357.9 %11 / 19
include/crpropa/magneticField/turbulentField -
72.9%72.9%
-
72.9 %43 / 5947.1 %8 / 17
include/crpropa -
73.6%73.6%
-
73.6 %408 / 55446.4 %77 / 166
src/massDistribution -
83.9%83.9%
-
83.9 %349 / 41690.8 %69 / 76
include/crpropa/magneticField -
89.3%89.3%
-
89.3 %50 / 5663.6 %7 / 11
test -
97.9%97.9%
-
97.9 %3320 / 339196.7 %264 / 273
include/crpropa/advectionField -
100.0%
-
100.0 %5 / 5-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/index.html b/doc/coverageReport/index.html deleted file mode 100644 index 11a901d77..000000000 --- a/doc/coverageReport/index.html +++ /dev/null @@ -1,293 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top levelHitTotalCoverage
Test:coverage.info.cleanedLines:87351426261.2 %
Date:2024-04-08 14:58:22Functions:1124206954.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Directory Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
/home/runner/.local/lib/python3.10/site-packages/numpy/core/include/numpy -
43.8%43.8%
-
43.8 %21 / 48100.0 %2 / 2
include/crpropa -
73.6%73.6%
-
73.6 %408 / 55446.4 %77 / 166
include/crpropa/advectionField -
100.0%
-
100.0 %5 / 5-0 / 0
include/crpropa/magneticField -
89.3%89.3%
-
89.3 %50 / 5663.6 %7 / 11
include/crpropa/magneticField/turbulentField -
72.9%72.9%
-
72.9 %43 / 5947.1 %8 / 17
include/crpropa/magneticLens -
42.9%42.9%
-
42.9 %30 / 7054.5 %6 / 11
include/crpropa/massDistribution -
19.2%19.2%
-
19.2 %5 / 260.0 %0 / 11
include/crpropa/module -
62.9%62.9%
-
62.9 %22 / 35-0 / 0
libs/HepPID/src -
11.4%11.4%
-
11.4 %50 / 44022.9 %11 / 48
libs/healpix_base -
14.1%14.1%
-
14.1 %112 / 7929.4 %10 / 106
libs/healpix_base/include/healpix_base -
19.1%19.1%
-
19.1 %33 / 1738.1 %5 / 62
libs/kiss/include/kiss -
57.9%57.9%
-
57.9 %11 / 1920.9 %14 / 67
libs/kiss/src -
28.1%28.1%
-
28.1 %34 / 12139.1 %9 / 23
src -
50.3%50.3%
-
50.3 %1361 / 270758.5 %251 / 429
src/advectionField -
42.5%42.5%
-
42.5 %131 / 30852.4 %44 / 84
src/magneticField -
18.2%18.2%
-
18.2 %166 / 91021.0 %29 / 138
src/magneticField/turbulentField -
71.1%71.1%
-
71.1 %187 / 26357.9 %11 / 19
src/magneticLens -
45.7%45.7%
-
45.7 %147 / 32251.2 %21 / 41
src/massDistribution -
83.9%83.9%
-
83.9 %349 / 41690.8 %69 / 76
src/module -
63.4%63.4%
-
63.4 %2250 / 354759.0 %286 / 485
test -
97.9%97.9%
-
97.9 %3320 / 339196.7 %264 / 273
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html deleted file mode 100644 index 295e10399..000000000 --- a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func-sort-c.html +++ /dev/null @@ -1,200 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleIDMethods.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - ParticleIDMethods.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5024920.1 %
Date:2024-04-08 14:58:22Functions:113234.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID10hasStrangeERKi0
_ZN6HepPID12_GLOBAL__N_15findQERKiS2_0
_ZN6HepPID12isPentaquarkERKi0
_ZN6HepPID18hasFundamentalAntiERKi0
_ZN6HepPID5hasUpERKi0
_ZN6HepPID5jSpinERKi0
_ZN6HepPID5lSpinERKi0
_ZN6HepPID5sSpinERKi0
_ZN6HepPID6hasTopERKi0
_ZN6HepPID6isSUSYERKi0
_ZN6HepPID6lambdaERKi0
_ZN6HepPID7hasDownERKi0
_ZN6HepPID7isMesonERKi0
_ZN6HepPID7isValidERKi0
_ZN6HepPID8hasCharmERKi0
_ZN6HepPID8isBaryonERKi0
_ZN6HepPID8isHadronERKi0
_ZN6HepPID8isLeptonERKi0
_ZN6HepPID9hasBottomERKi0
_ZN6HepPID9isDiQuarkERKi0
_ZN6HepPID9isRhadronERKi0
_ZN6HepPID1AERKi202818
_ZN6HepPID1ZERKi364529
_ZN6HepPID6isDyonERKi3325562
_ZN6HepPID13fundamentalIDERKi20168250
_ZN6HepPID6chargeERKi20168251
_ZN6HepPID11threeChargeERKi20168252
_ZN6HepPID9isNucleusERKi20937352
_ZN6HepPID7isQBallERKi23493806
_ZN6HepPID9extraBitsERKi50313164
_ZN6HepPID5digitENS_8locationERKi146041016
_ZN6HepPID6abspidERKi260299484
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html deleted file mode 100644 index 078e3d9b7..000000000 --- a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.func.html +++ /dev/null @@ -1,200 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleIDMethods.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - ParticleIDMethods.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5024920.1 %
Date:2024-04-08 14:58:22Functions:113234.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID10hasStrangeERKi0
_ZN6HepPID11threeChargeERKi20168252
_ZN6HepPID12_GLOBAL__N_15findQERKiS2_0
_ZN6HepPID12isPentaquarkERKi0
_ZN6HepPID13fundamentalIDERKi20168250
_ZN6HepPID18hasFundamentalAntiERKi0
_ZN6HepPID1AERKi202818
_ZN6HepPID1ZERKi364529
_ZN6HepPID5digitENS_8locationERKi146041016
_ZN6HepPID5hasUpERKi0
_ZN6HepPID5jSpinERKi0
_ZN6HepPID5lSpinERKi0
_ZN6HepPID5sSpinERKi0
_ZN6HepPID6abspidERKi260299484
_ZN6HepPID6chargeERKi20168251
_ZN6HepPID6hasTopERKi0
_ZN6HepPID6isDyonERKi3325562
_ZN6HepPID6isSUSYERKi0
_ZN6HepPID6lambdaERKi0
_ZN6HepPID7hasDownERKi0
_ZN6HepPID7isMesonERKi0
_ZN6HepPID7isQBallERKi23493806
_ZN6HepPID7isValidERKi0
_ZN6HepPID8hasCharmERKi0
_ZN6HepPID8isBaryonERKi0
_ZN6HepPID8isHadronERKi0
_ZN6HepPID8isLeptonERKi0
_ZN6HepPID9extraBitsERKi50313164
_ZN6HepPID9hasBottomERKi0
_ZN6HepPID9isDiQuarkERKi0
_ZN6HepPID9isNucleusERKi20937352
_ZN6HepPID9isRhadronERKi0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html b/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html deleted file mode 100644 index de197c29e..000000000 --- a/doc/coverageReport/libs/HepPID/src/ParticleIDMethods.cc.gcov.html +++ /dev/null @@ -1,641 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleIDMethods.cc - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - ParticleIDMethods.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5024920.1 %
Date:2024-04-08 14:58:22Functions:113234.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : // ----------------------------------------------------------------------
-       2             : //
-       3             : // ParticleIDMethods.cc
-       4             : //
-       5             : // ----------------------------------------------------------------------
-       6             : 
-       7             : #include <cmath>  // for pow()
-       8             : 
-       9             : #include "HepPID/ParticleIDMethods.hh"
-      10             : #include "HepPID/ParticleName.hh"
-      11             : 
-      12             : namespace HepPID {
-      13             : 
-      14             : namespace {
-      15             : 
-      16             : // internal function used by hasXXX methods
-      17           0 : bool findQ( const int & pid, const int & q )
-      18             : {
-      19           0 :     if( isDyon(pid) ) { return false; }
-      20           0 :     if( isRhadron(pid) ) {
-      21             :         int iz = 7;
-      22           0 :         for( int i=6; i > 1; --i ) {
-      23           0 :            if( digit(location(i),pid) == 0 ) {
-      24             :                iz = i;
-      25           0 :            } else if ( i == iz-1 ) {
-      26             :                // ignore squark or gluino
-      27             :            } else {
-      28           0 :                if( digit(location(i),pid) == q ) { return true; }
-      29             :            }
-      30             :         }
-      31             :         return false;
-      32             :     }
-      33           0 :     if( digit(nq3,pid) == q || digit(nq2,pid) == q || digit(nq1,pid) == q ) { return true; }
-      34           0 :     if( isPentaquark(pid) ) { 
-      35           0 :         if( digit(nl,pid) == q || digit(nr,pid) == q ) { return true; }
-      36             :     }
-      37             :     return false;
-      38             : }
-      39             : 
-      40             : }
-      41             : 
-      42             : // absolute value
-      43   260299484 : int abspid( const int & pid )
-      44             : {
-      45   260299484 :   return (pid < 0) ? -pid : pid;
-      46             : }
-      47             : 
-      48             : // returns everything beyond the 7th digit (e.g. outside the numbering scheme)
-      49    50313164 : int extraBits( const int & pid )
-      50             : {
-      51    50313164 :     return abspid(pid)/10000000;
-      52             : }
-      53             : 
-      54             : //  split the PID into constituent integers
-      55   146041016 : unsigned short digit( location loc, const int & pid )
-      56             : {
-      57             :     //  PID digits (base 10) are: n nr nl nq1 nq2 nq3 nj
-      58             :     //  the location enum provides a convenient index into the PID
-      59             :                 //
-      60             :                 //  Modified for CRPropa: use precalculated values isntead of pow for
-      61             :                 //  performance
-      62             :                 static unsigned int p10[] = { 1, 10, 100, 1000,  10000, 100000, 1000000,
-      63             :                         10000000, 100000000, 1000000000};
-      64   146041016 :     return (abspid(pid)/ p10[loc-1])%10;
-      65             : //    int numerator = (int) std::pow(10.0,(loc-1));
-      66             : //    return (abspid(pid)/numerator)%10;
-      67             : }
-      68             : 
-      69             : //  return the first two digits if this is a "fundamental" particle
-      70             : //  ID = 100 is a special case (internal generator ID's are 81-100)
-      71    20168250 : int fundamentalID( const int & pid )
-      72             : {
-      73    20168250 :     if( extraBits(pid) > 0 ) return 0;
-      74    20168243 :     if( digit(nq2,pid) == 0 && digit(nq1,pid) == 0) {
-      75    20168243 :         return abspid(pid)%10000;
-      76           0 :     } else if( abspid(pid) <= 100 ) {
-      77           0 :         return abspid(pid);
-      78             :     } else {
-      79             :         return 0;
-      80             :     }
-      81             : }
-      82             : 
-      83             : // Ion numbers are +/- 10LZZZAAAI. 
-      84      364529 : int Z( const int & pid )
-      85             : {
-      86             :     // a proton can also be a Hydrogen nucleus
-      87      364529 :     if( abspid(pid) == 2212 ) { return 1; }
-      88      364529 :     if( isNucleus(pid) ) return (abspid(pid)/10000)%1000;
-      89             :     return 0;
-      90             : }
-      91             : 
-      92             : // Ion numbers are +/- 10LZZZAAAI. 
-      93      202818 : int A( const int & pid )
-      94             : {
-      95             :     // a proton can also be a Hydrogen nucleus
-      96      202818 :     if( abspid(pid) == 2212 ) { return 1; }
-      97      202818 :     if( isNucleus(pid) ) return (abspid(pid)/10)%1000;
-      98             :     return 0;
-      99             : }
-     100             : 
-     101             : // if this is a nucleus (ion), get nLambda
-     102             : // Ion numbers are +/- 10LZZZAAAI. 
-     103           0 : int lambda( const int & pid )
-     104             : {
-     105             :     // a proton can also be a Hydrogen nucleus
-     106           0 :     if( abspid(pid) == 2212 ) { return 0; }
-     107           0 :     if( isNucleus(pid) ) return digit(n8,pid);
-     108             :     return 0;
-     109             : }
-     110             : 
-     111             : 
-     112             : // ---  boolean methods:
-     113             : //
-     114             : 
-     115             : //  check to see if this is a valid PID
-     116           0 : bool isValid( const int & pid )
-     117             : {
-     118           0 :     if( extraBits(pid) > 0 ) {
-     119           0 :         if( isNucleus(pid) )   { return true; }
-     120           0 :         if( isQBall(pid) )   { return true; }
-     121           0 :         return false; 
-     122             :     }
-     123           0 :     if( isSUSY(pid) ) { return true; }
-     124           0 :     if( isRhadron(pid) ) { return true; }
-     125           0 :     if( isDyon(pid) ) { return true; }
-     126             :     // Meson signature
-     127           0 :     if( isMeson(pid) )   { return true; }
-     128             :     // Baryon signature
-     129           0 :     if( isBaryon(pid) )  { return true; }
-     130             :     // DiQuark signature
-     131           0 :     if( isDiQuark(pid) ) { return true; }
-     132             :     // fundamental particle
-     133           0 :     if( fundamentalID(pid) > 0 ) { 
-     134           0 :       if(pid > 0 ) { 
-     135             :         return true; 
-     136             :       } else {
-     137           0 :         if( hasFundamentalAnti(pid) ) { return true; }
-     138           0 :         return false;
-     139             :       }
-     140             :     }
-     141             :     // pentaquark
-     142           0 :     if( isPentaquark(pid) ) { return true; }
-     143             :     // don't recognize this number
-     144             :     return false;
-     145             : }
-     146             : 
-     147             : // if this is a fundamental particle, does it have a valid antiparticle?
-     148           0 : bool hasFundamentalAnti( const int & pid )
-     149             : {
-     150             :     // these are defined by the generator and therefore are always valid
-     151           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) >= 80 ) { return true; }
-     152             :     // check id's from 1 to 79
-     153           0 :     if( fundamentalID(pid) > 0 && fundamentalID(pid) < 80 ) { 
-     154           0 :        if( validParticleName(-pid) ) { return true; }
-     155             :     }
-     156             :     return false;
-     157             : }
-     158             : 
-     159             : //  check to see if this is a valid meson
-     160           0 : bool isMeson( const int & pid )
-     161             : {
-     162           0 :     if( extraBits(pid) > 0 ) { return false; }
-     163           0 :     if( abspid(pid) <= 100 ) { return false; }
-     164           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) > 0 ) { return false; }
-     165           0 :     if( isRhadron(pid) ) { return false; }
-     166           0 :     int aid = abspid(pid);
-     167           0 :     if( aid == 130 || aid == 310 || aid == 210 ) { return true; }
-     168             :     // EvtGen uses some odd numbers
-     169           0 :     if( aid == 150 || aid == 350 || aid == 510 || aid == 530 ) { return true; }
-     170             :     // pomeron, etc.
-     171           0 :     if( pid == 110 || pid == 990 || pid == 9990 ) { return true; }
-     172           0 :     if(    digit(nj,pid) > 0 && digit(nq3,pid) > 0 
-     173           0 :         && digit(nq2,pid) > 0 && digit(nq1,pid) == 0 ) {
-     174             :         // check for illegal antiparticles
-     175           0 :         if( digit(nq3,pid) == digit(nq2,pid) && pid < 0 ) {
-     176           0 :             return false;
-     177             :         } else {
-     178             :             return true;
-     179             :         }
-     180             :     }
-     181             :     return false;
-     182             : }
-     183             : 
-     184             : //  check to see if this is a valid baryon
-     185           0 : bool isBaryon( const int & pid )
-     186             : {
-     187           0 :     if( extraBits(pid) > 0 ) { return false; }
-     188           0 :     if( abspid(pid) <= 100 ) { return false; }
-     189           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) > 0 ) { return false; }
-     190           0 :     if( isRhadron(pid) ) { return false; }
-     191           0 :     if( isPentaquark(pid) ) { return false; }
-     192           0 :     if( abspid(pid) == 2110 || abspid(pid) == 2210 ) { return true; }
-     193           0 :     if(    digit(nj,pid) > 0  && digit(nq3,pid) > 0 
-     194           0 :         && digit(nq2,pid) > 0 && digit(nq1,pid) > 0 ) { return true; }
-     195             :     return false;
-     196             : }
-     197             : 
-     198             : //  check to see if this is a valid diquark
-     199           0 : bool isDiQuark( const int & pid )
-     200             : {
-     201           0 :     if( extraBits(pid) > 0 ) { return false; }
-     202           0 :     if( abspid(pid) <= 100 ) { return false; }
-     203           0 :     if( fundamentalID(pid) <= 100 && fundamentalID(pid) > 0 ) { return false; }
-     204           0 :     if(    digit(nj,pid) > 0  && digit(nq3,pid) == 0 
-     205           0 :         && digit(nq2,pid) > 0 && digit(nq1,pid) > 0 ) {  // diquark signature
-     206             :        // EvtGen uses the diquarks for quark pairs, so, for instance, 
-     207             :        //   5501 is a valid "diquark" for EvtGen
-     208             :        //if( digit(nj) == 1 && digit(nq2) == digit(nq1) ) {     // illegal
-     209             :        //   return false; 
-     210             :        //} else {
-     211           0 :           return true;
-     212             :        //}
-     213             :     }
-     214             :     return false;
-     215             : }
-     216             : 
-     217             : // is this a valid hadron ID?
-     218           0 : bool isHadron( const int & pid )
-     219             : {
-     220           0 :     if( extraBits(pid) > 0 ) { return false; }
-     221           0 :     if( isMeson(pid) )   { return true; }
-     222           0 :     if( isBaryon(pid) )  { return true; }
-     223           0 :     if( isPentaquark(pid) ) { return true; }
-     224           0 :     if( isRhadron(pid) ) { return true; }
-     225             :     return false;
-     226             : }
-     227             : // is this a valid lepton ID?
-     228           0 : bool isLepton( const int & pid )
-     229             : {
-     230           0 :     if( extraBits(pid) > 0 ) { return false; }
-     231           0 :     if( fundamentalID(pid) >= 11 && fundamentalID(pid) <= 18 ) { return true; }
-     232             :     return false;
-     233             : }
-     234             : 
-     235             : //
-     236             : // This implements the 2006 Monte Carlo nuclear code scheme.
-     237             : // Ion numbers are +/- 10LZZZAAAI. 
-     238             : // AAA is A - total baryon number
-     239             : // ZZZ is Z - total charge
-     240             : // L is the total number of strange quarks.
-     241             : // I is the isomer number, with I=0 corresponding to the ground state.
-     242    20937352 : bool isNucleus( const int & pid )
-     243             : {
-     244             :      // a proton can also be a Hydrogen nucleus
-     245    20937352 :      if( abspid(pid) == 2212 ) { return true; }
-     246             :      // new standard: +/- 10LZZZAAAI
-     247    20937336 :      if( ( digit(n10,pid) == 1 ) && ( digit(n9,pid) == 0 ) ) {
-     248             :         // charge should always be less than or equal to baryon number
-     249             :         // the following line is A >= Z
-     250      769143 :         if( (abspid(pid)/10)%1000 >= (abspid(pid)/10000)%1000 ) { return true; }
-     251             :      }
-     252             :      return false;
-     253             : }
-     254             : 
-     255             : //  check to see if this is a valid pentaquark
-     256           0 : bool isPentaquark( const int & pid )
-     257             : {
-     258             :     // a pentaquark is of the form 9abcdej,
-     259             :     // where j is the spin and a, b, c, d, and e are quarks
-     260           0 :     if( extraBits(pid) > 0 ) { return false; }
-     261           0 :     if( digit(n,pid) != 9 )  { return false; }
-     262           0 :     if( digit(nr,pid) == 9 || digit(nr,pid) == 0 )  { return false; }
-     263           0 :     if( digit(nj,pid) == 9 || digit(nl,pid) == 0 )  { return false; }
-     264           0 :     if( digit(nq1,pid) == 0 )  { return false; }
-     265           0 :     if( digit(nq2,pid) == 0 )  { return false; }
-     266           0 :     if( digit(nq3,pid) == 0 )  { return false; }
-     267           0 :     if( digit(nj,pid) == 0 )  { return false; }
-     268             :     // check ordering
-     269           0 :     if( digit(nq2,pid) > digit(nq1,pid) )  { return false; }
-     270           0 :     if( digit(nq1,pid) > digit(nl,pid) )  { return false; }
-     271           0 :     if( digit(nl,pid) > digit(nr,pid) )  { return false; }
-     272             :     return true;
-     273             : }
-     274             : 
-     275             : // is this a SUSY?
-     276           0 : bool isSUSY( const int & pid )
-     277             : {
-     278             :     // fundamental SUSY particles have n = 1 or 2
-     279           0 :     if( extraBits(pid) > 0 ) { return false; }
-     280           0 :     if( digit(n,pid) != 1 && digit(n,pid) != 2 )  { return false; }
-     281           0 :     if( digit(nr,pid) != 0 )  { return false; }
-     282             :     // check fundamental part
-     283           0 :     if( fundamentalID(pid) == 0 )  { return false; }
-     284             :     return true;
-     285             : }
-     286             : 
-     287             : // is this an R-hadron?
-     288           0 : bool isRhadron( const int & pid )
-     289             : {
-     290             :     // an R-hadron is of the form 10abcdj, 100abcj, or 1000abj
-     291             :     // where j is the spin, b, c, and d are quarks or gluons,
-     292             :     // and a (the digit following the zero's) is a SUSY particle
-     293           0 :     if( extraBits(pid) > 0 ) { return false; }
-     294           0 :     if( digit(n,pid) != 1 )  { return false; }
-     295           0 :     if( digit(nr,pid) != 0 )  { return false; }
-     296             :     // make sure this isn't a SUSY particle
-     297           0 :     if( isSUSY(pid) ) { return false; }
-     298             :     // All R-hadrons have at least 3 core digits
-     299           0 :     if( digit(nq2,pid) == 0 )  { return false; }
-     300           0 :     if( digit(nq3,pid) == 0 )  { return false; }
-     301           0 :     if( digit(nj,pid) == 0 )  { return false; }
-     302             :     return true;
-     303             : }
-     304             : 
-     305             : // is this a Dyon (magnetic monopole)?
-     306     3325562 : bool isDyon( const int & pid )
-     307             : {
-     308             :     ///Magnetic monopoles and Dyons are assumed to have one unit of 
-     309             :     ///Dirac monopole charge and a variable integer number xyz units 
-     310             :     ///of electric charge.  
-     311             :     ///
-     312             :     ///Codes 411xyz0 are then used when the magnetic and electrical 
-     313             :     ///charge sign agree and 412xyz0 when they disagree, 
-     314             :     ///with the overall sign of the particle set by the magnetic charge.  
-     315             :     ///For now no spin information is provided.
-     316             :     ///
-     317     3325562 :     if( extraBits(pid) > 0 ) { return false; }
-     318     3325562 :     if( digit(n,pid) != 4 )  { return false; }
-     319           0 :     if( digit(nr,pid) != 1 )  { return false; }
-     320           0 :     if( (digit(nl,pid) != 1) && (digit(nl,pid) != 2) )  { return false; }
-     321             :     // All Dyons have at least 1 core digit
-     322           0 :     if( digit(nq3,pid) == 0 )  { return false; }
-     323             :     // Dyons have spin zero for now
-     324           0 :     if( digit(nj,pid) != 0 )  { return false; }
-     325             :     return true;
-     326             : }
-     327             : 
-     328             : // Check for QBalls
-     329             : // Ad-hoc numbering for such particles is 100xxxx0, 
-     330             : // where xxxx is the charge in tenths. 
-     331    23493806 : bool isQBall( const int & pid )
-     332             : {
-     333    23493806 :     if( extraBits(pid) != 1 ) { return false; }
-     334           0 :     if( digit(n,pid) != 0 )  { return false; }
-     335           0 :     if( digit(nr,pid) != 0 )  { return false; }
-     336             :     // check the core number
-     337           0 :     if( (abspid(pid)/10)%10000 == 0 )  { return false; }
-     338             :     // these particles have spin zero for now
-     339           0 :     if( digit(nj,pid) != 0 )  { return false; }
-     340             :     return true;
-     341             : }
-     342             : 
-     343             : // does this particle contain an up quark?
-     344           0 : bool hasUp( const int & pid)
-     345             : {
-     346           0 :     if( extraBits(pid) > 0 ) { return false; }
-     347           0 :     if( fundamentalID(pid) > 0 ) { return false; }
-     348           0 :     return findQ(pid,2);
-     349             : }
-     350             : // does this particle contain a down quark?
-     351           0 : bool hasDown( const int & pid)
-     352             : {
-     353           0 :     if( extraBits(pid) > 0 ) { return false; }
-     354           0 :     if( fundamentalID(pid) > 0 ) { return false; }
-     355           0 :     return findQ(pid,1);
-     356             : }
-     357             : // does this particle contain a strange quark?
-     358           0 : bool hasStrange( const int & pid )
-     359             : {
-     360           0 :     if( extraBits(pid) > 0 ) { return false; }
-     361           0 :     if( fundamentalID(pid) > 0 ) { return false; }
-     362           0 :     return findQ(pid,3);
-     363             : }
-     364             : // does this particle contain a charm quark?
-     365           0 : bool hasCharm( const int & pid )
-     366             : {
-     367           0 :     if( extraBits(pid) > 0 ) { return false; }
-     368           0 :     if( fundamentalID(pid) > 0 ) { return false; }
-     369           0 :     return findQ(pid,4);
-     370             : }
-     371             : // does this particle contain a bottom quark?
-     372           0 : bool hasBottom( const int & pid )
-     373             : {
-     374           0 :     if( extraBits(pid) > 0 ) { return false; }
-     375           0 :     if( fundamentalID(pid) > 0 ) { return false; }
-     376           0 :     return findQ(pid,5);
-     377             : }
-     378             : // does this particle contain a top quark?
-     379           0 : bool hasTop( const int & pid )
-     380             : {
-     381           0 :     if( extraBits(pid) > 0 ) { return false; }
-     382           0 :     if( fundamentalID(pid) > 0 ) { return false; }
-     383           0 :     return findQ(pid,6);
-     384             : }
-     385             : 
-     386             : // ---  other information
-     387             : //
-     388             : // jSpin returns 2J+1, where J is the total spin
-     389           0 : int  jSpin( const int & pid )
-     390             : {
-     391           0 :     if( fundamentalID(pid) > 0 ) { 
-     392             :         // some of these are known
-     393           0 :         int fund = fundamentalID(pid);
-     394           0 :         if( fund > 0 && fund < 7 ) return 2;
-     395           0 :         if( fund == 9 ) return 3; 
-     396           0 :         if( fund > 10 && fund < 17 ) return 2;
-     397           0 :         if( fund > 20 && fund < 25 ) return 3;
-     398           0 :         return 0; 
-     399           0 :     } else if( extraBits(pid) > 0 ) { 
-     400             :         return 0; 
-     401             :     }
-     402           0 :     return abspid(pid)%10;
-     403             : }
-     404             : // sSpin returns 2S+1, where S is the spin
-     405           0 : int  sSpin( const int & pid )
-     406             : {
-     407           0 :     if( !isMeson(pid) ) { return 0; }
-     408           0 :     int inl = digit(nl,pid);
-     409             :     //int tent = digit(n,pid);
-     410           0 :     int js = digit(nj,pid);
-     411           0 :     if( digit(n,pid) == 9 ) { return 0; }       // tentative ID
-     412             :     //if( tent == 9 ) { return 0; }     // tentative assignment
-     413           0 :     if( inl == 0 && js >= 3 ) { 
-     414             :         return 1;
-     415           0 :     } else if( inl == 0  && js == 1 ) {
-     416             :         return 0;
-     417           0 :     } else if( inl == 1  && js >= 3 ) {
-     418             :         return 0;
-     419           0 :     } else if( inl == 2  && js >= 3 ) {
-     420             :         return 1;
-     421           0 :     } else if( inl == 1  && js == 1 ) {
-     422             :         return 1;
-     423           0 :     } else if( inl == 3  && js >= 3 ) {
-     424           0 :         return 1;
-     425             :     }
-     426             :     // default to zero
-     427             :     return 0;
-     428             : }
-     429             : // lSpin returns 2L+1, where L is the orbital angular momentum
-     430           0 : int  lSpin( const int & pid )
-     431             : {
-     432           0 :     if( !isMeson(pid) ) { return 0; }
-     433           0 :     int inl = digit(nl,pid);
-     434             :     //int tent = digit(n,pid);
-     435           0 :     int js = digit(nj,pid);
-     436           0 :     if( digit(n,pid) == 9 ) { return 0; }       // tentative ID
-     437           0 :     if( inl == 0 && js == 3 ) { 
-     438             :         return 0;
-     439           0 :     } else if( inl == 0 && js == 5 ) {
-     440             :         return 1;
-     441           0 :     } else if( inl == 0 && js == 7 ) {
-     442             :         return 2;
-     443           0 :     } else if( inl == 0 && js == 9 ) {
-     444             :         return 3;
-     445           0 :     } else if( inl == 0  && js == 1 ) {
-     446             :         return 0;
-     447           0 :     } else if( inl == 1  && js == 3 ) {
-     448             :         return 1;
-     449           0 :     } else if( inl == 1  && js == 5 ) {
-     450             :         return 2;
-     451           0 :     } else if( inl == 1  && js == 7 ) {
-     452             :         return 3;
-     453           0 :     } else if( inl == 1  && js == 9 ) {
-     454             :         return 4;
-     455           0 :     } else if( inl == 2  && js == 3 ) {
-     456             :         return 1;
-     457           0 :     } else if( inl == 2  && js == 5 ) {
-     458             :         return 2;
-     459           0 :     } else if( inl == 2  && js == 7 ) {
-     460             :         return 3;
-     461           0 :     } else if( inl == 2  && js == 9 ) {
-     462             :         return 4;
-     463           0 :     } else if( inl == 1  && js == 1 ) {
-     464             :         return 1;
-     465           0 :     } else if( inl == 3  && js == 3 ) {
-     466             :         return 2;
-     467           0 :     } else if( inl == 3  && js == 5 ) {
-     468             :         return 3;
-     469           0 :     } else if( inl == 3  && js == 7 ) {
-     470             :         return 4;
-     471           0 :     } else if( inl == 3  && js == 9 ) {
-     472           0 :         return 5;
-     473             :     }
-     474             :     // default to zero
-     475             :     return 0;
-     476             : }
-     477             : 
-     478             : // 3 times the charge
-     479    20168252 : int threeCharge( const int & pid )
-     480             : {
-     481             :     int charge=0;
-     482             :     int ida, sid;
-     483             :     unsigned short q1, q2, q3, ql;
-     484             :     static int ch100[] = { -1, 2,-1, 2,-1, 2,-1, 2, 0, 0,
-     485             :                        -3, 0,-3, 0,-3, 0,-3, 0, 0, 0,
-     486             :                         0, 0, 0, 3, 0, 0, 0, 0, 0, 0,
-     487             :                         0, 0, 0, 3, 0, 0, 3, 0, 0, 0,
-     488             :                         0, -1, 0, 0, 0, 0, 0, 0, 0, 0,
-     489             :                         0, 6, 3, 6, 0, 0, 0, 0, 0, 0,
-     490             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
-     491             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
-     492             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
-     493             :                         0, 0, 0, 0, 0, 0, 0, 0, 0, 0 };
-     494    20168252 :     q1 = digit(nq1,pid);
-     495    20168249 :     q2 = digit(nq2,pid);
-     496    20168248 :     q3 = digit(nq3,pid);
-     497    20168250 :     ql = digit(nl,pid);
-     498    20168251 :     ida = abspid(pid);
-     499    20168250 :     sid = fundamentalID(pid);
-     500    20168244 :     if( ida == 0 ) {      // illegal
-     501             :         return 0;
-     502     3325563 :     } else if( isQBall(pid) ) {         // QBall
-     503           0 :        charge = 3*((abspid(pid)/10)%10000);
-     504     3325563 :     } else if( extraBits(pid) > 0 ) {                // ion
-     505             :         return 0;
-     506     3325562 :     } else if( isDyon(pid) ) {          // Dyon
-     507           0 :         charge = 3*( (abspid(pid)/10)%1000 );
-     508             :         // this is half right
-     509             :         // the charge sign will be changed below if pid < 0
-     510           0 :         if( ql == 2 ) {
-     511           0 :             charge = -charge; 
-     512             :         }
-     513     3325562 :     } else if( sid > 0 && sid <= 100 ) {  // use table
-     514     3325562 :         charge = ch100[sid-1];
-     515     3325562 :         if(ida==1000017 || ida==1000018) { charge = 0; }
-     516     3325562 :         if(ida==1000034 || ida==1000052) { charge = 0; }
-     517     3325562 :         if(ida==1000053 || ida==1000054) { charge = 0; }
-     518     3325562 :         if(ida==5100061 || ida==5100062) { charge = 6; }
-     519           0 :     } else if( digit(nj,pid) == 0 ) {           // KL, Ks, or undefined
-     520             :         return 0;
-     521           0 :     } else if( isMeson(pid) ) {                 // mesons
-     522           0 :             if( q2 == 3 || q2 == 5 ) {
-     523           0 :                 charge = ch100[q3-1] - ch100[q2-1];
-     524             :             } else {
-     525           0 :                 charge = ch100[q2-1] - ch100[q3-1];
-     526             :             }
-     527           0 :     } else if( isRhadron(pid) ) {               // Rhadron
-     528           0 :         if (( q1 == 0 ) || ( q1 == 9 )) {
-     529           0 :             if( q2 == 3 || q2 == 5 ) {
-     530           0 :                 charge = ch100[q3-1] - ch100[q2-1];
-     531             :             } else {
-     532           0 :                 charge = ch100[q2-1] - ch100[q3-1];
-     533             :             }
-     534           0 :         } else if( ql == 0 ) {
-     535           0 :             charge = ch100[q3-1] + ch100[q2-1] + ch100[q1-1];
-     536           0 :         } else if ( digit(nr,pid) == 0 ) {
-     537           0 :             charge = ch100[q3-1] + ch100[q2-1] + ch100[q1-1] + ch100[ql-1];
-     538             :         }
-     539           0 :     } else if( isDiQuark(pid) ) {                       // diquarks
-     540           0 :         charge = ch100[q2-1] + ch100[q1-1];
-     541           0 :     } else if( isBaryon(pid) ) {                        // baryons
-     542           0 :         charge = ch100[q3-1] + ch100[q2-1] + ch100[q1-1];
-     543             :     } else {            // unknown
-     544             :         return 0;
-     545             :     }
-     546     3325562 :     if( charge == 0 ) {
-     547     3310494 :         return 0;
-     548       15068 :     } else if( pid < 0 ) {
-     549        7103 :         charge = -charge; 
-     550             :     }
-     551             :     return charge;
-     552             : }
-     553             : 
-     554             : // the actual charge
-     555    20168251 : double charge( const int & pid )
-     556             : {
-     557    20168251 :    int tc = threeCharge(pid);
-     558    20168244 :    if( isQBall(pid) ) {
-     559           0 :        return double(tc)/30.;
-     560             :    } else {
-     561    20168248 :        return double(tc)/3.;
-     562             :    }
-     563             : }
-     564             : 
-     565             : } // HepPID
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html deleted file mode 100644 index 399175d29..000000000 --- a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleName.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - ParticleName.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01830.0 %
Date:2024-04-08 14:58:22Functions:0130.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID12_GLOBAL__N_116ParticleNameInitEv0
_ZN6HepPID12_GLOBAL__N_121writeParticleNameLineEiRSo0
_ZN6HepPID12_GLOBAL__N_123checkForSpecialParticleERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID12_GLOBAL__N_18dyonNameERKi0
_ZN6HepPID12_GLOBAL__N_19qballNameERKi0
_ZN6HepPID12particleNameB5cxx11ERKi0
_ZN6HepPID12particleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID15ParticleNameMapC2ESt3mapIiNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESt4lessIiESaISt4pairIKiS7_EEES1_IS7_iS8_IS7_ESaISA_IKS7_iEEE0
_ZN6HepPID15ParticleNameMapD2Ev0
_ZN6HepPID17listParticleNamesERSo0
_ZN6HepPID17validParticleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID17validParticleNameERKi0
_ZN6HepPID18getParticleNameMapEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html deleted file mode 100644 index 392fe15ed..000000000 --- a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleName.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - ParticleName.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01830.0 %
Date:2024-04-08 14:58:22Functions:0130.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID12_GLOBAL__N_116ParticleNameInitEv0
_ZN6HepPID12_GLOBAL__N_121writeParticleNameLineEiRSo0
_ZN6HepPID12_GLOBAL__N_123checkForSpecialParticleERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID12_GLOBAL__N_18dyonNameERKi0
_ZN6HepPID12_GLOBAL__N_19qballNameERKi0
_ZN6HepPID12particleNameB5cxx11ERKi0
_ZN6HepPID12particleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID15ParticleNameMapC2ESt3mapIiNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESt4lessIiESaISt4pairIKiS7_EEES1_IS7_iS8_IS7_ESaISA_IKS7_iEEE0
_ZN6HepPID15ParticleNameMapD2Ev0
_ZN6HepPID17listParticleNamesERSo0
_ZN6HepPID17validParticleNameERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN6HepPID17validParticleNameERKi0
_ZN6HepPID18getParticleNameMapEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html b/doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html deleted file mode 100644 index c67d5715b..000000000 --- a/doc/coverageReport/libs/HepPID/src/ParticleName.cc.gcov.html +++ /dev/null @@ -1,2075 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/ParticleName.cc - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - ParticleName.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01830.0 %
Date:2024-04-08 14:58:22Functions:0130.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : // ----------------------------------------------------------------------
-       2             : //
-       3             : // ParticleName.cc
-       4             : // Author: Lynn Garren and Walter Brown
-       5             : //
-       6             : //  Create a map that gives a standard name for each pre-defined 
-       7             : //  particle ID number.   Also create a map for the reverse lookup of 
-       8             : //  the ID number from a string.  These maps are initialized if and only if 
-       9             : //  the public functions are called. Because the maps are static, 
-      10             : //  the initialization happens only once.
-      11             : //
-      12             : //  The user NEVER calls ParticleNameInit()
-      13             : //  We use a data table (struct Snames) so that compile time is not impacted.
-      14             : //
-      15             : //  public functions:
-      16             : //     PartcleIdMap const &  getPartcleIdMap()
-      17             : //     std::string              ParticleName( const int pid )
-      18             : //     void                     listParticleNames( std::ostream & os  )
-      19             : //
-      20             : // ----------------------------------------------------------------------
-      21             : 
-      22             : #include <string>
-      23             : #include <map>
-      24             : #include <iostream>
-      25             : #include <sstream>
-      26             : #include <iomanip>        // width
-      27             : #include <utility>        // make_pair
-      28             : 
-      29             : #include "HepPID/ParticleName.hh"
-      30             : #include "HepPID/ParticleIDMethods.hh"
-      31             : #include "HepPID/Version.hh"
-      32             : 
-      33             : namespace HepPID {
-      34             : 
-      35             : typedef  std::map< int, std::string >  PartcleIdMap;
-      36             : typedef  std::map< std::string, int >  ParticleLookupMap;
-      37             : 
-      38             : ///
-      39             : /// \class ParticleNameMap
-      40             : /// \author Lynn Garren
-      41             : ///
-      42             : /// Used internally to store the static maps
-      43             : ///
-      44             : class ParticleNameMap{
-      45             : 
-      46             : public:
-      47             : 
-      48             :    typedef PartcleIdMap::const_iterator      idIterator;
-      49             :    typedef ParticleLookupMap::const_iterator nameIterator;
-      50             :    
-      51           0 :    ParticleNameMap(PartcleIdMap m1,ParticleLookupMap m2)
-      52           0 :    : itsNameMap(m1), itsLookupMap(m2) {}
-      53           0 :    ~ParticleNameMap() {}
-      54             :    
-      55             :    PartcleIdMap       nameMap()    const { return itsNameMap; }
-      56             :    ParticleLookupMap lookupMap()  const { return itsLookupMap; }
-      57             :    idIterator   begin()               const { return itsNameMap.begin(); }
-      58             :    idIterator   end()                 const { return itsNameMap.end(); }
-      59             :    idIterator   find( const int & id) const { return itsNameMap.find(id); }
-      60             :    nameIterator beginLookupMap()      const { return itsLookupMap.begin(); }
-      61             :    nameIterator endLookupMap()        const { return itsLookupMap.end(); }
-      62             :    nameIterator findString( const std::string & s) const { return itsLookupMap.find(s); }
-      63             : 
-      64             : private:
-      65             :    
-      66             :    PartcleIdMap       itsNameMap;
-      67             :    ParticleLookupMap itsLookupMap;
-      68             :    
-      69             :    // copies are not allowed
-      70             :    ParticleNameMap( const ParticleNameMap & );
-      71             :    ParticleNameMap & operator = ( const ParticleNameMap & );
-      72             :    
-      73             : };
-      74             : 
-      75             : namespace {     // ParticleNameInit and ParticleNameMap are private
-      76             : 
-      77           0 : ParticleNameMap const &  ParticleNameInit()
-      78             : {
-      79             : 
-      80             :   PartcleIdMap  m;
-      81             :   ParticleLookupMap nameMap;
-      82             : 
-      83             :   static const struct {
-      84             :       int pid;
-      85             :       const char* pname;
-      86             :   } SNames[] = {
-      87             :       {          0, "" },
-      88             :       {          1, "d" },
-      89             :       {         -1, "d~" },
-      90             :       {          2, "u" },
-      91             :       {         -2, "u~" },
-      92             :       {          3, "s" },
-      93             :       {         -3, "s~" },
-      94             :       {          4, "c" },
-      95             :       {         -4, "c~" },
-      96             :       {          5, "b" },
-      97             :       {         -5, "b~" },
-      98             :       {          6, "t" },
-      99             :       {         -6, "t~" },
-     100             :       {          7, "b'" },
-     101             :       {         -7, "b'~" },
-     102             :       {          8, "t'" },
-     103             :       {         -8, "t'~" },
-     104             :       {         11, "e^-" },
-     105             :       {        -11, "e^+" },
-     106             :       {         12, "nu_e" },
-     107             :       {        -12, "nu_e~" },
-     108             :       {         13, "mu^-" },
-     109             :       {        -13, "mu^+" },
-     110             :       {         14, "nu_mu" },
-     111             :       {        -14, "nu_mu~" },
-     112             :       {         15, "tau^-" },
-     113             :       {        -15, "tau^+" },
-     114             :       {         16, "nu_tau" },
-     115             :       {        -16, "nu_tau~" },
-     116             :       {         17, "tau'^-" },
-     117             :       {        -17, "tau'^+" },
-     118             :       {         18, "nu_tau'" },
-     119             :       {        -18, "nu_tau'~" },
-     120             :       {         21, "g" },
-     121             :       {         22, "gamma" },
-     122             :       {      10022, "virtual-photon" },
-     123             :       {      20022, "Cerenkov-radiation" },
-     124             :       {         23, "Z^0" },
-     125             :       {         24, "W^+" },
-     126             :       {        -24, "W^-" },
-     127             :       {         25, "H_1^0" },
-     128             :       {         32, "Z_2^0" },
-     129             :       {         33, "Z_3^0" },
-     130             :       {         34, "W_2^+" },
-     131             :       {        -34, "W_2^-" },
-     132             :       {         35, "H_2^0" },
-     133             :       {         36, "H_3^0" },
-     134             :       {         37, "H^+" },
-     135             :       {        -37, "H^-" },
-     136             :       {         39, "G"  },
-     137             :       {         41, "R^0" },
-     138             :       {        -41, "R~^0" },
-     139             :       {         42, "LQ_c" },
-     140             :       {        -42, "LQ_c~" },
-     141             :       {         43, "Xu^0" },
-     142             :       {         44, "Xu^+" },
-     143             :       {        -44, "Xu^-" },
-     144             :       {         51, "H_L^0" },
-     145             :       {         52, "H_1^++" },
-     146             :       {        -52, "H_1^--" },
-     147             :       {         53, "H_2^+" },
-     148             :       {        -53, "H_2^-" },
-     149             :       {         54, "H_2^++" },
-     150             :       {        -54, "H_2^--" },
-     151             :       {         55, "H_4^0" },
-     152             :       {        -55, "H_4~^0" },
-     153             :       {         81, "generator-specific+81" },
-     154             :       {         82, "generator-specific+82" },
-     155             :       {         83, "generator-specific+83" },
-     156             :       {         84, "generator-specific+84" },
-     157             :       {         85, "generator-specific+85" },
-     158             :       {         86, "generator-specific+86" },
-     159             :       {         87, "generator-specific+87" },
-     160             :       {         88, "generator-specific+88" },
-     161             :       {         89, "generator-specific+89" },
-     162             :       {         90, "generator-specific+90" },
-     163             :       {         91, "generator-specific+91" },
-     164             :       {         92, "generator-specific+92" },
-     165             :       {         93, "generator-specific+93" },
-     166             :       {         94, "generator-specific+94" },
-     167             :       {         95, "generator-specific+95" },
-     168             :       {         96, "generator-specific+96" },
-     169             :       {         97, "generator-specific+97" },
-     170             :       {         98, "generator-specific+98" },
-     171             :       {         99, "generator-specific+99" },
-     172             :       {        -81, "generator-specific-81" },
-     173             :       {        -82, "generator-specific-82" },
-     174             :       {        -83, "generator-specific-83" },
-     175             :       {        -84, "generator-specific-84" },
-     176             :       {        -85, "generator-specific-85" },
-     177             :       {        -86, "generator-specific-86" },
-     178             :       {        -87, "generator-specific-87" },
-     179             :       {        -88, "generator-specific-88" },
-     180             :       {        -89, "generator-specific-89" },
-     181             :       {        -90, "generator-specific-90" },
-     182             :       {        -91, "generator-specific-91" },
-     183             :       {        -92, "generator-specific-92" },
-     184             :       {        -93, "generator-specific-93" },
-     185             :       {        -94, "generator-specific-94" },
-     186             :       {        -95, "generator-specific-95" },
-     187             :       {        -96, "generator-specific-96" },
-     188             :       {        -97, "generator-specific-97" },
-     189             :       {        -98, "generator-specific-98" },
-     190             :       {        -99, "generator-specific-99" },
-     191             :       {        100, "generator-specific+100" },
-     192             :       {       -100, "generator-specific-100" },
-     193             :       {        101, "geantino" },
-     194             :       {        102, "charged-geantino" },
-     195             :       {        110, "reggeon" },
-     196             :       {        130, "K_L^0" },
-     197             :       {        310, "K_S^0" },
-     198             :       {        990, "pomeron" },
-     199             :       {       9990, "odderon" },
-     200             :       {    1000001, "susy-d_L" },
-     201             :       {   -1000001, "susy-d_L~" },
-     202             :       {    1000002, "susy-u_L" },
-     203             :       {   -1000002, "susy-u_L~" },
-     204             :       {    1000003, "susy-s_L" },
-     205             :       {   -1000003, "susy-s_L~" },
-     206             :       {    1000004, "susy-c_L" },
-     207             :       {   -1000004, "susy-c_L~" },
-     208             :       {    1000005, "susy-b_1" },
-     209             :       {   -1000005, "susy-b_1~" },
-     210             :       {    1000006, "susy-t_1" },
-     211             :       {   -1000006, "susy-t_1~" },
-     212             :       {    1000011, "susy-e_L^-" },
-     213             :       {   -1000011, "susy-e_L^+" },
-     214             :       {    1000012, "susy-nu_eL" },
-     215             :       {   -1000012, "susy-nu_eL~" },
-     216             :       {    1000013, "susy-mu_L^-" },
-     217             :       {   -1000013, "susy-mu_L^+" },
-     218             :       {    1000014, "susy-nu_muL" },
-     219             :       {   -1000014, "susy-nu_muL~" },
-     220             :       {    1000015, "susy-tau_L^-" },
-     221             :       {   -1000015, "susy-tau_L^+" },
-     222             :       {    1000016, "susy-nu_tauL" },
-     223             :       {   -1000016, "susy-nu_tauL~" },
-     224             :       {    1000021, "gluino" },
-     225             :       {    1000022, "susy-chi_1^0" },
-     226             :       {    1000023, "susy-chi_2^0" },
-     227             :       {    1000024, "susy-chi_1^+" },
-     228             :       {   -1000024, "susy-chi_1^-" },
-     229             :       {    1000025, "susy-chi_3^0" },
-     230             :       {    1000035, "susy-chi_4^0" },
-     231             :       {    1000037, "susy-chi_2^+" },
-     232             :       {   -1000037, "susy-chi_2^-" },
-     233             :       {    1000039, "gravitino" },
-     234             :       {    2000001, "susy-d_R" },
-     235             :       {   -2000001, "susy-d_R~" },
-     236             :       {    2000002, "susy-u_R" },
-     237             :       {   -2000002, "susy-u_R~" },
-     238             :       {    2000003, "susy-s_R" },
-     239             :       {   -2000003, "susy-s_R~" },
-     240             :       {    2000004, "susy-c_R" },
-     241             :       {   -2000004, "susy-c_R~" },
-     242             :       {    2000005, "susy-b_R" },
-     243             :       {   -2000005, "susy-b_R~" },
-     244             :       {    2000006, "susy-t_R" },
-     245             :       {   -2000006, "susy-t_R~" },
-     246             :       {    2000011, "susy-e_R^-" },
-     247             :       {   -2000011, "susy-e_R^+" },
-     248             :       {    2000012, "susy-nu_eR" },
-     249             :       {   -2000012, "susy-nu_eR~" },
-     250             :       {    2000013, "susy-mu_R^-" },
-     251             :       {   -2000013, "susy-mu_R^+" },
-     252             :       {    2000014, "susy-nu_muR" },
-     253             :       {   -2000014, "susy-nu_muR~" },
-     254             :       {    2000015, "susy-tau_R^-" },
-     255             :       {   -2000015, "susy-tau_R^+" },
-     256             :       {    2000016, "susy-nu_tauR" },
-     257             :       {   -2000016, "susy-nu_tauR~" },
-     258             :       {    3100021, "V8_tech" },
-     259             :       {   -3100021, "V8_tech~" },
-     260             :       {    3000111, "pi_tech^0" },
-     261             :       {    3000115, "a_tech^0" },
-     262             :       {    3060111, "pi_tech_22_1" },
-     263             :       {    3160111, "pi_tech_22_8" },
-     264             :       {    3000113, "rho_tech^0" },
-     265             :       {    3130113, "rho_tech_11" },
-     266             :       {    3140113, "rho_tech_12" },
-     267             :       {    3150113, "rho_tech_21" },
-     268             :       {    3160113, "rho_tech_22" },
-     269             :       {    3000211, "pi_tech^+" },
-     270             :       {   -3000211, "pi_tech^-" },
-     271             :       {    3000213, "rho_tech^+" },
-     272             :       {   -3000213, "rho_tech^-" },
-     273             :       {    3000215, "a_tech^+" },
-     274             :       {   -3000215, "a_tech^-" },
-     275             :       {    3000221, "pi'_tech" },
-     276             :       {    3100221, "eta_tech" },
-     277             :       {    3000223, "omega_tech" },
-     278             :       {    4000001, "d*" },
-     279             :       {   -4000001, "d*~" },
-     280             :       {    4000002, "u*" },
-     281             :       {   -4000002, "u*~" },
-     282             :       {    4000011, "e*^-" },
-     283             :       {   -4000011, "e*^+" },
-     284             :       {    4000012, "nu*_e" },
-     285             :       {   -4000012, "nu*_e~" },
-     286             :       {    4000039, "G*" },
-     287             :       {   -4000039, "G*~" },
-     288             :       {    5000040, "black_hole" },
-     289             :       {    5100001, "d_L^(1)" },
-     290             :       {   -5100001, "d~_L^(1)" },
-     291             :       {    5100002, "u_L^(1)" },
-     292             :       {   -5100002, "u~_L^(1)" },
-     293             :       {    5100003, "s_L^(1)" },
-     294             :       {   -5100003, "s~_L^(1)" },
-     295             :       {    5100004, "c_L^(1)" },
-     296             :       {   -5100004, "c~_L^(1)" },
-     297             :       {    5100005, "b_L^(1)" },
-     298             :       {   -5100005, "b~_L^(1)" },
-     299             :       {    5100006, "t_L^(1)" },
-     300             :       {   -5100006, "t~_L^(1)" },
-     301             :       {    5100011, "e_L^(1)-" },
-     302             :       {   -5100011, "e_L^(1)+" },
-     303             :       {    5100012, "nu_eL^(1)" },
-     304             :       {   -5100012, "nu_eL~^(1)" },
-     305             :       {    5100013, "mu_L^(1)-" },
-     306             :       {   -5100013, "mu_L^(1)+" },
-     307             :       {    5100014, "nu_muL^(1)" },
-     308             :       {   -5100014, "nu_muL~^(1)" },
-     309             :       {    5100015, "tau_L^(1)-" },
-     310             :       {   -5100015, "tau_L^(1)+" },
-     311             :       {    5100016, "nu_tauL^(1)" },
-     312             :       {   -5100016, "nu_tauL~^(1)" },
-     313             :       {    6100001, "d_R^(1)" },
-     314             :       {   -6100001, "d~_R^(1)" },
-     315             :       {    6100002, "u_R^(1)" },
-     316             :       {   -6100002, "u~_R^(1)" },
-     317             :       {    6100003, "s_R^(1)" },
-     318             :       {   -6100003, "s~_R^(1)" },
-     319             :       {    6100004, "c_R^(1)" },
-     320             :       {   -6100004, "c~_R^(1)" },
-     321             :       {    6100005, "b_R^(1)" },
-     322             :       {   -6100005, "b~_R^(1)" },
-     323             :       {    6100006, "t_R^(1)" },
-     324             :       {   -6100006, "t~_R^(1)" },
-     325             :       {    6100011, "e_R^(1)-" },
-     326             :       {   -6100011, "e_R^(1)+" },
-     327             :       {    6100012, "nu_eR^(1)" },
-     328             :       {   -6100012, "nu_eR~^(1)" },
-     329             :       {    6100013, "mu_R^(1)-" },
-     330             :       {   -6100013, "mu_R^(1)+" },
-     331             :       {    6100014, "nu_muR^(1)" },
-     332             :       {   -6100014, "nu_muR~^(1)" },
-     333             :       {    6100015, "tau_R^(1)-" },
-     334             :       {   -6100015, "tau_R^(1)+" },
-     335             :       {    6100016, "nu_tauR^(1)" },
-     336             :       {   -6100016, "nu_tauR~^(1)" },
-     337             :       {    5100021, "g^(1)" },
-     338             :       {    5100022, "gamma^(1)" },
-     339             :       {    5100023, "Z^(1)0" },
-     340             :       {    5100024, "W^(1)+" },
-     341             :       {   -5100024, "W^(1)-" },
-     342             :       {    5100025, "h^(1)0" },
-     343             :       {    5100039, "G^(1)" },
-     344             :       {    9900012, "nu_Re" },
-     345             :       {   -9900012, "nu_Re~" },
-     346             :       {    9900014, "nu_Rmu" },
-     347             :       {   -9900014, "nu_Rmu~" },
-     348             :       {    9900016, "nu_Rtau" },
-     349             :       {   -9900016, "nu_Rtau~" },
-     350             :       {    9900023, "Z_R^0" },
-     351             :       {   -9900023, "Z_R~^0" },
-     352             :       {    9900024, "W_R^+" },
-     353             :       {   -9900024, "W_R^-" },
-     354             :       {    9900041, "H_L^++" },
-     355             :       {   -9900041, "H_L^--" },
-     356             :       {    9900042, "H_R^++" },
-     357             :       {   -9900042, "H_R^--" },
-     358             :       {    9910113, "rho_diffr^0" },
-     359             :       {    9910211, "pi_diffr^+" },
-     360             :       {   -9910211, "pi_diffr^-" },
-     361             :       {    9910223, "omega_diffr" },
-     362             :       {    9910333, "phi_diffr" },
-     363             :       {    9910443, "psi_diffr" },
-     364             :       {    9912112, "n_diffr^0" },
-     365             :       {   -9912112, "n_diffr~^0" },
-     366             :       {    9912212, "p_diffr^+" },
-     367             :       {   -9912212, "p_diffr~^-" },
-     368             :       {    9920022, "remnant photon" },
-     369             :       {    9922212, "remnant nucleon" },
-     370             :       {   -9922212, "remnant nucleon~" },
-     371             :       {    9900441, "cc~[1S08]" },     
-     372             :       {    9910441, "cc~[3P08]" },     
-     373             :       {    9900443, "cc~[3S18]" },     
-     374             :       {    9900551, "bb~[1S08]" },     
-     375             :       {    9910551, "bb~[3P08]" },     
-     376             :       {    9900553, "bb~[3S18]" },    
-     377             :       {       1103, "dd_1" },
-     378             :       {      -1103, "dd_1~" },
-     379             :       {       2101, "ud_0" },
-     380             :       {      -2101, "ud_0~" },
-     381             :       {       2103, "ud_1" },
-     382             :       {      -2103, "ud_1~" },
-     383             :       {       2203, "uu_1" },
-     384             :       {      -2203, "uu_1~" },
-     385             :       {       3101, "sd_0" },
-     386             :       {      -3101, "sd_0~" },
-     387             :       {       3103, "sd_1" },
-     388             :       {      -3103, "sd_1~" },
-     389             :       {       3201, "su_0" },
-     390             :       {      -3201, "su_0~" },
-     391             :       {       3203, "su_1" },
-     392             :       {      -3203, "su_1~" },
-     393             :       {       3303, "ss_1" },
-     394             :       {      -3303, "ss_1~" },
-     395             :       {       4101, "cd_0" },
-     396             :       {      -4101, "cd_0~" },
-     397             :       {       4103, "cd_1" },
-     398             :       {      -4103, "cd_1~" },
-     399             :       {       4201, "cu_0" },
-     400             :       {      -4201, "cu_0~" },
-     401             :       {       4203, "cu_1" },
-     402             :       {      -4203, "cu_1~" },
-     403             :       {       4301, "cs_0" },
-     404             :       {      -4301, "cs_0~" },
-     405             :       {       4303, "cs_1" },
-     406             :       {      -4303, "cs_1~" },
-     407             :       {       4403, "cc_1" },
-     408             :       {      -4403, "cc_1~" },
-     409             :       {       5101, "bd_0" },
-     410             :       {      -5101, "bd_0~" },
-     411             :       {       5103, "bd_1" },
-     412             :       {      -5103, "bd_1~" },
-     413             :       {       5201, "bu_0" },
-     414             :       {      -5201, "bu_0~" },
-     415             :       {       5203, "bu_1" },
-     416             :       {      -5203, "bu_1~" },
-     417             :       {       5301, "bs_0" },
-     418             :       {      -5301, "bs_0~" },
-     419             :       {       5303, "bs_1" },
-     420             :       {      -5303, "bs_1~" },
-     421             :       {       5401, "bc_0" },
-     422             :       {      -5401, "bc_0~" },
-     423             :       {       5403, "bc_1" },
-     424             :       {      -5403, "bc_1~" },
-     425             :       {       5503, "bb_1" },
-     426             :       {      -5503, "bb_1~" },
-     427             :       {       6101, "td_0" },
-     428             :       {      -6101, "td_0~" },
-     429             :       {       6103, "td_1" },
-     430             :       {      -6103, "td_1~" },
-     431             :       {       6201, "tu_0" },
-     432             :       {      -6201, "tu_0~" },
-     433             :       {       6203, "tu_1" },
-     434             :       {      -6203, "tu_1~" },
-     435             :       {       6301, "ts_0" },
-     436             :       {      -6301, "ts_0~" },
-     437             :       {       6303, "ts_1" },
-     438             :       {      -6303, "ts_1~" },
-     439             :       {       6401, "tc_0" },
-     440             :       {      -6401, "tc_0~" },
-     441             :       {       6403, "tc_1" },
-     442             :       {      -6403, "tc_1~" },
-     443             :       {       6501, "tb_0" },
-     444             :       {      -6501, "tb_0~" },
-     445             :       {       6503, "tb_1" },
-     446             :       {      -6503, "tb_1~" },
-     447             :       {       6603, "tt_1" },
-     448             :       {      -6603, "tt_1~" },
-     449             :       {       7101, "b'd_0" },
-     450             :       {      -7101, "b'd_0~" },
-     451             :       {       7103, "b'd_1" },
-     452             :       {      -7103, "b'd_1~" },
-     453             :       {       7201, "b'u_0" },
-     454             :       {      -7201, "b'u_0~" },
-     455             :       {       7203, "b'u_1" },
-     456             :       {      -7203, "b'u_1~" },
-     457             :       {       7301, "b's_0" },
-     458             :       {      -7301, "b's_0~" },
-     459             :       {       7303, "b's_1" },
-     460             :       {      -7303, "b's_1~" },
-     461             :       {       7401, "b'c_0" },
-     462             :       {      -7401, "b'c_0~" },
-     463             :       {       7403, "b'c_1" },
-     464             :       {      -7403, "b'c_1~" },
-     465             :       {       7501, "b'b_0" },
-     466             :       {      -7501, "b'b_0~" },
-     467             :       {       7503, "b'b_1" },
-     468             :       {      -7503, "b'b_1~" },
-     469             :       {       7601, "b't_0" },
-     470             :       {      -7601, "b't_0~" },
-     471             :       {       7603, "b't_1" },
-     472             :       {      -7603, "b't_1~" },
-     473             :       {       7703, "b'b'_1" },
-     474             :       {      -7703, "b'b'_1~" },
-     475             :       {       8101, "t'd_0" },
-     476             :       {      -8101, "t'd_0~" },
-     477             :       {       8103, "t'd_1" },
-     478             :       {      -8103, "t'd_1~" },
-     479             :       {       8201, "t'u_0" },
-     480             :       {      -8201, "t'u_0~" },
-     481             :       {       8203, "t'u_1" },
-     482             :       {      -8203, "t'u_1~" },
-     483             :       {       8301, "t's_0" },
-     484             :       {      -8301, "t's_0~" },
-     485             :       {       8303, "t's_1" },
-     486             :       {      -8303, "t's_1~" },
-     487             :       {       8401, "t'c_0" },
-     488             :       {      -8401, "t'c_0~" },
-     489             :       {       8403, "t'c_1" },
-     490             :       {      -8403, "t'c_1~" },
-     491             :       {       8501, "t'b_0" },
-     492             :       {      -8501, "t'b_0~" },
-     493             :       {       8503, "t'b_1" },
-     494             :       {      -8503, "t'b_1~" },
-     495             :       {       8601, "t't_0" },
-     496             :       {      -8601, "t't_0~" },
-     497             :       {       8603, "t't_1" },
-     498             :       {      -8603, "t't_1~" },
-     499             :       {       8701, "t'b'_0" },
-     500             :       {      -8701, "t'b'_0~" },
-     501             :       {       8703, "t'b'_1" },
-     502             :       {      -8703, "t'b'_1~" },
-     503             :       {       8803, "t't'_1" },
-     504             :       {      -8803, "t't'_1~" },
-     505             :       {        111, "pi^0" },
-     506             :       {    9000111, "a_0(980)^0" },
-     507             :       {      10111, "a_0(1450)^0" },
-     508             :       {     100111, "pi(1300)^0" },
-     509             :       {    9010111, "pi(1800)^0" },
-     510             :       {        113, "rho(770)^0" },
-     511             :       {      10113, "b_1(1235)^0" },
-     512             :       {      20113, "a_1(1260)^0" },
-     513             :       {    9000113, "pi_1(1400)^0" },
-     514             :       {     100113, "rho(1450)^0" },
-     515             :       {    9010113, "pi_1(1600)^0" },
-     516             :       {    9020113, "a_1(1640)^0" },
-     517             :       {      30113, "rho(1700)^0" },
-     518             :       {    9030113, "rho(1900)^0" },
-     519             :       {    9040113, "rho(2150)^0" },
-     520             :       {        115, "a_2(1320)^0" },
-     521             :       {      10115, "pi_2(1670)^0" },
-     522             :       {    9000115, "a_2(1700)^0" },
-     523             :       {    9010115, "pi_2(2100)^0" },
-     524             :       {        117, "rho_3(1690)^0" },
-     525             :       {    9000117, "rho_3(1990)^0" },
-     526             :       {    9010117, "rho_3(2250)^0" },
-     527             :       {        119, "a_4(2040)^0" },
-     528             :       {        211, "pi^+" },
-     529             :       {       -211, "pi^-" },
-     530             :       {    9000211, "a_0(980)^+" },
-     531             :       {   -9000211, "a_0(980)^-" },
-     532             :       {      10211, "a_0(1450)^+" },
-     533             :       {     -10211, "a_0(1450)^-" },
-     534             :       {     100211, "pi(1300)^+" },
-     535             :       {    -100211, "pi(1300)^-" },
-     536             :       {    9010211, "pi(1800)^+" },
-     537             :       {   -9010211, "pi(1800)^-" },
-     538             :       {        213, "rho(770)^+" },
-     539             :       {       -213, "rho(770)^-" },
-     540             :       {      10213, "b_1(1235)^+" },
-     541             :       {     -10213, "b_1(1235)^-" },
-     542             :       {      20213, "a_1(1260)^+" },
-     543             :       {     -20213, "a_1(1260)^-" },
-     544             :       {    9000213, "pi_1(1400)^+" },
-     545             :       {   -9000213, "pi_1(1400)^-" },
-     546             :       {     100213, "rho(1450)^+" },
-     547             :       {    -100213, "rho(1450)^-" },
-     548             :       {    9010213, "pi_1(1600)^+" },
-     549             :       {   -9010213, "pi_1(1600)^-" },
-     550             :       {    9020213, "a_1(1640)^+" },
-     551             :       {   -9020213, "a_1(1640)^-" },
-     552             :       {      30213, "rho(1700)^+" },
-     553             :       {     -30213, "rho(1700)^-" },
-     554             :       {    9030213, "rho(1900)^+" },
-     555             :       {   -9030213, "rho(1900)^-" },
-     556             :       {    9040213, "rho(2150)^+" },
-     557             :       {   -9040213, "rho(2150)^-" },
-     558             :       {        215, "a_2(1320)^+" },
-     559             :       {       -215, "a_2(1320)^-" },
-     560             :       {      10215, "pi_2(1670)^+" },
-     561             :       {     -10215, "pi_2(1670)^-" },
-     562             :       {    9000215, "a_2(1700)^+" },
-     563             :       {   -9000215, "a_2(1700)^-" },
-     564             :       {    9010215, "pi_2(2100)^+" },
-     565             :       {   -9010215, "pi_2(2100)^-" },
-     566             :       {        217, "rho_3(1690)^+" },
-     567             :       {       -217, "rho_3(1690)^-" },
-     568             :       {    9000217, "rho_3(1990)^+" },
-     569             :       {   -9000217, "rho_3(1990)^-" },
-     570             :       {    9010217, "rho_3(2250)^+" },
-     571             :       {   -9010217, "rho_3(2250)^-" },
-     572             :       {        219, "a_4(2040)^+" },
-     573             :       {       -219, "a_4(2040)^-" },
-     574             :       {        221, "eta" },
-     575             :       {    9000221, "f_0(600)" },
-     576             :       {      10221, "f_0(1370)" },
-     577             :       {    9010221, "f_0(980)" },
-     578             :       {    9020221, "eta(1405)" },
-     579             :       {    9030221, "f_0(1500)" },
-     580             :       {    9040221, "eta(1760)" },
-     581             :       {    9050221, "f_0(2020)" },
-     582             :       {    9060221, "f_0(2100)" },
-     583             :       {    9070221, "f_0(2200)" },
-     584             :       {    9080221, "eta(2225)" },
-     585             :       {    9090221, "sigma_0" },
-     586             :       {     100221, "eta(1295)" },
-     587             :       {        331, "eta'(958)" },
-     588             :       {      10331, "f_0(1710)" },
-     589             :       {     100331, "eta(1475)" },
-     590             :       {        223, "omega(782)" },
-     591             :       {    9000223, "f_1(1510)" },
-     592             :       {    9010223, "h_1(1595)" },
-     593             :       {      10223, "h_1(1170)" },
-     594             :       {      20223, "f_1(1285)" },
-     595             :       {      30223, "omega(1650)" },
-     596             :       {     100223, "omega(1420)" },
-     597             :       {        333, "phi(1020)" },
-     598             :       {      10333, "h_1(1380)" },
-     599             :       {      20333, "f_1(1420)" },
-     600             :       {     100333, "phi(1680)" },
-     601             :       {        225, "f_2(1270)" },
-     602             :       {    9000225, "f_2(1430)" },
-     603             :       {      10225, "eta_2(1645)" },
-     604             :       {    9010225, "f_2(1565)" },
-     605             :       {    9020225, "f_2(1640)" },
-     606             :       {    9030225, "f_2(1810)" },
-     607             :       {    9040225, "f_2(1910)" },
-     608             :       {    9050225, "f_2(1950)" },
-     609             :       {    9060225, "f_2(2010)" },
-     610             :       {    9070225, "f_2(2150)" },
-     611             :       {    9080225, "f_2(2300)" },
-     612             :       {    9090225, "f_2(2340)" },
-     613             :       {        335, "f'_2(1525)" },
-     614             :       {      10335, "eta_2(1870)" },
-     615             :       {        227, "omega_3(1670)" },
-     616             :       {        337, "phi_3(1850)" },
-     617             :       {        229, "f_4(2050)" },
-     618             :       {    9000229, "f_J(2220)" },
-     619             :       {    9010229, "f_4(2300)" },
-     620             :       {        311, "K^0" },
-     621             :       {       -311, "K~^0" },
-     622             :       {    9000311, "K*_0(800)^0" },
-     623             :       {   -9000311, "K*_0(800)~^0" },
-     624             :       {      10311, "K*_0(1430)^0" },
-     625             :       {     -10311, "K*_0(1430)~^0" },
-     626             :       {     100311, "K(1460)^0" },
-     627             :       {    -100311, "K(1460)~^0" },
-     628             :       {    9010311, "K(1830)^0" },
-     629             :       {   -9010311, "K(1830)~^0" },
-     630             :       {    9020311, "K*_0(1950)^0" },
-     631             :       {   -9020311, "K*_0(1950)~^0" },
-     632             :       {        321, "K^+" },
-     633             :       {       -321, "K^-" },
-     634             :       {    9000321, "K*_0(800)^+" },
-     635             :       {   -9000321, "K*_0(800)^-" },
-     636             :       {      10321, "K*_0(1430)^+" },
-     637             :       {     -10321, "K*_0(1430)^-" },
-     638             :       {     100321, "K(1460)^+" },
-     639             :       {    -100321, "K(1460)^-" },
-     640             :       {    9010321, "K(1830)^+" },
-     641             :       {   -9010321, "K(1830)^-" },
-     642             :       {    9020321, "K*_0(1950)^+" },
-     643             :       {   -9020321, "K*_0(1950)^-" },
-     644             :       {        313, "K*(892)^0" },
-     645             :       {       -313, "K*(892)~^0" },
-     646             :       {      10313, "K_1(1270)^0" },
-     647             :       {     -10313, "K_1(1270)~^0" },
-     648             :       {      20313, "K_1(1400)^0" },
-     649             :       {     -20313, "K_1(1400)~^0" },
-     650             :       {      30313, "K*(1680)^0" },
-     651             :       {     -30313, "K*(1680)~^0" },
-     652             :       {     100313, "K*(1410)^0" },
-     653             :       {    -100313, "K*(1410)~^0" },
-     654             :       {    9000313, "K_1(1650)^0" },
-     655             :       {   -9000313, "K_1(1650)~^0" },
-     656             :       {        323, "K*(892)^+" },
-     657             :       {       -323, "K*(892)^-" },
-     658             :       {      10323, "K_1(1270)^+" },
-     659             :       {     -10323, "K_1(1270)^-" },
-     660             :       {      20323, "K_1(1400)^+" },
-     661             :       {     -20323, "K_1(1400)^-" },
-     662             :       {      30323, "K*(1680)^+" },
-     663             :       {     -30323, "K*(1680)^-" },
-     664             :       {     100323, "K*(1410)^+" },
-     665             :       {    -100323, "K*(1410)^-" },
-     666             :       {    9000323, "K_1(1650)^+" },
-     667             :       {   -9000323, "K_1(1650)^-" },
-     668             :       {        315, "K*_2(1430)^0" },
-     669             :       {       -315, "K*_2(1430)~^0" },
-     670             :       {    9000315, "K_2(1580)^0" },
-     671             :       {   -9000315, "K_2(1580)~^0" },
-     672             :       {      10315, "K_2(1770)^0" },
-     673             :       {     -10315, "K_2(1770)~^0" },
-     674             :       {    9010315, "K*_2(1980)^0" },
-     675             :       {   -9010315, "K*_2(1980)~^0" },
-     676             :       {    9020315, "K_2(2250)^0" },
-     677             :       {   -9020315, "K_2(2250)~^0" },
-     678             :       {      20315, "K_2(1820)^0" },
-     679             :       {     -20315, "K_2(1820)~^0" },
-     680             :       {        325, "K*_2(1430)^+" },
-     681             :       {       -325, "K*_2(1430)^-" },
-     682             :       {    9000325, "K_2(1580)^+" },
-     683             :       {   -9000325, "K_2(1580)^-" },
-     684             :       {      10325, "K_2(1770)^+" },
-     685             :       {     -10325, "K_2(1770)^-" },
-     686             :       {    9010325, "K*_2(1980)^+" },
-     687             :       {   -9010325, "K*_2(1980)^-" },
-     688             :       {    9020325, "K_2(2250)^+" },
-     689             :       {   -9020325, "K_2(2250)^-" },
-     690             :       {      20325, "K_2(1820)^+" },
-     691             :       {     -20325, "K_2(1820)^-" },
-     692             :       {     100325, "K_2(1980)^+" },
-     693             :       {    -100325, "K_2(1980)^-" },
-     694             :       {        317, "K*_3(1780)^0" },
-     695             :       {       -317, "K*_3(1780)~^0" },
-     696             :       {    9010317, "K_3(2320)^0" },
-     697             :       {   -9010317, "K_3(2320)~^0" },
-     698             :       {        327, "K*_3(1780)^+" },
-     699             :       {       -327, "K*_3(1780)^-" },
-     700             :       {    9010327, "K_3(2320)^+" },
-     701             :       {   -9010327, "K_3(2320)^-" },
-     702             :       {        319, "K*_4(2045)^0" },
-     703             :       {       -319, "K*_4(2045)~^0" },
-     704             :       {    9000319, "K_4(2500)^0" },
-     705             :       {   -9000319, "K_4(2500)~^0" },
-     706             :       {        329, "K*_4(2045)^+" },
-     707             :       {       -329, "K*_4(2045)^-" },
-     708             :       {    9000329, "K_4(2500)^+" },
-     709             :       {   -9000329, "K_4(2500)^-" },
-     710             :       {        411, "D^+" },
-     711             :       {       -411, "D^-" },
-     712             :       {      10411, "D*_0(2400)^+" },
-     713             :       {     -10411, "D*_0(2400)^-" },
-     714             :       {     100411, "D(2S)^+" },
-     715             :       {    -100411, "D(2S)^-" },
-     716             :       {        413, "D*(2010)^+" },
-     717             :       {       -413, "D*(2010)^-" },
-     718             :       {      10413, "D_1(2420)^+" },
-     719             :       {     -10413, "D_1(2420)^-" },
-     720             :       {      20413, "D_1(H)^+" },
-     721             :       {     -20413, "D_1(H)^-" },
-     722             :       {     100413, "D*(2S)^+" },
-     723             :       {    -100413, "D*(2S)^-" },
-     724             :       {        415, "D*_2(2460)^+" },
-     725             :       {       -415, "D*_2(2460)^-" },
-     726             :       {        421, "D^0" },
-     727             :       {       -421, "D~^0" },
-     728             :       {      10421, "D*_0(2400)^0" },
-     729             :       {     -10421, "D*_0(2400)~^0" },
-     730             :       {     100421, "D(2S)^0" },
-     731             :       {    -100421, "D(2S)~^0" },
-     732             :       {        423, "D*(2007)^0" },
-     733             :       {       -423, "D*(2007)~^0" },
-     734             :       {      10423, "D_1(2420)^0" },
-     735             :       {     -10423, "D_1(2420)~^0" },
-     736             :       {      20423, "D_1(2430)^0" },
-     737             :       {     -20423, "D_1(2430)~^0" },
-     738             :       {     100423, "D*(2S)^0" },
-     739             :       {    -100423, "D*(2S)~^0" },
-     740             :       {        425, "D*_2(2460)^0" },
-     741             :       {       -425, "D*_2(2460)~^0" },
-     742             :       {        431, "D_s^+" },
-     743             :       {       -431, "D_s^-" },
-     744             :       {      10431, "D*_s0(2317)^+" },
-     745             :       {     -10431, "D*_s0(2317)^-" },
-     746             :       {        433, "D*_s^+" },
-     747             :       {       -433, "D*_s^-" },
-     748             :       {      10433, "D_s1(2536)^+" },
-     749             :       {     -10433, "D_s1(2536)^-" },
-     750             :       {      20433, "D_s1(2460)^+" },
-     751             :       {     -20433, "D_s1(2460)^-" },
-     752             :       {        435, "D*_s2(2573)^+" },
-     753             :       {       -435, "D*_s2(2573)^-" },
-     754             :       {        441, "eta_c(1S)" },
-     755             :       {      10441, "chi_c0(1P)" },
-     756             :       {     100441, "eta_c(2S)" },
-     757             :       {        443, "J/psi(1S)" },
-     758             :       {    9000443, "psi(4040)" },
-     759             :       {      10443, "hc(1P)" },
-     760             :       {    9010443, "psi(4160)" },
-     761             :       {      20443, "chi_c1(1P)" },
-     762             :       {    9020443, "psi(4415)" },
-     763             :       {      30443, "psi(3770)" },
-     764             :       {     100443, "psi(2S)" },
-     765             :       {        445, "chi_c2(1P)" },
-     766             :       {     100445, "chi_c2(2P)" },
-     767             :       {        511, "B^0" },
-     768             :       {       -511, "B~^0" },
-     769             :       {      10511, "B*_0^0" },
-     770             :       {     -10511, "B*_0~^0" },
-     771             :       {        513, "B*^0" },
-     772             :       {       -513, "B*~^0" },
-     773             :       {      10513, "B_1(L)^0" },
-     774             :       {     -10513, "B_1(L)~^0" },
-     775             :       {      20513, "B_1(H)^0" },
-     776             :       {     -20513, "B_1(H)~^0" },
-     777             :       {        515, "B*_2^0" },
-     778             :       {       -515, "B*_2~^0" },
-     779             :       {        521, "B^+" },
-     780             :       {       -521, "B^-" },
-     781             :       {      10521, "B*_0^+" },
-     782             :       {     -10521, "B*_0^-" },
-     783             :       {        523, "B*^+" },
-     784             :       {       -523, "B*^-" },
-     785             :       {      10523, "B_1(L)^+" },
-     786             :       {     -10523, "B_1(L)^-" },
-     787             :       {      20523, "B_1(H)^+" },
-     788             :       {     -20523, "B_1(H)^-" },
-     789             :       {        525, "B*_2^+" },
-     790             :       {       -525, "B*_2^-" },
-     791             :       {        531, "B_s^0" },
-     792             :       {       -531, "B_s~^0" },
-     793             :       {      10531, "B*_s0^0" },
-     794             :       {     -10531, "B*_s0~^0" },
-     795             :       {        533, "B*_s^0" },
-     796             :       {       -533, "B*_s~^0" },
-     797             :       {      10533, "B_s1(L)^0" },
-     798             :       {     -10533, "B_s1(L)~^0" },
-     799             :       {      20533, "B_s1(H)^0" },
-     800             :       {     -20533, "B_s1(H)~^0" },
-     801             :       {        535, "B*_s2^0" },
-     802             :       {       -535, "B*_s2~^0" },
-     803             :       {        541, "B_c^+" },
-     804             :       {       -541, "B_c^-" },
-     805             :       {      10541, "B*_c0^+" },
-     806             :       {     -10541, "B*_c0^-" },
-     807             :       {        543, "B*_c^+" },
-     808             :       {       -543, "B*_c^-" },
-     809             :       {      10543, "B_c1(L)^+" },
-     810             :       {     -10543, "B_c1(L)^-" },
-     811             :       {      20543, "B_c1(H)^+" },
-     812             :       {     -20543, "B_c1(H)^-" },
-     813             :       {        545, "B*_c2^+" },
-     814             :       {       -545, "B*_c2^-" },
-     815             :       {        551, "eta_b(1S)" },
-     816             :       {      10551, "chi_b0(1P)" },
-     817             :       {     100551, "eta_b(2S)" },
-     818             :       {     110551, "chi_b0(2P)" },
-     819             :       {     200551, "eta_b(3S)" },
-     820             :       {     210551, "chi_b0(3P)" },
-     821             :       {        553, "Upsilon(1S)" },
-     822             :       {    9000553, "Upsilon(10860)" },
-     823             :       {      10553, "h_b(1P)" },
-     824             :       {    9010553, "Upsilon(11020)" },
-     825             :       {      20553, "chi_b1(1P)" },
-     826             :       {    9020553, "Upsilon(7S)" },
-     827             :       {      30553, "Upsilon_1(1D)" },
-     828             :       {     100553, "Upsilon(2S)" },
-     829             :       {     110553, "h_b(2P)" },
-     830             :       {     120553, "chi_b1(2P)" },
-     831             :       {     130553, "Upsilon_1(2D)" },
-     832             :       {     200553, "Upsilon(3S)" },
-     833             :       {     210553, "h_b(3P)" },
-     834             :       {     220553, "chi_b1(3P)" },
-     835             :       {     300553, "Upsilon(4S)" },
-     836             :       {        555, "chi_b2(1P)" },
-     837             :       {      10555, "eta_b2(1D)" },
-     838             :       {      20555, "Upsilon_2(1D)" },
-     839             :       {     100555, "chi_b2(2P)" },
-     840             :       {     110555, "eta_b2(2D)" },
-     841             :       {     120555, "Upsilon_2(2D)" },
-     842             :       {     200555, "chi_b2(3P)" },
-     843             :       {        557, "Upsilon_3(1D)" },
-     844             :       {     100557, "Upsilon_3(2D)" },
-     845             :       {        611, "T^+" },
-     846             :       {       -611, "T^-" },
-     847             :       {        613, "T*^+" },
-     848             :       {       -613, "T*^-" },
-     849             :       {        621, "T^0" },
-     850             :       {       -621, "T~^0" },
-     851             :       {        623, "T*^0" },
-     852             :       {       -623, "T*~^0" },
-     853             :       {        631, "T_s^+" },
-     854             :       {       -631, "T_s^-" },
-     855             :       {        633, "T*_s^+" },
-     856             :       {       -633, "T*_s^-" },
-     857             :       {        641, "T_c^0" },
-     858             :       {       -641, "T_c~^0" },
-     859             :       {        643, "T*_c^0" },
-     860             :       {       -643, "T*_c~^0" },
-     861             :       {        651, "T_b^+" },
-     862             :       {       -651, "T_b^-" },
-     863             :       {        653, "T*_b^+" },
-     864             :       {       -653, "T*_b^-" },
-     865             :       {        661, "eta_t" },
-     866             :       {        663, "theta" },
-     867             :       {        711, "L^0" },
-     868             :       {       -711, "L~^0" },
-     869             :       {        713, "L*^0" },
-     870             :       {       -713, "L*~^0" },
-     871             :       {        721, "L^-" },
-     872             :       {       -721, "L^+" },
-     873             :       {        723, "L*^-" },
-     874             :       {       -723, "L*^+" },
-     875             :       {        731, "L_s^0" },
-     876             :       {       -731, "L_s~^0" },
-     877             :       {        733, "L*_s^0" },
-     878             :       {       -733, "L*_s~^0" },
-     879             :       {        741, "L_c^-" },
-     880             :       {       -741, "L_c^+" },
-     881             :       {        743, "L*_c^-" },
-     882             :       {       -743, "L*_c^+" },
-     883             :       {        751, "L_b^0" },
-     884             :       {       -751, "L_b~^0" },
-     885             :       {        753, "L*_b^0" },
-     886             :       {       -753, "L*_b~^0" },
-     887             :       {        761, "L_t^-" },
-     888             :       {       -761, "L_t^+" },
-     889             :       {        763, "L*_t^-" },
-     890             :       {       -763, "L*_t^+" },
-     891             :       {        771, "eta_l" },
-     892             :       {        773, "theta_l" },
-     893             :       {        811, "X^+" },
-     894             :       {       -811, "X^-" },
-     895             :       {        813, "X*^+" },
-     896             :       {       -813, "X*^-" },
-     897             :       {        821, "X^0" },
-     898             :       {       -821, "X~^0" },
-     899             :       {        823, "X*^0" },
-     900             :       {       -823, "X*~^0" },
-     901             :       {        831, "X_s^+" },
-     902             :       {       -831, "X_s^-" },
-     903             :       {        833, "X*_s^+" },
-     904             :       {       -833, "X*_s^-" },
-     905             :       {        841, "X_c^0" },
-     906             :       {       -841, "X_c~^0" },
-     907             :       {        843, "X*_c^0" },
-     908             :       {       -843, "X*_c~^0" },
-     909             :       {        851, "X_b^+" },
-     910             :       {       -851, "X_b^-" },
-     911             :       {        853, "X*_b^+" },
-     912             :       {       -853, "X*_b^-" },
-     913             :       {        861, "X_t^0" },
-     914             :       {       -861, "X_t~^0" },
-     915             :       {        863, "X*_t^0" },
-     916             :       {       -863, "X*_t~^0" },
-     917             :       {        871, "X_l^+" },
-     918             :       {       -871, "X_l^-" },
-     919             :       {        873, "X*_l^+" },
-     920             :       {       -873, "X*_l^-" },
-     921             :       {        881, "eta_h" },
-     922             :       {        883, "theta_H" },
-     923             :       {      30343, "Xsd" },
-     924             :       {     -30343, "anti-Xsd" },
-     925             :       {      30353, "Xsu" },
-     926             :       {     -30353, "anti-Xsu" },
-     927             :       {      30363, "Xss" },
-     928             :       {     -30363, "anti-Xss" },
-     929             :       {      30373, "Xdd" },
-     930             :       {     -30373, "anti-Xdd" },
-     931             :       {      30383, "Xdu" },
-     932             :       {     -30383, "anti-Xdu" },
-     933             :       {       2112, "n^0" },
-     934             :       {      -2112, "n~^0" },
-     935             :       {       2212, "p^+" },
-     936             :       {      -2212, "p~^-" },
-     937             :     {        12212,        "N(1440)^+"},
-     938             :     {        12112,        "N(1440)^0"},
-     939             :     {        22212,        "N(1535)^+"},
-     940             :     {        22112,        "N(1535)^0"},
-     941             :     {        32212,        "N(1650)^+"},
-     942             :     {        32112,        "N(1650)^0"},
-     943             :     {        42212,        "N(1710)^+"},
-     944             :     {        42112,        "N(1710)^0"},
-     945             :     {         1214,         "N(1520)^0"},
-     946             :     {         2124,         "N(1520)^+"},
-     947             :     {        21214,        "N(1700)^0"},
-     948             :     {        22124,        "N(1700)^+"},
-     949             :     {        31214,        "N(1720)^0"},
-     950             :     {        32124,        "N(1720)^+"},
-     951             :     {         2116,         "N(1675)^0"},
-     952             :     {         2216,         "N(1675)^+"},
-     953             :     {        12116,        "N(1680)^0"},
-     954             :     {        12216,        "N(1680)^+"},
-     955             :     {         1218,         "N(2190)^0"},
-     956             :     {         2128,        "N(2190)^+" },
-     957             :       {       1114, "Delta^-" },
-     958             :       {      -1114, "Delta~^+" },
-     959             :       {       2114, "Delta^0" },
-     960             :       {      -2114, "Delta~^0" },
-     961             :       {       2214, "Delta^+" },
-     962             :       {      -2214, "Delta~^-" },
-     963             :       {       2224, "Delta^++" },
-     964             :       {      -2224, "Delta~^--" },
-     965             :     {        31114,   "Delta(1600)^-"      },
-     966             :     {        32114,   "Delta(1600)^0"      },
-     967             :     {        32214,    "Delta(1600)^+"     },
-     968             :     {        32224,     "Delta(1600)^++"    },
-     969             :     {         1112,    "Delta(1620)^-"     },
-     970             :     {         1212,    "Delta(1620)^0"     },
-     971             :     {         2122,    "Delta(1620)^+"     },
-     972             :     {         2222,     "Delta(1620)^++"    },
-     973             :     {        11114,     "Delta(1700)^-"    },
-     974             :     {        12114,     "Delta(1700)^0"    },
-     975             :     {        12214,     "Delta(1700)^+"    },
-     976             :     {        12224,      "Delta(1700)^++"   },
-     977             :     {         1116,     "Delta(1905)^-"    },
-     978             :     {         1216,     "Delta(1905)^0"    },
-     979             :     {         2126,     "Delta(1905)^+"    },
-     980             :     {         2226,      "Delta(1905)^++"   },
-     981             :     {        21112,    "Delta(1910)^-"    },
-     982             :     {        21212,     "Delta(1910)^0"   },
-     983             :     {        22122,     "Delta(1910)^+"   },
-     984             :     {        22222,     "Delta(1910)^++"   },
-     985             :     {        21114,    "Delta(1920)^-"    },
-     986             :     {        22114,     "Delta(1920)^0"   },
-     987             :     {        22214,     "Delta(1920)^+"   },
-     988             :     {        22224,    "Delta(1920)^++"    },
-     989             :     {        11116,    "Delta(1930)^-"    },
-     990             :     {        11216,     "Delta(1930)^0"   },
-     991             :     {        12126,     "Delta(1930)^+"   },
-     992             :     {        12226,     "Delta(1930)^++"   },
-     993             :     {         1118,     "Delta(1950)^-"    },
-     994             :     {         2118,      "Delta(1950)^0"   },
-     995             :     {         2218,      "Delta(1950)^+"   },
-     996             :     {         2228,     "Delta(1950)^++"    },
-     997             :       {       3122, "Lambda^0" },
-     998             :       {      -3122, "Lambda~^0" },
-     999             :       {      13122, "Lambda(1405)^0" },
-    1000             :       {     -13122, "Lambda~(1405)^0" },
-    1001             :       {      23122, "Lambda(1600)^0" },
-    1002             :       {     -23122, "Lambda~(1600)^0" },
-    1003             :       {      33122, "Lambda(1670)^0" },
-    1004             :       {     -33122, "Lambda~(1670)^0" },
-    1005             :       {      43122, "Lambda(1800)^0" },
-    1006             :       {     -43122, "Lambda~(1800)^0" },
-    1007             :       {      53122, "Lambda(1810)^0" },
-    1008             :       {     -53122, "Lambda~(1810)^0" },
-    1009             :       {       3124, "Lambda(1520)^0" },
-    1010             :       {      -3124, "Lambda~(1520)^0" },
-    1011             :       {      13124, "Lambda(1690)^0" },
-    1012             :       {     -13124, "Lambda~(1690)^0" },
-    1013             :       {      23124, "Lambda(1890)^0" },
-    1014             :       {     -23124, "Lambda~(1890)^0" },
-    1015             :       {       3126, "Lambda(1820)^0" },
-    1016             :       {      -3126, "Lambda~(1820)^0" },
-    1017             :       {      13126, "Lambda(1830)^0" },
-    1018             :       {     -13126, "Lambda~(1830)^0" },
-    1019             :       {      23126, "Lambda(2110)^0" },
-    1020             :       {     -23126, "Lambda~(2110)^0" },
-    1021             :       {       3128, "Lambda(2100)^0" },
-    1022             :       {      -3128, "Lambda~(2100)^0" },
-    1023             :       {       3112, "Sigma^-" },
-    1024             :       {      -3112, "Sigma~^+" },
-    1025             :       {       3212, "Sigma^0" },
-    1026             :       {      -3212, "Sigma~^0" },
-    1027             :       {       3222, "Sigma^+" },
-    1028             :       {      -3222, "Sigma~^-" },
-    1029             :       {      13222, "Sigma(1660)^+" },
-    1030             :       {     -13222, "Sigma~(1660)^+" },
-    1031             :       {      13212, "Sigma(1660)^0" },
-    1032             :       {     -13212, "Sigma~(1660)^0" },
-    1033             :       {      13112, "Sigma(1660)^-" },
-    1034             :       {     -13112, "Sigma~(1660)^-" },
-    1035             :       {      23112, "Sigma(1750)^-" },
-    1036             :       {     -23112, "Sigma~(1750)^-" },
-    1037             :       {      23212, "Sigma(1750)^0" },
-    1038             :       {     -23212, "Sigma~(1750)^0" },
-    1039             :       {      23222, "Sigma(1750)^+" },
-    1040             :       {     -23222, "Sigma~(1750)^+" },
-    1041             :       {       3114, "Sigma*^-" },
-    1042             :       {      -3114, "Sigma*~^+" },
-    1043             :       {       3214, "Sigma*^0" },
-    1044             :       {      -3214, "Sigma*~^0" },
-    1045             :       {       3224, "Sigma*^+" },
-    1046             :       {      -3224, "Sigma*~^-" },
-    1047             :       {      13224, "Sigma(1670)^+" },
-    1048             :       {     -13224, "Sigma~(1670)^+" },
-    1049             :       {      13214, "Sigma(1670)^0" },
-    1050             :       {     -13214, "Sigma~(1670)^0" },
-    1051             :       {      13114, "Sigma(1670)^-" },
-    1052             :       {     -13114, "Sigma~(1670)^-" },
-    1053             :       {      23224, "Sigma(1940)^+" },
-    1054             :       {     -23224, "Sigma~(1940)^+" },
-    1055             :       {      23214, "Sigma(1940)^0" },
-    1056             :       {     -23214, "Sigma~(1940)^0" },
-    1057             :       {      23114, "Sigma(1940)^-" },
-    1058             :       {     -23114, "Sigma~(1940)^-" },
-    1059             :       {       3226, "Sigma(1775)^+" },
-    1060             :       {      -3226, "Sigma~(1775)^+" },
-    1061             :       {       3216, "Sigma(1775)^0" },
-    1062             :       {      -3216, "Sigma~(1775)^0" },
-    1063             :       {       3116, "Sigma(1775)^-" },
-    1064             :       {      -3116, "Sigma~(1775)^-" },
-    1065             :       {      13226, "Sigma(1915)^+" },
-    1066             :       {     -13226, "Sigma~(1915)^+" },
-    1067             :       {      13216, "Sigma(1915)^0" },
-    1068             :       {     -13216, "Sigma~(1915)^0" },
-    1069             :       {      13116, "Sigma(1915)^-" },
-    1070             :       {     -13116, "Sigma~(1915)^-" },
-    1071             :       {       3228, "Sigma(2030)^+" },
-    1072             :       {      -3228, "Sigma~(2030)^+" },
-    1073             :       {       3218, "Sigma(2030)^0" },
-    1074             :       {      -3218, "Sigma~(2030)^0" },
-    1075             :       {       3118, "Sigma(2030)^-" },
-    1076             :       {      -3118, "Sigma~(2030)^-" },
-    1077             :       {       3312, "Xi^-" },
-    1078             :       {      -3312, "Xi~^+" },
-    1079             :       {       3322, "Xi^0" },
-    1080             :       {      -3322, "Xi~^0" },
-    1081             :       {       3314, "Xi*^-" },
-    1082             :       {      -3314, "Xi*~^+" },
-    1083             :       {       3324, "Xi*^0" },
-    1084             :       {      -3324, "Xi*~^0" },
-    1085             :       {      13314, "Xi(1820)^-" },
-    1086             :       {     -13314, "Xi(1820)~^+" },
-    1087             :       {      13324, "Xi(1820)^0" },
-    1088             :       {     -13324, "Xi(1820)~^0" },
-    1089             :       {       3334, "Omega^-" },
-    1090             :       {      -3334, "Omega~^+" },
-    1091             :       {       4112, "Sigma_c^0" },
-    1092             :       {      -4112, "Sigma_c~^0" },
-    1093             :       {       4114, "Sigma*_c^0" },
-    1094             :       {      -4114, "Sigma*_c~^0" },
-    1095             :       {       4122, "Lambda_c^+" },
-    1096             :       {      -4122, "Lambda_c~^-" },
-    1097             :       {      14122, "Lambda_c(2593)^+" },
-    1098             :       {     -14122, "Lambda_c~(2593)^-" },
-    1099             :       {      14124, "Lambda_c(2625)^+" },
-    1100             :       {     -14124, "Lambda_c~(2625)^-" },
-    1101             :       {       4132, "Xi_c^0" },
-    1102             :       {      -4132, "Xi_c~^0" },
-    1103             :       {       4212, "Sigma_c^+" },
-    1104             :       {      -4212, "Sigma_c~^-" },
-    1105             :       {       4214, "Sigma*_c^+" },
-    1106             :       {      -4214, "Sigma*_c~^-" },
-    1107             :       {       4222, "Sigma_c^++" },
-    1108             :       {      -4222, "Sigma_c~^--" },
-    1109             :       {       4224, "Sigma*_c^++" },
-    1110             :       {      -4224, "Sigma*_c~^--" },
-    1111             :       {       4232, "Xi_c^+" },
-    1112             :       {      -4232, "Xi_c~^-" },
-    1113             :       {       4312, "Xi'_c^0" },
-    1114             :       {      -4312, "Xi'_c~^0" },
-    1115             :       {       4314, "Xi*_c^0" },
-    1116             :       {      -4314, "Xi*_c~^0" },
-    1117             :       {       4322, "Xi'_c^+" },
-    1118             :       {      -4322, "Xi'_c~^-" },
-    1119             :       {       4324, "Xi*_c^+" },
-    1120             :       {      -4324, "Xi*_c~^-" },
-    1121             :       {       4332, "Omega_c^0" },
-    1122             :       {      -4332, "Omega_c~^0" },
-    1123             :       {       4334, "Omega*_c^0" },
-    1124             :       {      -4334, "Omega*_c~^0" },
-    1125             :       {       4412, "Xi_cc^+" },
-    1126             :       {      -4412, "Xi_cc~^-" },
-    1127             :       {       4414, "Xi*_cc^+" },
-    1128             :       {      -4414, "Xi*_cc~^-" },
-    1129             :       {       4422, "Xi_cc^++" },
-    1130             :       {      -4422, "Xi_cc~^--" },
-    1131             :       {       4424, "Xi*_cc^++" },
-    1132             :       {      -4424, "Xi*_cc~^--" },
-    1133             :       {       4432, "Omega_cc^+" },
-    1134             :       {      -4432, "Omega_cc~^-" },
-    1135             :       {       4434, "Omega*_cc^+" },
-    1136             :       {      -4434, "Omega*_cc~^-" },
-    1137             :       {       4444, "Omega*_ccc^++" },
-    1138             :       {      -4444, "Omega*_ccc~^--" },
-    1139             :       {       5112, "Sigma_b^-" },
-    1140             :       {      -5112, "Sigma_b~^+" },
-    1141             :       {       5114, "Sigma*_b^-" },
-    1142             :       {      -5114, "Sigma*_b~^+" },
-    1143             :       {       5122, "Lambda_b^0" },
-    1144             :       {      -5122, "Lambda_b~^0" },
-    1145             :       {       5132, "Xi_b^-" },
-    1146             :       {      -5132, "Xi_b~^+" },
-    1147             :       {       5142, "Xi_bc^0" },
-    1148             :       {      -5142, "Xi_bc~^0" },
-    1149             :       {       5212, "Sigma_b^0" },
-    1150             :       {      -5212, "Sigma_b~^0" },
-    1151             :       {       5214, "Sigma*_b^0" },
-    1152             :       {      -5214, "Sigma*_b~^0" },
-    1153             :       {       5222, "Sigma_b^+" },
-    1154             :       {      -5222, "Sigma_b~^-" },
-    1155             :       {       5224, "Sigma*_b^+" },
-    1156             :       {      -5224, "Sigma*_b~^-" },
-    1157             :       {       5232, "Xi_b^0" },
-    1158             :       {      -5232, "Xi_b~^0" },
-    1159             :       {       5242, "Xi_bc^+" },
-    1160             :       {      -5242, "Xi_bc~^-" },
-    1161             :       {       5312, "Xi'_b^-" },
-    1162             :       {      -5312, "Xi'_b~^+" },
-    1163             :       {       5314, "Xi*_b^-" },
-    1164             :       {      -5314, "Xi*_b~^+" },
-    1165             :       {       5322, "Xi'_b^0" },
-    1166             :       {      -5322, "Xi'_b~^0" },
-    1167             :       {       5324, "Xi*_b^0" },
-    1168             :       {      -5324, "Xi*_b~^0" },
-    1169             :       {       5332, "Omega_b^-" },
-    1170             :       {      -5332, "Omega_b~^+" },
-    1171             :       {       5334, "Omega*_b^-" },
-    1172             :       {      -5334, "Omega*_b~^+" },
-    1173             :       {       5342, "Omega_bc^0" },
-    1174             :       {      -5342, "Omega_bc~^0" },
-    1175             :       {       5412, "Xi'_bc^0" },
-    1176             :       {      -5412, "Xi'_bc~^0" },
-    1177             :       {       5414, "Xi*_bc^0" },
-    1178             :       {      -5414, "Xi*_bc~^0" },
-    1179             :       {       5422, "Xi'_bc^+" },
-    1180             :       {      -5422, "Xi'_bc~^-" },
-    1181             :       {       5424, "Xi*_bc^+" },
-    1182             :       {      -5424, "Xi*_bc~^-" },
-    1183             :       {       5432, "Omega'_bc^0" },
-    1184             :       {      -5432, "Omega'_bc~^0" },
-    1185             :       {       5434, "Omega*_bc^0" },
-    1186             :       {      -5434, "Omega*_bc~^0" },
-    1187             :       {       5442, "Omega_bcc^+" },
-    1188             :       {      -5442, "Omega_bcc~^-" },
-    1189             :       {       5444, "Omega*_bcc^+" },
-    1190             :       {      -5444, "Omega*_bcc~^-" },
-    1191             :       {       5512, "Xi_bb^-" },
-    1192             :       {      -5512, "Xi_bb~^+" },
-    1193             :       {       5514, "Xi*_bb^-" },
-    1194             :       {      -5514, "Xi*_bb~^+" },
-    1195             :       {       5522, "Xi_bb^0" },
-    1196             :       {      -5522, "Xi_bb~^0" },
-    1197             :       {       5524, "Xi*_bb^0" },
-    1198             :       {      -5524, "Xi*_bb~^0" },
-    1199             :       {       5532, "Omega_bb^-" },
-    1200             :       {      -5532, "Omega_bb~^+" },
-    1201             :       {       5534, "Omega*_bb^-" },
-    1202             :       {      -5534, "Omega*_bb~^+" },
-    1203             :       {       5542, "Omega_bbc^0" },
-    1204             :       {      -5542, "Omega_bbc~^0" },
-    1205             :       {       5544, "Omega*_bbc^0" },
-    1206             :       {      -5544, "Omega*_bbc~^0" },
-    1207             :       {       5554, "Omega*_bbb^-" },
-    1208             :       {      -5554, "Omega*_bbb~^+" },
-    1209             :       {       6112, "Sigma_t^0" },
-    1210             :       {      -6112, "Sigma_t~^0" },
-    1211             :       {       6114, "Sigma*_t^0" },
-    1212             :       {      -6114, "Sigma*_t~^0" },
-    1213             :       {       6122, "Lambda_t^+" },
-    1214             :       {      -6122, "Lambda_t~^-" },
-    1215             :       {       6132, "Xi_t^0" },
-    1216             :       {      -6132, "Xi_t~^0" },
-    1217             :       {       6142, "Xi_tc^+" },
-    1218             :       {      -6142, "Xi_tc~^-" },
-    1219             :       {       6152, "Xi_tb^0" },
-    1220             :       {      -6152, "Xi_tb~^0" },
-    1221             :       {       6212, "Sigma_t^+" },
-    1222             :       {      -6212, "Sigma_t~^-" },
-    1223             :       {       6214, "Sigma*_t^+" },
-    1224             :       {      -6214, "Sigma*_t~^-" },
-    1225             :       {       6222, "Sigma_t^++" },
-    1226             :       {      -6222, "Sigma_t~^--" },
-    1227             :       {       6224, "Sigma*_t^++" },
-    1228             :       {      -6224, "Sigma*_t~^--" },
-    1229             :       {       6232, "Xi_t^+" },
-    1230             :       {      -6232, "Xi_t~^-" },
-    1231             :       {       6242, "Xi_tc^++" },
-    1232             :       {      -6242, "Xi_tc~^--" },
-    1233             :       {       6252, "Xi_tb^+" },
-    1234             :       {      -6252, "Xi_tb~^-" },
-    1235             :       {       6312, "Xi'_t^0" },
-    1236             :       {      -6312, "Xi'_t~^0" },
-    1237             :       {       6314, "Xi*_t^0" },
-    1238             :       {      -6314, "Xi*_t~^0" },
-    1239             :       {       6322, "Xi'_t^+" },
-    1240             :       {      -6322, "Xi'_t~^-" },
-    1241             :       {       6324, "Xi*_t^+" },
-    1242             :       {      -6324, "Xi*_t~^-" },
-    1243             :       {       6332, "Omega_t^0" },
-    1244             :       {      -6332, "Omega_t~^0" },
-    1245             :       {       6334, "Omega*_t^0" },
-    1246             :       {      -6334, "Omega*_t~^0" },
-    1247             :       {       6342, "Omega_tc^+" },
-    1248             :       {      -6342, "Omega_tc~^-" },
-    1249             :       {       6352, "Omega_tb^0" },
-    1250             :       {      -6352, "Omega_tb~^0" },
-    1251             :       {       6412, "Xi'_tc^+" },
-    1252             :       {      -6412, "Xi'_tc~^-" },
-    1253             :       {       6414, "Xi*_tc^+" },
-    1254             :       {      -6414, "Xi*_tc~^-" },
-    1255             :       {       6422, "Xi'_tc^++" },
-    1256             :       {      -6422, "Xi'_tc~^--" },
-    1257             :       {       6424, "Xi*_tc^++" },
-    1258             :       {      -6424, "Xi*_tc~^--" },
-    1259             :       {       6432, "Omega'_tc^+" },
-    1260             :       {      -6432, "Omega'_tc~^-" },
-    1261             :       {       6434, "Omega*_tc^+" },
-    1262             :       {      -6434, "Omega*_tc~^-" },
-    1263             :       {       6442, "Omega_tcc^++" },
-    1264             :       {      -6442, "Omega_tcc~^--" },
-    1265             :       {       6444, "Omega*_tcc^++" },
-    1266             :       {      -6444, "Omega*_tcc~^--" },
-    1267             :       {       6452, "Omega_tbc^+" },
-    1268             :       {      -6452, "Omega_tbc~^-" },
-    1269             :       {       6512, "Xi'_tb^0" },
-    1270             :       {      -6512, "Xi'_tb~^0" },
-    1271             :       {       6514, "Xi*_tb^0" },
-    1272             :       {      -6514, "Xi*_tb~^0" },
-    1273             :       {       6522, "Xi'_tb^+" },
-    1274             :       {      -6522, "Xi'_tb~^-" },
-    1275             :       {       6524, "Xi*_tb^+" },
-    1276             :       {      -6524, "Xi*_tb~^-" },
-    1277             :       {       6532, "Omega'_tb^0" },
-    1278             :       {      -6532, "Omega'_tb~^0" },
-    1279             :       {       6534, "Omega*_tb^0" },
-    1280             :       {      -6534, "Omega*_tb~^0" },
-    1281             :       {       6542, "Omega'_tbc^+" },
-    1282             :       {      -6542, "Omega'_tbc~^-" },
-    1283             :       {       6544, "Omega*_tbc^+" },
-    1284             :       {      -6544, "Omega*_tbc~^-" },
-    1285             :       {       6552, "Omega_tbb^0" },
-    1286             :       {      -6552, "Omega_tbb~^0" },
-    1287             :       {       6554, "Omega*_tbb^0" },
-    1288             :       {      -6554, "Omega*_tbb~^0" },
-    1289             :       {       6612, "Xi_tt^+" },
-    1290             :       {      -6612, "Xi_tt~^-" },
-    1291             :       {       6614, "Xi*_tt^+" },
-    1292             :       {      -6614, "Xi*_tt~^-" },
-    1293             :       {       6622, "Xi_tt^++" },
-    1294             :       {      -6622, "Xi_tt~^--" },
-    1295             :       {       6624, "Xi*_tt^++" },
-    1296             :       {      -6624, "Xi*_tt~^--" },
-    1297             :       {       6632, "Omega_tt^+" },
-    1298             :       {      -6632, "Omega_tt~^-" },
-    1299             :       {       6634, "Omega*_tt^+" },
-    1300             :       {      -6634, "Omega*_tt~^-" },
-    1301             :       {       6642, "Omega_ttc^++" },
-    1302             :       {      -6642, "Omega_ttc~^--" },
-    1303             :       {       6644, "Omega*_ttc^++" },
-    1304             :       {      -6644, "Omega*_ttc~^--" },
-    1305             :       {       6652, "Omega_ttb^+" },
-    1306             :       {      -6652, "Omega_ttb~^-" },
-    1307             :       {       6654, "Omega*_ttb^+" },
-    1308             :       {      -6654, "Omega*_ttb~^-" },
-    1309             :       {       6664, "Omega*_ttt^++" },
-    1310             :       {      -6664, "Omega*_ttt~^--" },
-    1311             :       {       7112, "Sigma_b'^-" },
-    1312             :       {      -7112, "Sigma_b'~^+" },
-    1313             :       {       7114, "Sigma*_b'^-" },
-    1314             :       {      -7114, "Sigma*_b'~^+" },
-    1315             :       {       7122, "Lambda_b'^0" },
-    1316             :       {      -7122, "Lambda_b'~^0" },
-    1317             :       {       7132, "Xi_b'^-" },
-    1318             :       {      -7132, "Xi_b'~^+" },
-    1319             :       {       7142, "Xi_b'c^0" },
-    1320             :       {      -7142, "Xi_b'c~^0" },
-    1321             :       {       7152, "Xi_b'b^-" },
-    1322             :       {      -7152, "Xi_b'b~^+" },
-    1323             :       {       7162, "Xi_b't^0" },
-    1324             :       {      -7162, "Xi_b't~^0" },
-    1325             :       {       7212, "Sigma_b'^0" },
-    1326             :       {      -7212, "Sigma_b'~^0" },
-    1327             :       {       7214, "Sigma*_b'^0" },
-    1328             :       {      -7214, "Sigma*_b'~^0" },
-    1329             :       {       7222, "Sigma_b'^+" },
-    1330             :       {      -7222, "Sigma_b'~^-" },
-    1331             :       {       7224, "Sigma*_b'^+" },
-    1332             :       {      -7224, "Sigma*_b'~^-" },
-    1333             :       {       7232, "Xi_b'^0" },
-    1334             :       {      -7232, "Xi_b'~^0" },
-    1335             :       {       7242, "Xi_b'c^+" },
-    1336             :       {      -7242, "Xi_b'c~^-" },
-    1337             :       {       7252, "Xi_b'b^0" },
-    1338             :       {      -7252, "Xi_b'b~^0" },
-    1339             :       {       7262, "Xi_b't^+" },
-    1340             :       {      -7262, "Xi_b't~^-" },
-    1341             :       {       7312, "Xi'_b'^-" },
-    1342             :       {      -7312, "Xi'_b'~^+" },
-    1343             :       {       7314, "Xi*_b'^-" },
-    1344             :       {      -7314, "Xi*_b'~^+" },
-    1345             :       {       7322, "Xi'_b'^0" },
-    1346             :       {      -7322, "Xi'_b'~^0" },
-    1347             :       {       7324, "Xi*_b'^0" },
-    1348             :       {      -7324, "Xi*_b'~^0" },
-    1349             :       {       7332, "Omega'_b'^-" },
-    1350             :       {      -7332, "Omega'_b'~^+" },
-    1351             :       {       7334, "Omega*_b'^-" },
-    1352             :       {      -7334, "Omega*_b'~^+" },
-    1353             :       {       7342, "Omega_b'c^0" },
-    1354             :       {      -7342, "Omega_b'c~^0" },
-    1355             :       {       7352, "Omega_b'b^-" },
-    1356             :       {      -7352, "Omega_b'b~^+" },
-    1357             :       {       7362, "Omega_b't^0" },
-    1358             :       {      -7362, "Omega_b't~^0" },
-    1359             :       {       7412, "Xi'_b'c^0" },
-    1360             :       {      -7412, "Xi'_b'c~^0" },
-    1361             :       {       7414, "Xi*_b'c^0" },
-    1362             :       {      -7414, "Xi*_b'c~^0" },
-    1363             :       {       7422, "Xi'_b'c^+" },
-    1364             :       {      -7422, "Xi'_b'c~^-" },
-    1365             :       {       7424, "Xi*_b'c^+" },
-    1366             :       {      -7424, "Xi*_b'c~^-" },
-    1367             :       {       7432, "Omega'_b'c^0" },
-    1368             :       {      -7432, "Omega'_b'c~^0" },
-    1369             :       {       7434, "Omega*_b'c^0" },
-    1370             :       {      -7434, "Omega*_b'c~^0" },
-    1371             :       {       7442, "Omega'_b'cc^+" },
-    1372             :       {      -7442, "Omega'_b'cc~^-" },
-    1373             :       {       7444, "Omega*_b'cc^+" },
-    1374             :       {      -7444, "Omega*_b'cc~^-" },
-    1375             :       {       7452, "Omega_b'bc^0" },
-    1376             :       {      -7452, "Omega_b'bc~^0" },
-    1377             :       {       7462, "Omega_b'tc^+" },
-    1378             :       {      -7462, "Omega_b'tc~^-" },
-    1379             :       {       7512, "Xi'_b'b^-" },
-    1380             :       {      -7512, "Xi'_b'b~^+" },
-    1381             :       {       7514, "Xi*_b'b^-" },
-    1382             :       {      -7514, "Xi*_b'b~^+" },
-    1383             :       {       7522, "Xi'_b'b^0" },
-    1384             :       {      -7522, "Xi'_b'b~^0" },
-    1385             :       {       7524, "Xi*_b'b^0" },
-    1386             :       {      -7524, "Xi*_b'b~^0" },
-    1387             :       {       7532, "Omega'_b'b^-" },
-    1388             :       {      -7532, "Omega'_b'b~^+" },
-    1389             :       {       7534, "Omega*_b'b^-" },
-    1390             :       {      -7534, "Omega*_b'b~^+" },
-    1391             :       {       7542, "Omega'_b'bc^0" },
-    1392             :       {      -7542, "Omega'_b'bc~^0" },
-    1393             :       {       7544, "Omega*_b'bc^0" },
-    1394             :       {      -7544, "Omega*_b'bc~^0" },
-    1395             :       {       7552, "Omega'_b'bb^-" },
-    1396             :       {      -7552, "Omega'_b'bb~^+" },
-    1397             :       {       7554, "Omega*_b'bb^-" },
-    1398             :       {      -7554, "Omega*_b'bb~^+" },
-    1399             :       {       7562, "Omega_b'tb^0" },
-    1400             :       {      -7562, "Omega_b'tb~^0" },
-    1401             :       {       7612, "Xi'_b't^0" },
-    1402             :       {      -7612, "Xi'_b't~^0" },
-    1403             :       {       7614, "Xi*_b't^0" },
-    1404             :       {      -7614, "Xi*_b't~^0" },
-    1405             :       {       7622, "Xi'_b't^+" },
-    1406             :       {      -7622, "Xi'_b't~^-" },
-    1407             :       {       7624, "Xi*_b't^+" },
-    1408             :       {      -7624, "Xi*_b't~^-" },
-    1409             :       {       7632, "Omega'_b't^0" },
-    1410             :       {      -7632, "Omega'_b't~^0" },
-    1411             :       {       7634, "Omega*_b't^0" },
-    1412             :       {      -7634, "Omega*_b't~^0" },
-    1413             :       {       7642, "Omega'_b'tc^+" },
-    1414             :       {      -7642, "Omega'_b'tc~^-" },
-    1415             :       {       7644, "Omega*_b'tc^+" },
-    1416             :       {      -7644, "Omega*_b'tc~^-" },
-    1417             :       {       7652, "Omega'_b'tb^0" },
-    1418             :       {      -7652, "Omega'_b'tb~^0" },
-    1419             :       {       7654, "Omega*_b'tb^0" },
-    1420             :       {      -7654, "Omega*_b'tb~^0" },
-    1421             :       {       7662, "Omega'_b'tt^+" },
-    1422             :       {      -7662, "Omega'_b'tt~^-" },
-    1423             :       {       7664, "Omega*_b'tt^+" },
-    1424             :       {      -7664, "Omega*_b'tt~^-" },
-    1425             :       {       7712, "Xi'_b'b'^-" },
-    1426             :       {      -7712, "Xi'_b'b'~^+" },
-    1427             :       {       7714, "Xi*_b'b'^-" },
-    1428             :       {      -7714, "Xi*_b'b'~^+" },
-    1429             :       {       7722, "Xi'_b'b'^0" },
-    1430             :       {      -7722, "Xi'_b'b'~^0" },
-    1431             :       {       7724, "Xi*_b'b'^0" },
-    1432             :       {      -7724, "Xi*_b'b'~^0" },
-    1433             :       {       7732, "Omega'_b'b'^-" },
-    1434             :       {      -7732, "Omega'_b'b'~^+" },
-    1435             :       {       7734, "Omega*_b'b'^-" },
-    1436             :       {      -7734, "Omega*_b'b'~^+" },
-    1437             :       {       7742, "Omega'_b'b'c^0" },
-    1438             :       {      -7742, "Omega'_b'b'c~^0" },
-    1439             :       {       7744, "Omega*_b'b'c^0" },
-    1440             :       {      -7744, "Omega*_b'b'c~^0" },
-    1441             :       {       7752, "Omega'_b'b'b^-" },
-    1442             :       {      -7752, "Omega'_b'b'b~^+" },
-    1443             :       {       7754, "Omega*_b'b'b^-" },
-    1444             :       {      -7754, "Omega*_b'b'b~^+" },
-    1445             :       {       7762, "Omega'_b'b't^0" },
-    1446             :       {      -7762, "Omega'_b'b't~^0" },
-    1447             :       {       7764, "Omega*_b'b't^0" },
-    1448             :       {      -7764, "Omega*_b'b't~^0" },
-    1449             :       {       7774, "Omega*_b'b'b'^-" },
-    1450             :       {      -7774, "Omega*_b'b'b'~^+" },
-    1451             :       {       8112, "Sigma_t'^0" },
-    1452             :       {      -8112, "Sigma_t'~^0" },
-    1453             :       {       8114, "Sigma*_t'^0" },
-    1454             :       {      -8114, "Sigma*_t'~^0" },
-    1455             :       {       8122, "Lambda_t'^+" },
-    1456             :       {      -8122, "Lambda_t'~^-" },
-    1457             :       {       8132, "Xi_t'^0" },
-    1458             :       {      -8132, "Xi_t'~^0" },
-    1459             :       {       8142, "Xi_t'c^+" },
-    1460             :       {      -8142, "Xi_t'c~^-" },
-    1461             :       {       8152, "Xi_t'b^0" },
-    1462             :       {      -8152, "Xi_t'b~^0" },
-    1463             :       {       8162, "Xi_t't^+" },
-    1464             :       {      -8162, "Xi_t't~^-" },
-    1465             :       {       8172, "Xi_t'b'^0" },
-    1466             :       {      -8172, "Xi_t'b'~^0" },
-    1467             :       {       8212, "Sigma_t'^+" },
-    1468             :       {      -8212, "Sigma_t'~^-" },
-    1469             :       {       8214, "Sigma*_t'^+" },
-    1470             :       {      -8214, "Sigma*_t'~^-" },
-    1471             :       {       8222, "Sigma_t'^++" },
-    1472             :       {      -8222, "Sigma_t'~^--" },
-    1473             :       {       8224, "Sigma*_t'^++" },
-    1474             :       {      -8224, "Sigma*_t'~^--" },
-    1475             :       {       8232, "Xi_t'^+" },
-    1476             :       {      -8232, "Xi_t'~^-" },
-    1477             :       {       8242, "Xi_t'c^++" },
-    1478             :       {      -8242, "Xi_t'c~^--" },
-    1479             :       {       8252, "Xi_t'b^+" },
-    1480             :       {      -8252, "Xi_t'b~^-" },
-    1481             :       {       8262, "Xi_t't^++" },
-    1482             :       {      -8262, "Xi_t't~^--" },
-    1483             :       {       8272, "Xi_t'b'^+" },
-    1484             :       {      -8272, "Xi_t'b'~^-" },
-    1485             :       {       8312, "Xi'_t'^0" },
-    1486             :       {      -8312, "Xi'_t'~^0" },
-    1487             :       {       8314, "Xi*_t'^0" },
-    1488             :       {      -8314, "Xi*_t'~^0" },
-    1489             :       {       8322, "Xi'_t'^+" },
-    1490             :       {      -8322, "Xi'_t'~^-" },
-    1491             :       {       8324, "Xi*_t'^+" },
-    1492             :       {      -8324, "Xi*_t'~^-" },
-    1493             :       {       8332, "Omega'_t'^0" },
-    1494             :       {      -8332, "Omega'_t'~^0" },
-    1495             :       {       8334, "Omega*_t'^0" },
-    1496             :       {      -8334, "Omega*_t'~^0" },
-    1497             :       {       8342, "Omega_t'c^+" },
-    1498             :       {      -8342, "Omega_t'c~^-" },
-    1499             :       {       8352, "Omega_t'b^0" },
-    1500             :       {      -8352, "Omega_t'b~^0" },
-    1501             :       {       8362, "Omega_t't^+" },
-    1502             :       {      -8362, "Omega_t't~^-" },
-    1503             :       {       8372, "Omega_t'b'^0" },
-    1504             :       {      -8372, "Omega_t'b'~^0" },
-    1505             :       {       8412, "Xi'_t'c^+" },
-    1506             :       {      -8412, "Xi'_t'c~^-" },
-    1507             :       {       8414, "Xi*_t'c^+" },
-    1508             :       {      -8414, "Xi*_t'c~^-" },
-    1509             :       {       8422, "Xi'_t'c^++" },
-    1510             :       {      -8422, "Xi'_t'c~^--" },
-    1511             :       {       8424, "Xi*_t'c^++" },
-    1512             :       {      -8424, "Xi*_t'c~^--" },
-    1513             :       {       8432, "Omega'_t'c^+" },
-    1514             :       {      -8432, "Omega'_t'c~^-" },
-    1515             :       {       8434, "Omega*_t'c^+" },
-    1516             :       {      -8434, "Omega*_t'c~^-" },
-    1517             :       {       8442, "Omega'_t'cc^++" },
-    1518             :       {      -8442, "Omega'_t'cc~^--" },
-    1519             :       {       8444, "Omega*_t'cc^++" },
-    1520             :       {      -8444, "Omega*_t'cc~^--" },
-    1521             :       {       8452, "Omega_t'bc^+" },
-    1522             :       {      -8452, "Omega_t'bc~^-" },
-    1523             :       {       8462, "Omega_t'tc^++" },
-    1524             :       {      -8462, "Omega_t'tc~^--" },
-    1525             :       {       8472, "Omega_t'b'c ^+" },
-    1526             :       {      -8472, "Omega_t'b'c ~^-" },
-    1527             :       {       8512, "Xi'_t'b^0" },
-    1528             :       {      -8512, "Xi'_t'b~^0" },
-    1529             :       {       8514, "Xi*_t'b^0" },
-    1530             :       {      -8514, "Xi*_t'b~^0" },
-    1531             :       {       8522, "Xi'_t'b^+" },
-    1532             :       {      -8522, "Xi'_t'b~^-" },
-    1533             :       {       8524, "Xi*_t'b^+" },
-    1534             :       {      -8524, "Xi*_t'b~^-" },
-    1535             :       {       8532, "Omega'_t'b^0" },
-    1536             :       {      -8532, "Omega'_t'b~^0" },
-    1537             :       {       8534, "Omega*_t'b^0" },
-    1538             :       {      -8534, "Omega*_t'b~^0" },
-    1539             :       {       8542, "Omega'_t'bc^+" },
-    1540             :       {      -8542, "Omega'_t'bc~^-" },
-    1541             :       {       8544, "Omega*_t'bc^+" },
-    1542             :       {      -8544, "Omega*_t'bc~^-" },
-    1543             :       {       8552, "Omega'_t'bb^0" },
-    1544             :       {      -8552, "Omega'_t'bb~^0" },
-    1545             :       {       8554, "Omega*_t'bb^0" },
-    1546             :       {      -8554, "Omega*_t'bb~^0" },
-    1547             :       {       8562, "Omega_t'tb^+" },
-    1548             :       {      -8562, "Omega_t'tb~^-" },
-    1549             :       {       8572, "Omega_t'b'b ^0" },
-    1550             :       {      -8572, "Omega_t'b'b ~^0" },
-    1551             :       {       8612, "Xi'_t't^+" },
-    1552             :       {      -8612, "Xi'_t't~^-" },
-    1553             :       {       8614, "Xi*_t't^+" },
-    1554             :       {      -8614, "Xi*_t't~^-" },
-    1555             :       {       8622, "Xi'_t't^++" },
-    1556             :       {      -8622, "Xi'_t't~^--" },
-    1557             :       {       8624, "Xi*_t't^++" },
-    1558             :       {      -8624, "Xi*_t't~^--" },
-    1559             :       {       8632, "Omega'_t't^+" },
-    1560             :       {      -8632, "Omega'_t't~^-" },
-    1561             :       {       8634, "Omega*_t't^+" },
-    1562             :       {      -8634, "Omega*_t't~^-" },
-    1563             :       {       8642, "Omega'_t'tc^++" },
-    1564             :       {      -8642, "Omega'_t'tc~^--" },
-    1565             :       {       8644, "Omega*_t'tc^++" },
-    1566             :       {      -8644, "Omega*_t'tc~^--" },
-    1567             :       {       8652, "Omega'_t'tb^+" },
-    1568             :       {      -8652, "Omega'_t'tb~^-" },
-    1569             :       {       8654, "Omega*_t'tb^+" },
-    1570             :       {      -8654, "Omega*_t'tb~^-" },
-    1571             :       {       8662, "Omega'_t'tt^++" },
-    1572             :       {      -8662, "Omega'_t'tt~^--" },
-    1573             :       {       8664, "Omega*_t'tt^++" },
-    1574             :       {      -8664, "Omega*_t'tt~^--" },
-    1575             :       {       8672, "Omega_t'b't ^+" },
-    1576             :       {      -8672, "Omega_t'b't ~^-" },
-    1577             :       {       8712, "Xi'_t'b'^0" },
-    1578             :       {      -8712, "Xi'_t'b'~^0" },
-    1579             :       {       8714, "Xi*_t'b'^0" },
-    1580             :       {      -8714, "Xi*_t'b'~^0" },
-    1581             :       {       8722, "Xi'_t'b'^+" },
-    1582             :       {      -8722, "Xi'_t'b'~^-" },
-    1583             :       {       8724, "Xi*_t'b'^+" },
-    1584             :       {      -8724, "Xi*_t'b'~^-" },
-    1585             :       {       8732, "Omega'_t'b'^0" },
-    1586             :       {      -8732, "Omega'_t'b'~^0" },
-    1587             :       {       8734, "Omega*_t'b'^0" },
-    1588             :       {      -8734, "Omega*_t'b'~^0" },
-    1589             :       {       8742, "Omega'_t'b'c^+" },
-    1590             :       {      -8742, "Omega'_t'b'c~^-" },
-    1591             :       {       8744, "Omega*_t'b'c^+" },
-    1592             :       {      -8744, "Omega*_t'b'c~^-" },
-    1593             :       {       8752, "Omega'_t'b'b^0" },
-    1594             :       {      -8752, "Omega'_t'b'b~^0" },
-    1595             :       {       8754, "Omega*_t'b'b^0" },
-    1596             :       {      -8754, "Omega*_t'b'b~^0" },
-    1597             :       {       8762, "Omega'_t'b't^+" },
-    1598             :       {      -8762, "Omega'_t'b't~^-" },
-    1599             :       {       8764, "Omega*_t'b't^+" },
-    1600             :       {      -8764, "Omega*_t'b't~^-" },
-    1601             :       {       8772, "Omega'_t'b'b'^0" },
-    1602             :       {      -8772, "Omega'_t'b'b'~^0" },
-    1603             :       {       8774, "Omega*_t'b'b'^0" },
-    1604             :       {      -8774, "Omega*_t'b'b'~^0" },
-    1605             :       {       8812, "Xi'_t't'^+" },
-    1606             :       {      -8812, "Xi'_t't'~^-" },
-    1607             :       {       8814, "Xi*_t't'^+" },
-    1608             :       {      -8814, "Xi*_t't'~^-" },
-    1609             :       {       8822, "Xi'_t't'^++" },
-    1610             :       {      -8822, "Xi'_t't'~^--" },
-    1611             :       {       8824, "Xi*_t't'^++" },
-    1612             :       {      -8824, "Xi*_t't'~^--" },
-    1613             :       {       8832, "Omega'_t't'^+" },
-    1614             :       {      -8832, "Omega'_t't'~^-" },
-    1615             :       {       8834, "Omega*_t't'^+" },
-    1616             :       {      -8834, "Omega*_t't'~^-" },
-    1617             :       {       8842, "Omega'_t't'c^++" },
-    1618             :       {      -8842, "Omega'_t't'c~^--" },
-    1619             :       {       8844, "Omega*_t't'c^++" },
-    1620             :       {      -8844, "Omega*_t't'c~^--" },
-    1621             :       {       8852, "Omega'_t't'b^+" },
-    1622             :       {      -8852, "Omega'_t't'b~^-" },
-    1623             :       {       8854, "Omega*_t't'b^+" },
-    1624             :       {      -8854, "Omega*_t't'b~^-" },
-    1625             :       {       8862, "Omega'_t't't^++" },
-    1626             :       {      -8862, "Omega'_t't't~^--" },
-    1627             :       {       8864, "Omega*_t't't^++" },
-    1628             :       {      -8864, "Omega*_t't't~^--" },
-    1629             :       {       8872, "Omega'_t't'b'^+" },
-    1630             :       {      -8872, "Omega'_t't'b'~^-" },
-    1631             :       {       8874, "Omega*_t't'b'^+" },
-    1632             :       {      -8874, "Omega*_t't'b'~^-" },
-    1633             :       {       8884, "Omega*_t't't'^++" },
-    1634             :       {      -8884, "Omega*_t't't'~^--" },
-    1635             :       {    9221132, "Theta^+" },
-    1636             :       {    9331122, "Phi^--" },
-    1637             :       {    1000993, "R_~gg^0" },
-    1638             :       {    1009113, "R_~gd~d^0" },
-    1639             :       {    1009213, "R_~gu~d^+" },
-    1640             :       {    1009223, "R_~gu~u^0" },
-    1641             :       {    1009313, "R_~gd~s^0" },
-    1642             :       {    1009323, "R_~gu~s^+" },
-    1643             :       {    1009333, "R_~gs~s^0" },
-    1644             :       {    1091114, "R_~gddd^-" },
-    1645             :       {    1092114, "R_~gudd^0" },
-    1646             :       {    1092214, "R_~guud^+" },
-    1647             :       {    1092224, "R_~guuu^++" },
-    1648             :       {    1093114, "R_~gsdd^-" },
-    1649             :       {    1093214, "R_~gsud^0" },
-    1650             :       {    1093224, "R_~gsuu^+" },
-    1651             :       {    1093314, "R_~gssd^-" },
-    1652             :       {    1093324, "R_~gssu^0" },
-    1653             :       {    1093334, "R_~gsss^-" },
-    1654             :       {    1000612, "R_~t_1~d^+" },
-    1655             :       {    1000622, "R_~t_1~u^0" },
-    1656             :       {    1000632, "R_~t_1~s^+" },
-    1657             :       {    1000642, "R_~t_1~c^0" },
-    1658             :       {    1000652, "R_~t_1~b^+" },
-    1659             :       {    1006113, "R_~t_1dd_1^0" },
-    1660             :       {    1006211, "R_~t_1ud_0^+" },
-    1661             :       {    1006213, "R_~t_1ud_1^+" },
-    1662             :       {    1006223, "R_~t_1uu_1^++" },
-    1663             :       {    1006311, "R_~t_1sd_0^0" },
-    1664             :       {    1006313, "R_~t_1sd_1^0" },
-    1665             :       {    1006321, "R_~t_1su_0^+" },
-    1666             :       {    1006323, "R_~t_1su_1^+" },
-    1667             :       {    1006333, "R_~t_1ss_1^0" },
-    1668             :       { 1000010010, "Hydrogen" },
-    1669             :       { 1000010020, "Deuterium" },
-    1670             :       {-1000010020, "Anti-Deuterium" },
-    1671             :       { 1000010030, "Tritium" },
-    1672             :       {-1000010030, "Anti-Tritium" },
-    1673             :       { 1000020030, "He3" },
-    1674             :       {-1000020030, "Anti-He3" },
-    1675             :       { 1000020040, "Alpha-(He4)" },
-    1676             :       {-1000020040, "Anti-Alpha-(He4)" }
-    1677             :   };
-    1678             : 
-    1679             :   int lnames = sizeof(SNames)/sizeof(SNames[0]);
-    1680           0 :   for( int k=0; k!=lnames; ++k) {
-    1681           0 :       m.insert( std::make_pair( SNames[k].pid, std::string(SNames[k].pname)) );
-    1682           0 :       nameMap.insert( std::make_pair( std::string(SNames[k].pname), SNames[k].pid ) );
-    1683             :   }
-    1684           0 :   static ParticleNameMap mymaps(m,nameMap);
-    1685             : 
-    1686           0 :   return mymaps;
-    1687             : }  // ParticleNameInit()
-    1688             : 
-    1689           0 : void writeParticleNameLine( int i, std::ostream & os  )
-    1690             : {
-    1691           0 :     if ( validParticleName( i ) ) {
-    1692           0 :         std::string pn = particleName( i );
-    1693           0 :         int pid = particleName( pn );
-    1694           0 :         os << " PDT number: " ;
-    1695           0 :         os.width(12);
-    1696           0 :         os << i << " PDT name: " << pn << std::endl;
-    1697             :         // verify reverse lookup
-    1698           0 :         if( pid != i ) {
-    1699             :             os << "HepPID::writeParticleNameLine ERROR: "
-    1700           0 :                << " got " << pid << " instead of " << i << std::endl;
-    1701             :         }
-    1702             :     }
-    1703           0 :     return;
-    1704             : }  // writeParticleNameLine()
-    1705             : 
-    1706           0 : std::string dyonName( const int & pid )
-    1707             : {
-    1708           0 :     std::ostringstream pn;
-    1709           0 :     pn << "Dyon^" << digit(nq1,pid) << digit(nq2,pid) << digit(nq3,pid);
-    1710           0 :     if ( digit(nl,pid) == 1 ) {
-    1711           0 :        if ( pid > 0 ) {
-    1712           0 :           pn << "++";
-    1713             :        } else {
-    1714           0 :           pn << "--";
-    1715             :        }
-    1716           0 :     } else if ( digit(nl,pid) == 2 ) {
-    1717           0 :        if ( pid > 0 ) {
-    1718           0 :           pn << "+-";
-    1719             :        } else {
-    1720           0 :           pn << "-+";
-    1721             :        }
-    1722             :     }
-    1723           0 :     return pn.str();
-    1724           0 : }
-    1725             : 
-    1726           0 : std::string qballName( const int & pid )
-    1727             : {
-    1728           0 :     std::ostringstream pn;
-    1729           0 :     pn << "QBall^" << ((abspid(pid)/100)%1000) << "." << digit(nq3,pid);
-    1730           0 :     if ( pid > 0 ) {
-    1731           0 :        pn << "+";
-    1732             :     } else {
-    1733           0 :        pn << "-";
-    1734             :     }
-    1735           0 :     return pn.str();
-    1736           0 : }
-    1737             : 
-    1738           0 : int  checkForSpecialParticle( const std::string & s )
-    1739             : {
-    1740             :     int chg, chg2, id;
-    1741             :     int m = 1;
-    1742           0 :     int len = s.length();
-    1743           0 :     if( s.substr(0,4) == "Dyon" ) {
-    1744           0 :        std::istringstream var1(s.substr(5,3).c_str());
-    1745           0 :        var1 >> chg;
-    1746           0 :        if( s.substr(len-2,1) == "+" && s.substr(len-1,1) == "-") m = 2;
-    1747           0 :        if( s.substr(len-2,1) == "-" && s.substr(len-1,1) == "+") m = 2;
-    1748           0 :        id = 4100000 + m*10000 + chg*10;
-    1749           0 :        if( s.substr(len-2,1) == "-" ) id = -id;
-    1750             :        return id;
-    1751           0 :     }
-    1752           0 :     if( s.substr(0,5) == "QBall" ) {
-    1753           0 :        int rem = len - 9;
-    1754           0 :        std::istringstream var2(s.substr(6,rem).c_str());
-    1755           0 :        var2 >> chg;
-    1756           0 :        std::istringstream var3(s.substr(7+rem,1).c_str());
-    1757           0 :        var3 >> chg2;
-    1758           0 :        id = 10000000 + chg*100+chg2*10;
-    1759           0 :        if( s.substr(len-1,1) == "-" ) id = -id;
-    1760             :        return id;
-    1761           0 :     }
-    1762             :     return 0;
-    1763             : }
-    1764             : 
-    1765             : } // unnamed namespace
-    1766             : 
-    1767             : //
-    1768             : // getPartcleIdMap is the ONLY function allowed to call ParticleNameInit
-    1769             : //
-    1770           0 : ParticleNameMap const &  getParticleNameMap()
-    1771             : {
-    1772           0 :   static  ParticleNameMap const &  pmap = ParticleNameInit();
-    1773           0 :   return pmap;
-    1774             : }  // getPartcleIdMap()
-    1775             : 
-    1776           0 : bool validParticleName( const int & pid )
-    1777             : {
-    1778             :     // check for the special cases first
-    1779           0 :     if ( isDyon(pid) ) return true;
-    1780           0 :     if ( isQBall(pid) ) return true;
-    1781             :     
-    1782           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
-    1783             : 
-    1784           0 :     ParticleNameMap::idIterator const cit = pmap.find( pid );
-    1785             :     return ( cit == pmap.end() )
-    1786           0 :          ? false
-    1787             :          : true;
-    1788             : }  // validParticleName()
-    1789             : 
-    1790           0 : bool validParticleName( const std::string & s )
-    1791             : {
-    1792           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
-    1793           0 :     ParticleNameMap::nameIterator const cit = pmap.findString( s );
-    1794             :     return ( cit == pmap.endLookupMap() )
-    1795           0 :          ? false
-    1796           0 :          : true;
-    1797             : }  // validParticleName()
-    1798             : 
-    1799           0 : std::string  particleName( const int & pid )
-    1800             : {
-    1801             :     // check for the special cases first
-    1802           0 :     if ( isDyon(pid) ) return dyonName(pid);
-    1803           0 :     if ( isQBall(pid) ) return qballName(pid);
-    1804             :     
-    1805           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
-    1806             : 
-    1807           0 :     ParticleNameMap::idIterator const cit = pmap.find( pid );
-    1808             :     return ( cit == pmap.end() )
-    1809             :          ? std::string("not defined")
-    1810           0 :          : cit->second;
-    1811             : }  // particleName()
-    1812             : 
-    1813           0 : int  particleName( const std::string & s )
-    1814             : {
-    1815           0 :     static  ParticleNameMap const &  pmap = getParticleNameMap();
-    1816           0 :     ParticleNameMap::nameIterator const cit = pmap.findString( s );
-    1817             :     return ( cit == pmap.endLookupMap() )
-    1818           0 :          ? checkForSpecialParticle(s)
-    1819           0 :          : cit->second;
-    1820             : }  // particleName()
-    1821             : 
-    1822             : //
-    1823             : // list all the defined names
-    1824             : //
-    1825           0 : void  listParticleNames( std::ostream & os  )
-    1826             : {
-    1827           0 :     writeVersion( os );
-    1828             :     os << "     HepPID Particle List" << std::endl;
-    1829             :     os << std::endl;
-    1830             : 
-    1831             :     // simple: static  PartcleIdMap const &  pmap = getPartcleIdMap();
-    1832             :     // simple: for( PartcleIdMap::const_iterator cit = pmap.begin(), mend = pmap.end(); 
-    1833             :     // simple:                                 cit != mend;
-    1834             :         // simple:                        ++cit ) {
-    1835             :         // simple: os << "  PDT number: " ;
-    1836             :         // simple: os.width(12);
-    1837             :         // simple: os << cit->first << "  PDT name: " << cit->second << std::endl;
-    1838             :     // simple: }
-    1839             :     int id, i, j, q1, q2, q3, l, m, n;
-    1840             :     // special cases
-    1841           0 :     for( id=1; id<101; ++id) {
-    1842           0 :         writeParticleNameLine(  id, os );
-    1843           0 :         writeParticleNameLine( -id, os );
-    1844             :     }
-    1845           0 :     for( i=11; i<1000; ++i) {
-    1846           0 :         id = i*10;
-    1847           0 :         writeParticleNameLine(  id, os );
-    1848           0 :         writeParticleNameLine( -id, os );
-    1849             :     }
-    1850             :     // SUSY
-    1851           0 :     for( n=1; n<3; ++n) {
-    1852           0 :         for( q1=0; q1<10; ++q1) {
-    1853           0 :             for( j=0; j<10; ++j) {
-    1854           0 :                 id = 1000000*n+10*q1+j;
-    1855           0 :                 writeParticleNameLine(  id, os );
-    1856           0 :                 writeParticleNameLine( -id, os );
-    1857             :             }
-    1858             :         }
-    1859             :     }
-    1860             :     // technicolor, etc.
-    1861           0 :     for( n=3; n<7; ++n) {
-    1862           0 :         for( q2=0; q2<10; ++q2) {
-    1863           0 :             for( q1=0; q1<10; ++q1) {
-    1864           0 :                 for( j=0; j<10; ++j) {
-    1865           0 :                     for( m=0; m<10; ++m) {
-    1866           0 :                         for( l=0; l<7; ++l) {
-    1867           0 :                             id = 1000000*n+100000*m+10000*l+100*q2+10*q1+j;
-    1868             :                             // save dyons for later
-    1869           0 :                             if( !(n == 4 && m == 1) ) {
-    1870           0 :                             writeParticleNameLine(  id, os );
-    1871           0 :                             writeParticleNameLine( -id, os );
-    1872             :                             }
-    1873             :                         }
-    1874             :                     }
-    1875             :                 }
-    1876             :             }
-    1877             :         }
-    1878             :     }
-    1879             :     // R-hadrons
-    1880           0 :     for( q3=0; q3<10; ++q3) {
-    1881           0 :         for( q2=1; q2<10; ++q2) {
-    1882           0 :             for( q1=1; q1<10; ++q1) {
-    1883           0 :                 for( j=1; j<5; ++j) {
-    1884           0 :                     id = 1000000+1000*q3+100*q2+10*q1+j;
-    1885           0 :                     writeParticleNameLine( id, os );
-    1886           0 :                     if(q3 > 0 ) id = 1000000+90000+1000*q3+100*q2+10*q1+j;
-    1887           0 :                     writeParticleNameLine( id, os );
-    1888             :                 }
-    1889             :             }
-    1890             :         }
-    1891             :     }
-    1892             :     // miscellaneous generator particles
-    1893           0 :     for( l=0; l<9; ++l) {
-    1894           0 :         for( i=1; i<100; ++i) {
-    1895           0 :             id = 9900000+10000*l+i;
-    1896           0 :             writeParticleNameLine(  id, os );
-    1897           0 :             writeParticleNameLine( -id, os );
-    1898             :         }
-    1899           0 :         for( q3=0; q3<10; ++q3) {
-    1900           0 :             for( q2=1; q2<10; ++q2) {
-    1901           0 :                 for( q1=1; q1<10; ++q1) {
-    1902           0 :                     for( j=0; j<10; ++j) {
-    1903           0 :                         id = 9900000+10000*l+1000*q3+100*q2+10*q1+j;
-    1904           0 :                         writeParticleNameLine(  id, os );
-    1905           0 :                         writeParticleNameLine( -id, os );
-    1906             :                     }
-    1907             :                 }
-    1908             :             }
-    1909             :         }
-    1910             :     }
-    1911             :     // diquark
-    1912           0 :     for( i=11; i<100; ++i) {
-    1913           0 :         for( j=0; j<10; ++j) {
-    1914           0 :             id = 100*i+j;
-    1915           0 :             writeParticleNameLine(  id, os );
-    1916           0 :             writeParticleNameLine( -id, os );
-    1917             :         }
-    1918             :     }
-    1919             :     // mesons
-    1920           0 :     for( q2=1; q2<10; ++q2) {
-    1921           0 :         for( q1=1; q1<10; ++q1) {
-    1922           0 :             for( j=1; j<10; ++j) {
-    1923           0 :                 for( m=0; m<9; ++m) {
-    1924           0 :                     for( l=0; l<10; ++l) {
-    1925           0 :                         id = 100000*m+10000*l+100*q2+10*q1+j;
-    1926           0 :                         writeParticleNameLine(  id, os );
-    1927           0 :                         writeParticleNameLine( -id, os );
-    1928           0 :                         id = 9000000+100000*m+10000*l+100*q2+10*q1+j;
-    1929           0 :                         writeParticleNameLine(  id, os );
-    1930           0 :                         writeParticleNameLine( -id, os );
-    1931             :                     }
-    1932             :                 }
-    1933             :             }
-    1934             :         }
-    1935             :     }
-    1936             :     // baryons
-    1937           0 :     for( q3=1; q3<10; ++q3) {
-    1938           0 :         for( q2=1; q2<10; ++q2) {
-    1939           0 :             for( q1=1; q1<10; ++q1) {
-    1940           0 :                 for( j=1; j<10; ++j) {
-    1941           0 :                     for( m=0; m<9; ++m) {
-    1942           0 :                         id = 10000*m+1000*q3+100*q2+10*q1+j;
-    1943           0 :                         writeParticleNameLine(  id, os );
-    1944           0 :                         writeParticleNameLine( -id, os );
-    1945             :                     }
-    1946             :                 }
-    1947             :             }
-    1948             :         }
-    1949             :     }
-    1950             :     // pentaquarks
-    1951           0 :     for( l=1; l<9; ++l ) {
-    1952           0 :         for ( m=1; m<9; ++m ) {
-    1953           0 :             for( q3=1; q3<9; ++q3) {
-    1954           0 :                 for( q2=1; q2<9; ++q2) {
-    1955           0 :                     for( q1=1; q1<9; ++q1) {
-    1956           0 :                         id = 9*1000000+l*100000+m*10000+1000*q3+100*q2+10*q1+2;
-    1957           0 :                         writeParticleNameLine(  id, os );
-    1958           0 :                         writeParticleNameLine( -id, os );
-    1959             :                     }
-    1960             :                 }
-    1961             :             }
-    1962             :         }
-    1963             :     }
-    1964             :     // ions
-    1965           0 :     for( i=1; i<3; ++i) {
-    1966           0 :         for( m=1; m<5; ++m) {
-    1967           0 :                 id = 1000000000+10*m+10000*i;
-    1968           0 :                 writeParticleNameLine(  id, os );
-    1969           0 :                 writeParticleNameLine( -id, os );
-    1970             :         }
-    1971             :     }
-    1972             :     // some Dyons
-    1973           0 :     for( q3=0; q3<2; ++q3) {
-    1974           0 :         for( q2=0; q2<4; ++q2) {
-    1975           0 :             for( q1=0; q1<10; ++q1) {
-    1976           0 :                 ++q1;
-    1977           0 :                 id = 4110000+1000*q3+100*q2+10*q1;
-    1978           0 :                 writeParticleNameLine(  id, os );
-    1979           0 :                 writeParticleNameLine( -id, os );
-    1980           0 :                 id = 4120000+1000*q3+100*q2+10*q1;
-    1981           0 :                 writeParticleNameLine(  id, os );
-    1982           0 :                 writeParticleNameLine( -id, os );
-    1983             :             }
-    1984             :         }
-    1985             :     }
-    1986             :     // a few QBalls
-    1987           0 :     for( i=1; i<199; ++i ) {
-    1988           0 :         for( m=1; m<10; ) {
-    1989           0 :                 id = 10000000+10*m+100*i;
-    1990           0 :                 writeParticleNameLine(  id, os );
-    1991           0 :                 writeParticleNameLine( -id, os );
-    1992           0 :                 m += 3;
-    1993             :         }
-    1994             :         i += 11;
-    1995             :     }
-    1996           0 :     return;
-    1997             : }  // listParticleNames()
-    1998             : 
-    1999             : }       // HepPID
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html b/doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html deleted file mode 100644 index 65c9d6164..000000000 --- a/doc/coverageReport/libs/HepPID/src/Version.cc.func-sort-c.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/Version.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - Version.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:080.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID11versionNameB5cxx11Ev0
_ZN6HepPID12writeVersionERSo0
_ZN6HepPID7versionEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/Version.cc.func.html b/doc/coverageReport/libs/HepPID/src/Version.cc.func.html deleted file mode 100644 index 0a0efae49..000000000 --- a/doc/coverageReport/libs/HepPID/src/Version.cc.func.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/Version.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - Version.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:080.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN6HepPID11versionNameB5cxx11Ev0
_ZN6HepPID12writeVersionERSo0
_ZN6HepPID7versionEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html b/doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html deleted file mode 100644 index 1d5d7f616..000000000 --- a/doc/coverageReport/libs/HepPID/src/Version.cc.gcov.html +++ /dev/null @@ -1,106 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src/Version.cc - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/src - Version.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:080.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : // ----------------------------------------------------------------------
-       2             : //
-       3             : // version.cc
-       4             : // Author: Lynn Garren
-       5             : //
-       6             : //  for now, this is a free function
-       7             : //
-       8             : // ----------------------------------------------------------------------
-       9             : 
-      10             : #include "HepPID/Version.hh"
-      11             : 
-      12             : namespace HepPID {
-      13             : 
-      14           0 : std::string versionName( )
-      15             : {
-      16           0 :     return "3.04.01";
-      17             : }
-      18             : 
-      19           0 : void version( )
-      20             : {
-      21           0 :     std::cout << " --------------- HepPID Version " << versionName()
-      22             :               << " --------------- " << std::endl;
-      23           0 : }
-      24             : 
-      25           0 : void writeVersion( std::ostream & os )
-      26             : {
-      27           0 :     os << "             HepPID Version: " << versionName() << std::endl;
-      28           0 : }
-      29             : 
-      30             : }       // HepPID
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/index-sort-f.html b/doc/coverageReport/libs/HepPID/src/index-sort-f.html deleted file mode 100644 index 0bc408cce..000000000 --- a/doc/coverageReport/libs/HepPID/src/index-sort-f.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/srcHitTotalCoverage
Test:coverage.info.cleanedLines:5044011.4 %
Date:2024-04-08 14:58:22Functions:114822.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Version.cc -
0.0%
-
0.0 %0 / 80.0 %0 / 3
ParticleName.cc -
0.0%
-
0.0 %0 / 1830.0 %0 / 13
ParticleIDMethods.cc -
20.1%20.1%
-
20.1 %50 / 24934.4 %11 / 32
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/index-sort-l.html b/doc/coverageReport/libs/HepPID/src/index-sort-l.html deleted file mode 100644 index 5545aaf67..000000000 --- a/doc/coverageReport/libs/HepPID/src/index-sort-l.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/srcHitTotalCoverage
Test:coverage.info.cleanedLines:5044011.4 %
Date:2024-04-08 14:58:22Functions:114822.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Version.cc -
0.0%
-
0.0 %0 / 80.0 %0 / 3
ParticleName.cc -
0.0%
-
0.0 %0 / 1830.0 %0 / 13
ParticleIDMethods.cc -
20.1%20.1%
-
20.1 %50 / 24934.4 %11 / 32
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/HepPID/src/index.html b/doc/coverageReport/libs/HepPID/src/index.html deleted file mode 100644 index cce8733cc..000000000 --- a/doc/coverageReport/libs/HepPID/src/index.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/HepPID/src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/HepPID/srcHitTotalCoverage
Test:coverage.info.cleanedLines:5044011.4 %
Date:2024-04-08 14:58:22Functions:114822.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ParticleIDMethods.cc -
20.1%20.1%
-
20.1 %50 / 24934.4 %11 / 32
ParticleName.cc -
0.0%
-
0.0 %0 / 1830.0 %0 / 13
Version.cc -
0.0%
-
0.0 %0 / 80.0 %0 / 3
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html deleted file mode 100644 index 48630a2e2..000000000 --- a/doc/coverageReport/libs/healpix_base/error_handling.cc.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/error_handling.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - error_handling.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0120.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix11PlanckErrorC2EPKc0
_ZN7healpix11PlanckErrorC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix11PlanckErrorD0Ev0
_ZN7healpix11PlanckErrorD2Ev0
_ZN7healpix16planck_failure__EPKciS1_RKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix16planck_failure__EPKciS1_S1_0
_ZN7healpix9killjob__Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/error_handling.cc.func.html b/doc/coverageReport/libs/healpix_base/error_handling.cc.func.html deleted file mode 100644 index 3f1abe29a..000000000 --- a/doc/coverageReport/libs/healpix_base/error_handling.cc.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/error_handling.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - error_handling.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0120.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix11PlanckErrorC2EPKc0
_ZN7healpix11PlanckErrorC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix11PlanckErrorD0Ev0
_ZN7healpix11PlanckErrorD2Ev0
_ZN7healpix16planck_failure__EPKciS1_RKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7healpix16planck_failure__EPKciS1_S1_0
_ZN7healpix9killjob__Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html b/doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html deleted file mode 100644 index d09b41e69..000000000 --- a/doc/coverageReport/libs/healpix_base/error_handling.cc.gcov.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/error_handling.cc - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - error_handling.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0120.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : 
-       2             : /*
-       3             :  *  This file is part of libcxxsupport.
-       4             :  *
-       5             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       6             :  *  it under the terms of the GNU General Public License as published by
-       7             :  *  the Free Software Foundation; either version 2 of the License, or
-       8             :  *  (at your option) any later version.
-       9             :  *
-      10             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      11             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      12             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      13             :  *  GNU General Public License for more details.
-      14             :  *
-      15             :  *  You should have received a copy of the GNU General Public License
-      16             :  *  along with libcxxsupport; if not, write to the Free Software
-      17             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      18             :  */
-      19             : 
-      20             : /*
-      21             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      22             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      23             :  *  (DLR).
-      24             :  */
-      25             : 
-      26             : /*
-      27             :  *  Utilities for error reporting
-      28             :  *
-      29             :  *  Copyright (C) 2003-2011 Max-Planck-Society
-      30             :  *  Author: Martin Reinecke
-      31             :  */
-      32             : 
-      33             : #include "healpix_base/error_handling.h"
-      34             : 
-      35             : namespace healpix{
-      36             : using namespace std;
-      37             : 
-      38           0 : PlanckError::PlanckError(const string &message) : msg (message) {}
-      39           0 : PlanckError::PlanckError(const char *message) : msg (message) {}
-      40             : 
-      41             : //virtual
-      42           0 : PlanckError::~PlanckError() {}
-      43             : 
-      44           0 : void planck_failure__(const char *file, int line, const char *func,
-      45             :   const string &msg)
-      46             :   {
-      47           0 :   cerr << "Error encountered at " << file << ", line " << line << endl;
-      48           0 :   if (func) cerr << "(function " << func << ")" << endl;
-      49           0 :   if (msg!="") cerr << endl << msg << endl;
-      50             :   cerr << endl;
-      51           0 :   }
-      52             : 
-      53           0 : void planck_failure__(const char *file, int line, const char *func,
-      54             :   const char *msg)
-      55           0 :   { planck_failure__ (file,line,func,string(msg)); }
-      56             : 
-      57           0 : void killjob__()
-      58           0 :   { throw; }
-      59             : } // namespace healpix
-      60             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html deleted file mode 100644 index c1777f967..000000000 --- a/doc/coverageReport/libs/healpix_base/geom_utils.cc.func-sort-c.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/geom_utils.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - geom_utils.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0250.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmRS2_Rd0
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmmRS2_Rd0
_ZN7healpix21find_enclosing_circleERKNS_3arrINS_6vec3_tIdEEEERS2_Rd0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html b/doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html deleted file mode 100644 index db584b322..000000000 --- a/doc/coverageReport/libs/healpix_base/geom_utils.cc.func.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/geom_utils.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - geom_utils.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0250.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmRS2_Rd0
_ZN7healpix10get_circleERKNS_3arrINS_6vec3_tIdEEEEmmRS2_Rd0
_ZN7healpix21find_enclosing_circleERKNS_3arrINS_6vec3_tIdEEEERS2_Rd0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html b/doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html deleted file mode 100644 index 2fdacf966..000000000 --- a/doc/coverageReport/libs/healpix_base/geom_utils.cc.gcov.html +++ /dev/null @@ -1,151 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/geom_utils.cc - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - geom_utils.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0250.0 %
Date:2024-04-08 14:58:22Functions:030.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*
-      26             :  *  Copyright (C) 2011 Max-Planck-Society
-      27             :  *  \author Martin Reinecke
-      28             :  */
-      29             : 
-      30             : #include "healpix_base/geom_utils.h"
-      31             : #include "healpix_base/arr.h"
-      32             : 
-      33             : 
-      34             : namespace healpix{
-      35             : using namespace std;
-      36             : 
-      37             : 
-      38           0 : void get_circle (const arr<vec3> &point, tsize q1, tsize q2, vec3 &center,
-      39             :   double &cosrad)
-      40             :   {
-      41           0 :   center = (point[q1]+point[q2]).Norm();
-      42           0 :   cosrad = dotprod(point[q1],center);
-      43           0 :   for (tsize i=0; i<q1; ++i)
-      44           0 :     if (dotprod(point[i],center)<cosrad) // point outside the current circle
-      45             :       {
-      46           0 :       center=crossprod(point[q1]-point[i],point[q2]-point[i]).Norm();
-      47           0 :       cosrad=dotprod(point[i],center);
-      48           0 :       if (cosrad<0)
-      49           0 :         { center.Flip(); cosrad=-cosrad; }
-      50             :       }
-      51           0 :   }
-      52           0 : void get_circle (const arr<vec3> &point, tsize q, vec3 &center,
-      53             :   double &cosrad)
-      54             :   {
-      55           0 :   center = (point[0]+point[q]).Norm();
-      56           0 :   cosrad = dotprod(point[0],center);
-      57           0 :   for (tsize i=1; i<q; ++i)
-      58           0 :     if (dotprod(point[i],center)<cosrad) // point outside the current circle
-      59           0 :       get_circle(point,i,q,center,cosrad);
-      60           0 :   }
-      61             : 
-      62             : 
-      63           0 : void find_enclosing_circle (const arr<vec3> &point, vec3 &center,
-      64             :   double &cosrad)
-      65             :   {
-      66             :   tsize np=point.size();
-      67           0 :   planck_assert(np>=3,"too few points");
-      68           0 :   center = (point[0]+point[1]).Norm();
-      69           0 :   cosrad = dotprod(point[0],center);
-      70           0 :   for (tsize i=2; i<np; ++i)
-      71           0 :     if (dotprod(point[i],center)<cosrad) // point outside the current circle
-      72           0 :       get_circle(point,i,center,cosrad);
-      73           0 :   }
-      74             : } // namespace healpix
-      75             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html deleted file mode 100644 index 522a3b809..000000000 --- a/doc/coverageReport/libs/healpix_base/healpix_base.cc.func-sort-c.html +++ /dev/null @@ -1,436 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/healpix_base.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - healpix_base.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11273415.3 %
Date:2024-04-08 14:58:22Functions:109111.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12_GLOBAL__N_111check_pixelIiiEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIliEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIllEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIiEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIlEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_19locToVec3Edddb0
_ZN7healpix14T_Healpix_BaseIiE10npix2nsideEi0
_ZN7healpix14T_Healpix_BaseIiE11nside2orderEi0
_ZN7healpix14T_Healpix_BaseIiE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIiE8SetNsideEiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2Ev0
_ZN7healpix14T_Healpix_BaseIlE10npix2nsideEl0
_ZN7healpix14T_Healpix_BaseIlE11nside2orderEl0
_ZN7healpix14T_Healpix_BaseIlE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIlE8SetNsideElNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2Ev0
_ZNK7healpix14T_Healpix_BaseIiE10boundariesEimRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEi0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIiE10nest2peanoEi0
_ZNK7healpix14T_Healpix_BaseIiE10peano2nestEi0
_ZNK7healpix14T_Healpix_BaseIiE10query_discENS_8pointingEdRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIiE11query_stripEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIiE12get_interpolERKNS_8pointingERNS_7fix_arrIiLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIiE13get_ring_infoEiRiS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIiE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE14get_ring_info2EiRiS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIiE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE17nest_peano_helperEii0
_ZNK7healpix14T_Healpix_BaseIiE19get_ring_info_smallEiRiS2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE20query_strip_internalEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE6ring2zEi0
_ZNK7healpix14T_Healpix_BaseIiE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE8nest2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE8pix2ringEi0
_ZNK7healpix14T_Healpix_BaseIiE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIiE9neighborsEiRNS_7fix_arrIiLm8EEE0
_ZNK7healpix14T_Healpix_BaseIiE9nest2ringEi0
_ZNK7healpix14T_Healpix_BaseIlE10boundariesElmRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEl0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIlE10nest2peanoEl0
_ZNK7healpix14T_Healpix_BaseIlE10peano2nestEl0
_ZNK7healpix14T_Healpix_BaseIlE10query_discENS_8pointingEdRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIlE11query_stripEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11spread_bitsEi0
_ZNK7healpix14T_Healpix_BaseIlE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIlE12get_interpolERKNS_8pointingERNS_7fix_arrIlLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIlE13get_ring_infoElRlS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIlE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE14get_ring_info2ElRlS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIlEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE17nest_peano_helperEli0
_ZNK7healpix14T_Healpix_BaseIlE19get_ring_info_smallElRlS2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIlEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE20query_strip_internalEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIlEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE6ring2zEl0
_ZNK7healpix14T_Healpix_BaseIlE7loc2pixEdddb0
_ZNK7healpix14T_Healpix_BaseIlE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE8pix2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE8ring2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2nestEiii0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIlE9neighborsElRNS_7fix_arrIlLm8EEE0
_ZNK7healpix14T_Healpix_BaseIlE9nest2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE9ring2nestEl0
_ZN7healpix14T_Healpix_BaseIiE3SetEiNS_23Healpix_Ordering_SchemeE10
_ZN7healpix14T_Healpix_BaseIlE3SetEiNS_23Healpix_Ordering_SchemeE19
_ZNK7healpix14T_Healpix_BaseIiE8ring2xyfEiRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIiE8xyf2nestEiii421
_ZNK7healpix14T_Healpix_BaseIiE9ring2nestEi421
_ZNK7healpix14T_Healpix_BaseIlE7pix2locElRdS2_S2_Rb421
_ZNK7healpix14T_Healpix_BaseIlE8nest2xyfElRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIlE13compress_bitsEl842
_ZNK7healpix14T_Healpix_BaseIiE7loc2pixEdddb24585
_ZNK7healpix14T_Healpix_BaseIiE7pix2locEiRdS2_S2_Rb135172
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html b/doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html deleted file mode 100644 index 30c46e124..000000000 --- a/doc/coverageReport/libs/healpix_base/healpix_base.cc.func.html +++ /dev/null @@ -1,436 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/healpix_base.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - healpix_base.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11273415.3 %
Date:2024-04-08 14:58:22Functions:109111.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12_GLOBAL__N_111check_pixelIiiEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIliEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_111check_pixelIllEEviiiiRNS_8rangesetIT0_EET_RSt6vectorISt4pairIS6_iESaIS9_EEbRi0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIiEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_116check_pixel_ringIlEEbRKNS_14T_Healpix_BaseIT_EES6_S3_S3_S3_idddS3_0
_ZN7healpix12_GLOBAL__N_19locToVec3Edddb0
_ZN7healpix14T_Healpix_BaseIiE10npix2nsideEi0
_ZN7healpix14T_Healpix_BaseIiE11nside2orderEi0
_ZN7healpix14T_Healpix_BaseIiE3SetEiNS_23Healpix_Ordering_SchemeE10
_ZN7healpix14T_Healpix_BaseIiE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIiE8SetNsideEiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2Ev0
_ZN7healpix14T_Healpix_BaseIlE10npix2nsideEl0
_ZN7healpix14T_Healpix_BaseIlE11nside2orderEl0
_ZN7healpix14T_Healpix_BaseIlE3SetEiNS_23Healpix_Ordering_SchemeE19
_ZN7healpix14T_Healpix_BaseIlE4swapERS1_0
_ZN7healpix14T_Healpix_BaseIlE8SetNsideElNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2Ev0
_ZNK7healpix14T_Healpix_BaseIiE10boundariesEimRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEi0
_ZNK7healpix14T_Healpix_BaseIiE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIiE10nest2peanoEi0
_ZNK7healpix14T_Healpix_BaseIiE10peano2nestEi0
_ZNK7healpix14T_Healpix_BaseIiE10query_discENS_8pointingEdRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIiE11query_stripEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIiE12get_interpolERKNS_8pointingERNS_7fix_arrIiLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIiE13get_ring_infoEiRiS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIiE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE14get_ring_info2EiRiS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIiE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE17nest_peano_helperEii0
_ZNK7healpix14T_Healpix_BaseIiE19get_ring_info_smallEiRiS2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE20query_strip_internalEddbRNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIiE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIiEE0
_ZNK7healpix14T_Healpix_BaseIiE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE6ring2zEi0
_ZNK7healpix14T_Healpix_BaseIiE7loc2pixEdddb24585
_ZNK7healpix14T_Healpix_BaseIiE7pix2locEiRdS2_S2_Rb135172
_ZNK7healpix14T_Healpix_BaseIiE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIiE8nest2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE8pix2ringEi0
_ZNK7healpix14T_Healpix_BaseIiE8ring2xyfEiRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIiE8xyf2nestEiii421
_ZNK7healpix14T_Healpix_BaseIiE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIiE9neighborsEiRNS_7fix_arrIiLm8EEE0
_ZNK7healpix14T_Healpix_BaseIiE9nest2ringEi0
_ZNK7healpix14T_Healpix_BaseIiE9ring2nestEi421
_ZNK7healpix14T_Healpix_BaseIlE10boundariesElmRSt6vectorINS_6vec3_tIdEESaIS4_EE0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEl0
_ZNK7healpix14T_Healpix_BaseIlE10max_pixradEv0
_ZNK7healpix14T_Healpix_BaseIlE10nest2peanoEl0
_ZNK7healpix14T_Healpix_BaseIlE10peano2nestEl0
_ZNK7healpix14T_Healpix_BaseIlE10query_discENS_8pointingEdRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE10ring_aboveEd0
_ZNK7healpix14T_Healpix_BaseIlE11query_stripEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11spread_bitsEi0
_ZNK7healpix14T_Healpix_BaseIlE11swap_cyclesEv0
_ZNK7healpix14T_Healpix_BaseIlE12get_interpolERKNS_8pointingERNS_7fix_arrIlLm4EEERNS5_IdLm4EEE0
_ZNK7healpix14T_Healpix_BaseIlE13compress_bitsEl842
_ZNK7healpix14T_Healpix_BaseIlE13get_ring_infoElRlS2_RdS3_Rb0
_ZNK7healpix14T_Healpix_BaseIlE13query_polygonERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE14get_ring_info2ElRlS2_RdRb0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIiEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE15query_multidiscIlEEvRKNS_3arrINS_6vec3_tIdEEEERKNS3_IdEEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE17nest_peano_helperEli0
_ZNK7healpix14T_Healpix_BaseIlE19get_ring_info_smallElRlS2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIiEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE19query_disc_internalIlEEvNS_8pointingEdiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveENS_8pointingEdRNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE20query_strip_internalEddbRNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIiEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE22query_polygon_internalIlEEvRKSt6vectorINS_8pointingESaIS4_EEiRNS_8rangesetIT_EE0
_ZNK7healpix14T_Healpix_BaseIlE23query_multidisc_generalERKNS_3arrINS_6vec3_tIdEEEERKNS2_IdEEbRKSt6vectorIiSaIiEERNS_8rangesetIlEE0
_ZNK7healpix14T_Healpix_BaseIlE23query_polygon_inclusiveERKSt6vectorINS_8pointingESaIS3_EERNS_8rangesetIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE6ring2zEl0
_ZNK7healpix14T_Healpix_BaseIlE7loc2pixEdddb0
_ZNK7healpix14T_Healpix_BaseIlE7pix2locElRdS2_S2_Rb421
_ZNK7healpix14T_Healpix_BaseIlE7xyf2locEddiRdS2_S2_Rb0
_ZNK7healpix14T_Healpix_BaseIlE8nest2xyfElRiS2_S2_421
_ZNK7healpix14T_Healpix_BaseIlE8pix2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE8ring2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2nestEiii0
_ZNK7healpix14T_Healpix_BaseIlE8xyf2ringEiii0
_ZNK7healpix14T_Healpix_BaseIlE9neighborsElRNS_7fix_arrIlLm8EEE0
_ZNK7healpix14T_Healpix_BaseIlE9nest2ringEl0
_ZNK7healpix14T_Healpix_BaseIlE9ring2nestEl0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html b/doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html deleted file mode 100644 index be3123d75..000000000 --- a/doc/coverageReport/libs/healpix_base/healpix_base.cc.gcov.html +++ /dev/null @@ -1,1454 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/healpix_base.cc - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - healpix_base.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:11273415.3 %
Date:2024-04-08 14:58:22Functions:109111.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of Healpix_cxx.
-       3             :  *
-       4             :  *  Healpix_cxx is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  Healpix_cxx is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with Healpix_cxx; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  *
-      18             :  *  For more information about HEALPix, see http://healpix.sourceforge.net
-      19             :  */
-      20             : 
-      21             : /*
-      22             :  *  Healpix_cxx is being developed at the Max-Planck-Institut fuer Astrophysik
-      23             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      24             :  *  (DLR).
-      25             :  */
-      26             : 
-      27             : /*
-      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
-      29             :  *  Author: Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #include "healpix_base/healpix_base.h"
-      33             : #include "healpix_base/geom_utils.h"
-      34             : #include "healpix_base/lsconstants.h"
-      35             : 
-      36             : namespace healpix{
-      37             : 
-      38             : using namespace std;
-      39             : 
-      40             : template<> const int T_Healpix_Base<int  >::order_max=13;
-      41             : template<> const int T_Healpix_Base<int64>::order_max=29;
-      42             : 
-      43           0 : template<typename I> int T_Healpix_Base<I>::nside2order (I nside)
-      44             :   {
-      45           0 :   planck_assert (nside>I(0), "invalid value for Nside");
-      46           0 :   return ((nside)&(nside-1)) ? -1 : ilog2(nside);
-      47             :   }
-      48           0 : template<typename I> I T_Healpix_Base<I>::npix2nside (I npix)
-      49             :   {
-      50           0 :   I res=isqrt(npix/I(12));
-      51           0 :   planck_assert (npix==res*res*I(12), "invalid value for npix");
-      52           0 :   return res;
-      53             :   }
-      54             : 
-      55           0 : template<typename I> I T_Healpix_Base<I>::ring_above (double z) const
-      56             :   {
-      57             :   double az=abs(z);
-      58           0 :   if (az<=twothird) // equatorial region
-      59           0 :     return I(nside_*(2-1.5*z));
-      60           0 :   I iring = I(nside_*sqrt(3*(1-az)));
-      61           0 :   return (z>0) ? iring : 4*nside_-iring-1;
-      62             :   }
-      63             : 
-      64             : namespace {
-      65             : 
-      66             : /* Short note on the "zone":
-      67             :    zone = 0: pixel lies completely outside the queried shape
-      68             :           1: pixel may overlap with the shape, pixel center is outside
-      69             :           2: pixel center is inside the shape, but maybe not the complete pixel
-      70             :           3: pixel lies completely inside the shape */
-      71             : 
-      72           0 : template<typename I, typename I2> inline void check_pixel (int o, int order_,
-      73             :   int omax, int zone, rangeset<I2> &pixset, I pix, vector<pair<I,int> > &stk,
-      74             :   bool inclusive, int &stacktop)
-      75             :   {
-      76           0 :   if (zone==0) return;
-      77             : 
-      78           0 :   if (o<order_)
-      79             :     {
-      80           0 :     if (zone>=3)
-      81             :       {
-      82           0 :       int sdist=2*(order_-o); // the "bit-shift distance" between map orders
-      83           0 :       pixset.append(pix<<sdist,(pix+1)<<sdist); // output all subpixels
-      84             :       }
-      85             :     else // (zone>=1)
-      86           0 :       for (int i=0; i<4; ++i)
-      87           0 :         stk.push_back(make_pair(4*pix+3-i,o+1)); // add children
-      88             :     }
-      89           0 :   else if (o>order_) // this implies that inclusive==true
-      90             :     {
-      91           0 :     if (zone>=2) // pixel center in shape
-      92             :       {
-      93           0 :       pixset.append(pix>>(2*(o-order_))); // output the parent pixel at order_
-      94           0 :       stk.resize(stacktop); // unwind the stack
-      95             :       }
-      96             :     else // (zone>=1): pixel center in safety range
-      97             :       {
-      98           0 :       if (o<omax) // check sublevels
-      99           0 :         for (int i=0; i<4; ++i) // add children in reverse order
-     100           0 :           stk.push_back(make_pair(4*pix+3-i,o+1));
-     101             :       else // at resolution limit
-     102             :         {
-     103           0 :         pixset.append(pix>>(2*(o-order_))); // output the parent pixel at order_
-     104           0 :         stk.resize(stacktop); // unwind the stack
-     105             :         }
-     106             :       }
-     107             :     }
-     108             :   else // o==order_
-     109             :     {
-     110           0 :     if (zone>=2)
-     111           0 :       pixset.append(pix);
-     112           0 :     else if (inclusive) // and (zone>=1)
-     113             :       {
-     114           0 :       if (order_<omax) // check sublevels
-     115             :         {
-     116           0 :         stacktop=stk.size(); // remember current stack position
-     117           0 :         for (int i=0; i<4; ++i) // add children in reverse order
-     118           0 :           stk.push_back(make_pair(4*pix+3-i,o+1));
-     119             :         }
-     120             :       else // at resolution limit
-     121           0 :         pixset.append(pix); // output the pixel
-     122             :       }
-     123             :     }
-     124             :   }
-     125             : 
-     126           0 : template<typename I> bool check_pixel_ring (const T_Healpix_Base<I> &b1,
-     127             :   const T_Healpix_Base<I> &b2, I pix, I nr, I ipix1, int fct,
-     128             :   double cz, double cphi, double cosrp2, I cpix)
-     129             :   {
-     130           0 :   if (pix>=nr) pix-=nr;
-     131           0 :   if (pix<0) pix+=nr;
-     132           0 :   pix+=ipix1;
-     133           0 :   if (pix==cpix) return false; // disk center in pixel => overlap
-     134             :   int px,py,pf;
-     135           0 :   b1.pix2xyf(pix,px,py,pf);
-     136           0 :   for (int i=0; i<fct-1; ++i) // go along the 4 edges
-     137             :     {
-     138           0 :     I ox=fct*px, oy=fct*py;
-     139             :     double pz,pphi;
-     140           0 :     b2.pix2zphi(b2.xyf2pix(ox+i,oy,pf),pz,pphi);
-     141           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
-     142           0 :       return false;
-     143           0 :     b2.pix2zphi(b2.xyf2pix(ox+fct-1,oy+i,pf),pz,pphi);
-     144           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
-     145             :       return false;
-     146           0 :     b2.pix2zphi(b2.xyf2pix(ox+fct-1-i,oy+fct-1,pf),pz,pphi);
-     147           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
-     148             :       return false;
-     149           0 :     b2.pix2zphi(b2.xyf2pix(ox,oy+fct-1-i,pf),pz,pphi);
-     150           0 :     if (cosdist_zphi(pz,pphi,cz,cphi)>cosrp2) // overlap
-     151             :       return false;
-     152             :     }
-     153             :   return true;
-     154             :   }
-     155             : 
-     156             : } // unnamed namespace
-     157             : 
-     158             : template<typename I> template<typename I2>
-     159           0 :   void T_Healpix_Base<I>::query_disc_internal
-     160             :   (pointing ptg, double radius, int fact, rangeset<I2> &pixset) const
-     161             :   {
-     162           0 :   bool inclusive = (fact!=0);
-     163             :   pixset.clear();
-     164           0 :   ptg.normalize();
-     165             : 
-     166           0 :   if (scheme_==RING)
-     167             :     {
-     168             :     I fct=1;
-     169           0 :     if (inclusive)
-     170             :       {
-     171           0 :       planck_assert (((I(1)<<order_max)/nside_)>=fact,
-     172             :         "invalid oversampling factor");
-     173             :       fct = fact;
-     174             :       }
-     175           0 :     T_Healpix_Base b2;
-     176             :     double rsmall, rbig;
-     177           0 :     if (fct>1)
-     178             :       {
-     179           0 :       b2.SetNside(fct*nside_,RING);
-     180           0 :       rsmall = radius+b2.max_pixrad();
-     181           0 :       rbig = radius+max_pixrad();
-     182             :       }
-     183             :     else
-     184           0 :       rsmall = rbig = inclusive ? radius+max_pixrad() : radius;
-     185             : 
-     186           0 :     if (rsmall>=pi)
-     187           0 :       { pixset.append(0,npix_); return; }
-     188             : 
-     189           0 :     rbig = min(pi,rbig);
-     190             : 
-     191           0 :     double cosrsmall = cos(rsmall);
-     192           0 :     double cosrbig = cos(rbig);
-     193             : 
-     194           0 :     double z0 = cos(ptg.theta);
-     195           0 :     double xa = 1./sqrt((1-z0)*(1+z0));
-     196             : 
-     197           0 :     I cpix=zphi2pix(z0,ptg.phi);
-     198             : 
-     199           0 :     double rlat1 = ptg.theta - rsmall;
-     200           0 :     double zmax = cos(rlat1);
-     201           0 :     I irmin = ring_above (zmax)+1;
-     202             : 
-     203           0 :     if ((rlat1<=0) && (irmin>1)) // north pole in the disk
-     204             :       {
-     205             :       I sp,rp; bool dummy;
-     206           0 :       get_ring_info_small(irmin-1,sp,rp,dummy);
-     207           0 :       pixset.append(0,sp+rp);
-     208             :       }
-     209             : 
-     210           0 :     if ((fct>1) && (rlat1>0)) irmin=max(I(1),irmin-1);
-     211             : 
-     212           0 :     double rlat2 = ptg.theta + rsmall;
-     213           0 :     double zmin = cos(rlat2);
-     214           0 :     I irmax = ring_above (zmin);
-     215             : 
-     216           0 :     if ((fct>1) && (rlat2<pi)) irmax=min(4*nside_-1,irmax+1);
-     217             : 
-     218           0 :     for (I iz=irmin; iz<=irmax; ++iz)
-     219             :       {
-     220           0 :       double z=ring2z(iz);
-     221           0 :       double x = (cosrbig-z*z0)*xa;
-     222           0 :       double ysq = 1-z*z-x*x;
-     223           0 :       double dphi = (ysq<=0) ? pi-1e-15 : atan2(sqrt(ysq),x);
-     224             :       I nr, ipix1;
-     225             :       bool shifted;
-     226           0 :       get_ring_info_small(iz,ipix1,nr,shifted);
-     227           0 :       double shift = shifted ? 0.5 : 0.;
-     228             : 
-     229           0 :       I ipix2 = ipix1 + nr - 1; // highest pixel number in the ring
-     230             : 
-     231           0 :       I ip_lo = ifloor<I>(nr*inv_twopi*(ptg.phi-dphi) - shift)+1;
-     232           0 :       I ip_hi = ifloor<I>(nr*inv_twopi*(ptg.phi+dphi) - shift);
-     233             : 
-     234           0 :       if (fct>1)
-     235             :         {
-     236           0 :         while ((ip_lo<=ip_hi) && check_pixel_ring
-     237           0 :                (*this,b2,ip_lo,nr,ipix1,fct,z0,ptg.phi,cosrsmall,cpix))
-     238           0 :           ++ip_lo;
-     239           0 :         while ((ip_hi>ip_lo) && check_pixel_ring
-     240           0 :                (*this,b2,ip_hi,nr,ipix1,fct,z0,ptg.phi,cosrsmall,cpix))
-     241           0 :           --ip_hi;
-     242             :         }
-     243             : 
-     244           0 :       if (ip_lo<=ip_hi)
-     245             :         {
-     246           0 :         if (ip_hi>=nr)
-     247           0 :           { ip_lo-=nr; ip_hi-=nr; }
-     248           0 :         if (ip_lo<0)
-     249             :           {
-     250           0 :           pixset.append(ipix1,ipix1+ip_hi+1);
-     251           0 :           pixset.append(ipix1+ip_lo+nr,ipix2+1);
-     252             :           }
-     253             :         else
-     254           0 :           pixset.append(ipix1+ip_lo,ipix1+ip_hi+1);
-     255             :         }
-     256             :       }
-     257           0 :     if ((rlat2>=pi) && (irmax+1<4*nside_)) // south pole in the disk
-     258             :       {
-     259             :       I sp,rp; bool dummy;
-     260           0 :       get_ring_info_small(irmax+1,sp,rp,dummy);
-     261           0 :       pixset.append(sp,npix_);
-     262             :       }
-     263             :     }
-     264             :   else // scheme_==NEST
-     265             :     {
-     266           0 :     if (radius>=pi) // disk covers the whole sphere
-     267           0 :       { pixset.append(0,npix_); return; }
-     268             : 
-     269             :     int oplus = 0;
-     270           0 :     if (inclusive)
-     271             :       {
-     272           0 :       planck_assert ((I(1)<<(order_max-order_))>=fact,
-     273             :         "invalid oversampling factor");
-     274           0 :       planck_assert ((fact&(fact-1))==0,
-     275             :         "oversampling factor must be a power of 2");
-     276           0 :       oplus=ilog2(fact);
-     277             :       }
-     278           0 :     int omax=order_+oplus; // the order up to which we test
-     279             : 
-     280             :     vec3 vptg(ptg);
-     281           0 :     arr<T_Healpix_Base<I> > base(omax+1);
-     282             :     arr<double> crpdr(omax+1), crmdr(omax+1);
-     283           0 :     double cosrad=cos(radius);
-     284           0 :     for (int o=0; o<=omax; ++o) // prepare data at the required orders
-     285             :       {
-     286           0 :       base[o].Set(o,NEST);
-     287           0 :       double dr=base[o].max_pixrad(); // safety distance
-     288           0 :       crpdr[o] = (radius+dr>pi) ? -1. : cos(radius+dr);
-     289           0 :       crmdr[o] = (radius-dr<0.) ?  1. : cos(radius-dr);
-     290             :       }
-     291             :     vector<pair<I,int> > stk; // stack for pixel numbers and their orders
-     292           0 :     stk.reserve(12+3*omax); // reserve maximum size to avoid reallocation
-     293           0 :     for (int i=0; i<12; ++i) // insert the 12 base pixels in reverse order
-     294           0 :       stk.push_back(make_pair(I(11-i),0));
-     295             : 
-     296           0 :     int stacktop=0; // a place to save a stack position
-     297             : 
-     298           0 :     while (!stk.empty()) // as long as there are pixels on the stack
-     299             :       {
-     300             :       // pop current pixel number and order from the stack
-     301           0 :       I pix=stk.back().first;
-     302           0 :       int o=stk.back().second;
-     303             :       stk.pop_back();
-     304             : 
-     305             :       double z,phi;
-     306             :       base[o].pix2zphi(pix,z,phi);
-     307             :       // cosine of angular distance between pixel center and disk center
-     308           0 :       double cangdist=cosdist_zphi(vptg.z,ptg.phi,z,phi);
-     309             : 
-     310           0 :       if (cangdist>crpdr[o])
-     311             :         {
-     312           0 :         int zone = (cangdist<cosrad) ? 1 : ((cangdist<=crmdr[o]) ? 2 : 3);
-     313             : 
-     314           0 :         check_pixel (o, order_, omax, zone, pixset, pix, stk, inclusive,
-     315             :           stacktop);
-     316             :         }
-     317             :       }
-     318             :     }
-     319             :   }
-     320             : 
-     321           0 : template<typename I> void T_Healpix_Base<I>::query_disc
-     322             :   (pointing ptg, double radius, rangeset<I> &pixset) const
-     323             :   {
-     324           0 :   query_disc_internal (ptg, radius, 0, pixset);
-     325           0 :   }
-     326             : 
-     327           0 : template<typename I> void T_Healpix_Base<I>::query_disc_inclusive
-     328             :   (pointing ptg, double radius, rangeset<I> &pixset, int fact) const
-     329             :   {
-     330           0 :   planck_assert(fact>0,"fact must be a positive integer");
-     331           0 :   if ((sizeof(I)<8) && (((I(1)<<order_max)/nside_)<fact))
-     332             :     {
-     333           0 :     T_Healpix_Base<int64> base2(nside_,scheme_,SET_NSIDE);
-     334           0 :     base2.query_disc_internal(ptg,radius,fact,pixset);
-     335             :     return;
-     336             :     }
-     337           0 :   query_disc_internal (ptg, radius, fact, pixset);
-     338             :   }
-     339             : 
-     340             : template<typename I> template<typename I2>
-     341           0 :   void T_Healpix_Base<I>::query_multidisc (const arr<vec3> &norm,
-     342             :   const arr<double> &rad, int fact, rangeset<I2> &pixset) const
-     343             :   {
-     344           0 :   bool inclusive = (fact!=0);
-     345             :   tsize nv=norm.size();
-     346           0 :   planck_assert(nv==rad.size(),"inconsistent input arrays");
-     347             :   pixset.clear();
-     348             : 
-     349           0 :   if (scheme_==RING)
-     350             :     {
-     351             :     I fct=1;
-     352           0 :     if (inclusive)
-     353             :       {
-     354           0 :       planck_assert (((I(1)<<order_max)/nside_)>=fact,
-     355             :         "invalid oversampling factor");
-     356             :       fct = fact;
-     357             :       }
-     358           0 :     T_Healpix_Base b2;
-     359             :     double rpsmall, rpbig;
-     360           0 :     if (fct>1)
-     361             :       {
-     362           0 :       b2.SetNside(fct*nside_,RING);
-     363           0 :       rpsmall = b2.max_pixrad();
-     364           0 :       rpbig = max_pixrad();
-     365             :       }
-     366             :     else
-     367           0 :       rpsmall = rpbig = inclusive ? max_pixrad() : 0;
-     368             : 
-     369           0 :     I irmin=1, irmax=4*nside_-1;
-     370             :     vector<double> z0,xa,cosrsmall,cosrbig;
-     371             :     vector<pointing> ptg;
-     372             :     vector<I> cpix;
-     373           0 :     for (tsize i=0; i<nv; ++i)
-     374             :       {
-     375           0 :       double rsmall=rad[i]+rpsmall;
-     376           0 :       if (rsmall<pi)
-     377             :         {
-     378           0 :         double rbig=min(pi,rad[i]+rpbig);
-     379             :         pointing pnt=pointing(norm[i]);
-     380           0 :         cosrsmall.push_back(cos(rsmall));
-     381           0 :         cosrbig.push_back(cos(rbig));
-     382           0 :         double cth=cos(pnt.theta);
-     383           0 :         z0.push_back(cth);
-     384           0 :         if (fct>1) cpix.push_back(zphi2pix(cth,pnt.phi));
-     385           0 :         xa.push_back(1./sqrt((1-cth)*(1+cth)));
-     386           0 :         ptg.push_back(pnt);
-     387             : 
-     388           0 :         double rlat1 = pnt.theta - rsmall;
-     389           0 :         double zmax = cos(rlat1);
-     390           0 :         I irmin_t = (rlat1<=0) ? 1 : ring_above (zmax)+1;
-     391             : 
-     392           0 :         if ((fct>1) && (rlat1>0)) irmin_t=max(I(1),irmin_t-1);
-     393             : 
-     394           0 :         double rlat2 = pnt.theta + rsmall;
-     395           0 :         double zmin = cos(rlat2);
-     396           0 :         I irmax_t = (rlat2>=pi) ? 4*nside_-1 : ring_above (zmin);
-     397             : 
-     398           0 :         if ((fct>1) && (rlat2<pi)) irmax_t=min(4*nside_-1,irmax_t+1);
-     399             : 
-     400             :         if (irmax_t < irmax) irmax=irmax_t;
-     401             :         if (irmin_t > irmin) irmin=irmin_t;
-     402             :         }
-     403             :       }
-     404             : 
-     405           0 :     for (I iz=irmin; iz<=irmax; ++iz)
-     406             :       {
-     407           0 :       double z=ring2z(iz);
-     408             :       I ipix1,nr;
-     409             :       bool shifted;
-     410           0 :       get_ring_info_small(iz,ipix1,nr,shifted);
-     411           0 :       double shift = shifted ? 0.5 : 0.;
-     412             :       rangeset<I2> tr;
-     413           0 :       tr.append(ipix1,ipix1+nr);
-     414           0 :       for (tsize j=0; j<z0.size(); ++j)
-     415             :         {
-     416           0 :         double x = (cosrbig[j]-z*z0[j])*xa[j];
-     417           0 :         double ysq = 1.-z*z-x*x;
-     418           0 :         double dphi = (ysq<=0) ? pi-1e-15 : atan2(sqrt(ysq),x);
-     419           0 :         I ip_lo = ifloor<I>(nr*inv_twopi*(ptg[j].phi-dphi) - shift)+1;
-     420           0 :         I ip_hi = ifloor<I>(nr*inv_twopi*(ptg[j].phi+dphi) - shift);
-     421           0 :         if (fct>1)
-     422             :           {
-     423           0 :           while ((ip_lo<=ip_hi) && check_pixel_ring
-     424           0 :             (*this,b2,ip_lo,nr,ipix1,fct,z0[j],ptg[j].phi,cosrsmall[j],cpix[j]))
-     425           0 :             ++ip_lo;
-     426           0 :           while ((ip_hi>ip_lo) && check_pixel_ring
-     427           0 :             (*this,b2,ip_hi,nr,ipix1,fct,z0[j],ptg[j].phi,cosrsmall[j],cpix[j]))
-     428           0 :             --ip_hi;
-     429             :           }
-     430           0 :         if (ip_hi>=nr)
-     431           0 :           { ip_lo-=nr; ip_hi-=nr;}
-     432           0 :         if (ip_lo<0)
-     433           0 :           tr.remove(ipix1+ip_hi+1,ipix1+ip_lo+nr);
-     434             :         else
-     435           0 :           tr.intersect(ipix1+ip_lo,ipix1+ip_hi+1);
-     436             :         }
-     437           0 :       pixset.append(tr);
-     438             :       }
-     439             :     }
-     440             :   else // scheme_ == NEST
-     441             :     {
-     442             :     int oplus = 0;
-     443           0 :     if (inclusive)
-     444             :       {
-     445           0 :       planck_assert ((I(1)<<(order_max-order_))>=fact,
-     446             :         "invalid oversampling factor");
-     447           0 :       planck_assert ((fact&(fact-1))==0,
-     448             :         "oversampling factor must be a power of 2");
-     449           0 :       oplus=ilog2(fact);
-     450             :       }
-     451           0 :     int omax=order_+oplus; // the order up to which we test
-     452             : 
-     453             :     // TODO: ignore all disks with radius>=pi
-     454             : 
-     455           0 :     arr<T_Healpix_Base<I> > base(omax+1);
-     456             :     arr3<double> crlimit(omax+1,nv,3);
-     457           0 :     for (int o=0; o<=omax; ++o) // prepare data at the required orders
-     458             :       {
-     459           0 :       base[o].Set(o,NEST);
-     460           0 :       double dr=base[o].max_pixrad(); // safety distance
-     461           0 :       for (tsize i=0; i<nv; ++i)
-     462             :         {
-     463           0 :         crlimit(o,i,0) = (rad[i]+dr>pi) ? -1. : cos(rad[i]+dr);
-     464           0 :         crlimit(o,i,1) = (o==0) ? cos(rad[i]) : crlimit(0,i,1);
-     465           0 :         crlimit(o,i,2) = (rad[i]-dr<0.) ?  1. : cos(rad[i]-dr);
-     466             :         }
-     467             :       }
-     468             : 
-     469             :     vector<pair<I,int> > stk; // stack for pixel numbers and their orders
-     470           0 :     stk.reserve(12+3*omax); // reserve maximum size to avoid reallocation
-     471           0 :     for (int i=0; i<12; ++i) // insert the 12 base pixels in reverse order
-     472           0 :       stk.push_back(make_pair(I(11-i),0));
-     473             : 
-     474           0 :     int stacktop=0; // a place to save a stack position
-     475             : 
-     476           0 :     while (!stk.empty()) // as long as there are pixels on the stack
-     477             :       {
-     478             :       // pop current pixel number and order from the stack
-     479           0 :       I pix=stk.back().first;
-     480           0 :       int o=stk.back().second;
-     481             :       stk.pop_back();
-     482             : 
-     483           0 :       vec3 pv(base[o].pix2vec(pix));
-     484             : 
-     485             :       tsize zone=3;
-     486           0 :       for (tsize i=0; i<nv; ++i)
-     487             :         {
-     488             :         double crad=dotprod(pv,norm[i]);
-     489           0 :         for (tsize iz=0; iz<zone; ++iz)
-     490           0 :           if (crad<crlimit(o,i,iz))
-     491           0 :             if ((zone=iz)==0) goto bailout;
-     492             :         }
-     493             : 
-     494           0 :       check_pixel (o, order_, omax, zone, pixset, pix, stk, inclusive,
-     495             :         stacktop);
-     496           0 :       bailout:;
-     497             :       }
-     498             :     }
-     499           0 :   }
-     500             : 
-     501           0 : template<typename I> void T_Healpix_Base<I>::query_multidisc_general
-     502             :   (const arr<vec3> &norm, const arr<double> &rad, bool inclusive,
-     503             :   const vector<int> &cmds, rangeset<I> &pixset) const
-     504             :   {
-     505             :   tsize nv=norm.size();
-     506           0 :   planck_assert(nv==rad.size(),"inconsistent input arrays");
-     507             :   pixset.clear();
-     508             : 
-     509           0 :   if (scheme_==RING)
-     510             :     {
-     511           0 :     planck_fail ("not yet implemented");
-     512             :     }
-     513             :   else // scheme_ == NEST
-     514             :     {
-     515           0 :     int oplus=inclusive ? 2 : 0;
-     516           0 :     int omax=min(order_max,order_+oplus); // the order up to which we test
-     517             : 
-     518             :     // TODO: ignore all disks with radius>=pi
-     519             : 
-     520           0 :     arr<T_Healpix_Base<I> > base(omax+1);
-     521             :     arr3<double> crlimit(omax+1,nv,3);
-     522           0 :     for (int o=0; o<=omax; ++o) // prepare data at the required orders
-     523             :       {
-     524           0 :       base[o].Set(o,NEST);
-     525           0 :       double dr=base[o].max_pixrad(); // safety distance
-     526           0 :       for (tsize i=0; i<nv; ++i)
-     527             :         {
-     528           0 :         crlimit(o,i,0) = (rad[i]+dr>pi) ? -1. : cos(rad[i]+dr);
-     529           0 :         crlimit(o,i,1) = (o==0) ? cos(rad[i]) : crlimit(0,i,1);
-     530           0 :         crlimit(o,i,2) = (rad[i]-dr<0.) ?  1. : cos(rad[i]-dr);
-     531             :         }
-     532             :       }
-     533             : 
-     534             :     vector<pair<I,int> > stk; // stack for pixel numbers and their orders
-     535           0 :     stk.reserve(12+3*omax); // reserve maximum size to avoid reallocation
-     536           0 :     for (int i=0; i<12; ++i) // insert the 12 base pixels in reverse order
-     537           0 :       stk.push_back(make_pair(I(11-i),0));
-     538             : 
-     539           0 :     int stacktop=0; // a place to save a stack position
-     540             :     arr<tsize> zone(nv);
-     541             : 
-     542           0 :     vector<tsize> zstk; zstk.reserve(cmds.size());
-     543             : 
-     544           0 :     while (!stk.empty()) // as long as there are pixels on the stack
-     545             :       {
-     546             :       // pop current pixel number and order from the stack
-     547           0 :       I pix=stk.back().first;
-     548           0 :       int o=stk.back().second;
-     549             :       stk.pop_back();
-     550             : 
-     551           0 :       vec3 pv(base[o].pix2vec(pix));
-     552             : 
-     553           0 :       for (tsize i=0; i<nv; ++i)
-     554             :         {
-     555           0 :         zone[i]=3;
-     556             :         double crad=dotprod(pv,norm[i]);
-     557           0 :         for (tsize iz=0; iz<zone[i]; ++iz)
-     558           0 :           if (crad<crlimit(o,i,iz))
-     559           0 :             zone[i]=iz;
-     560             :         }
-     561             : 
-     562           0 :       for (tsize i=0; i<cmds.size(); ++i)
-     563             :         {
-     564             :         tsize tmp;
-     565           0 :         switch (cmds[i])
-     566             :           {
-     567             :           case -1: // union
-     568           0 :             tmp=zstk.back(); zstk.pop_back();
-     569           0 :             zstk.back() = max(zstk.back(),tmp);
-     570           0 :             break;
-     571             :           case -2: // intersection
-     572           0 :             tmp=zstk.back(); zstk.pop_back();
-     573           0 :             zstk.back() = min(zstk.back(),tmp);
-     574           0 :             break;
-     575             :           default: // add value
-     576           0 :             zstk.push_back(zone[cmds[i]]);
-     577             :           }
-     578             :         }
-     579           0 :       planck_assert(zstk.size()==1,"inconsistent commands");
-     580           0 :       tsize zn=zstk[0]; zstk.pop_back();
-     581             : 
-     582           0 :       check_pixel (o, order_, omax, zn, pixset, pix, stk, inclusive,
-     583             :         stacktop);
-     584             :       }
-     585             :     }
-     586           0 :   }
-     587             : 
-     588             : template<> inline int T_Healpix_Base<int>::spread_bits (int v) const
-     589         421 :   { return utab[v&0xff] | (utab[(v>>8)&0xff]<<16); }
-     590           0 : template<> inline int64 T_Healpix_Base<int64>::spread_bits (int v) const
-     591             :   {
-     592           0 :   return  int64(utab[ v     &0xff])      | (int64(utab[(v>> 8)&0xff])<<16)
-     593           0 :        | (int64(utab[(v>>16)&0xff])<<32) | (int64(utab[(v>>24)&0xff])<<48);
-     594             :   }
-     595             : 
-     596             : template<> inline int T_Healpix_Base<int>::compress_bits (int v) const
-     597             :   {
-     598           0 :   int raw = (v&0x5555) | ((v&0x55550000)>>15);
-     599           0 :   return ctab[raw&0xff] | (ctab[raw>>8]<<4);
-     600             :   }
-     601         842 : template<> inline int T_Healpix_Base<int64>::compress_bits (int64 v) const
-     602             :   {
-     603         842 :   int64 raw = v&0x5555555555555555ull;
-     604         842 :   raw|=raw>>15;
-     605         842 :   return ctab[ raw     &0xff]      | (ctab[(raw>> 8)&0xff]<< 4)
-     606         842 :       | (ctab[(raw>>32)&0xff]<<16) | (ctab[(raw>>40)&0xff]<<20);
-     607             :   }
-     608             : 
-     609         421 : template<typename I> inline void T_Healpix_Base<I>::nest2xyf (I pix, int &ix,
-     610             :   int &iy, int &face_num) const
-     611             :   {
-     612         421 :   face_num = pix>>(2*order_);
-     613         421 :   pix &= (npface_-1);
-     614         421 :   ix = compress_bits(pix);
-     615         421 :   iy = compress_bits(pix>>1);
-     616         421 :   }
-     617             : 
-     618         421 : template<typename I> inline I T_Healpix_Base<I>::xyf2nest (int ix, int iy,
-     619             :   int face_num) const
-     620         421 :   { return (I(face_num)<<(2*order_)) + spread_bits(ix) + (spread_bits(iy)<<1); }
-     621             : 
-     622         421 : template<typename I> void T_Healpix_Base<I>::ring2xyf (I pix, int &ix, int &iy,
-     623             :   int &face_num) const
-     624             :   {
-     625             :   I iring, iphi, kshift, nr;
-     626         421 :   I nl2 = 2*nside_;
-     627             : 
-     628         421 :   if (pix<ncap_) // North Polar cap
-     629             :     {
-     630           0 :     iring = (1+isqrt(1+2*pix))>>1; //counted from North pole
-     631           0 :     iphi  = (pix+1) - 2*iring*(iring-1);
-     632             :     kshift = 0;
-     633             :     nr = iring;
-     634           0 :     face_num=(iphi-1)/nr;
-     635             :     }
-     636         421 :   else if (pix<(npix_-ncap_)) // Equatorial region
-     637             :     {
-     638         421 :     I ip = pix - ncap_;
-     639         421 :     I tmp = (order_>=0) ? ip>>(order_+2) : ip/(4*nside_);
-     640         421 :     iring = tmp+nside_;
-     641         421 :     iphi = ip-tmp*4*nside_ + 1;
-     642         421 :     kshift = (iring+nside_)&1;
-     643             :     nr = nside_;
-     644         421 :     I ire = iring-nside_+1,
-     645         421 :       irm = nl2+2-ire;
-     646         421 :     I ifm = iphi - ire/2 + nside_ -1,
-     647         421 :       ifp = iphi - irm/2 + nside_ -1;
-     648         421 :     if (order_>=0)
-     649         421 :       { ifm >>= order_; ifp >>= order_; }
-     650             :     else
-     651           0 :       { ifm /= nside_; ifp /= nside_; }
-     652         421 :     face_num = (ifp==ifm) ? (ifp|4) : ((ifp<ifm) ? ifp : (ifm+8));
-     653             :     }
-     654             :   else // South Polar cap
-     655             :     {
-     656           0 :     I ip = npix_ - pix;
-     657           0 :     iring = (1+isqrt(2*ip-1))>>1; //counted from South pole
-     658           0 :     iphi  = 4*iring + 1 - (ip - 2*iring*(iring-1));
-     659             :     kshift = 0;
-     660             :     nr = iring;
-     661           0 :     iring = 2*nl2-iring;
-     662           0 :     face_num = 8 + (iphi-1)/nr;
-     663             :     }
-     664             : 
-     665         421 :   I irt = iring - (jrll[face_num]*nside_) + 1;
-     666         421 :   I ipt = 2*iphi- jpll[face_num]*nr - kshift -1;
-     667         421 :   if (ipt>=nl2) ipt-=8*nside_;
-     668             : 
-     669         421 :   ix =  (ipt-irt) >>1;
-     670         421 :   iy = (-ipt-irt) >>1;
-     671         421 :   }
-     672             : 
-     673           0 : template<typename I> I T_Healpix_Base<I>::xyf2ring (int ix, int iy,
-     674             :   int face_num) const
-     675             :   {
-     676           0 :   I nl4 = 4*nside_;
-     677           0 :   I jr = (jrll[face_num]*nside_) - ix - iy  - 1;
-     678             : 
-     679             :   I nr, kshift, n_before;
-     680             : 
-     681             :   bool shifted;
-     682           0 :   get_ring_info_small(jr,n_before,nr,shifted);
-     683           0 :   nr>>=2;
-     684           0 :   kshift=1-shifted;
-     685           0 :   I jp = (jpll[face_num]*nr + ix - iy + 1 + kshift) / 2;
-     686           0 :   planck_assert(jp<=4*nr,"must not happen");
-     687           0 :   if (jp<1) jp+=nl4; // assumption: if this triggers, then nl4==4*nr
-     688             : 
-     689           0 :   return n_before + jp - 1;
-     690             :   }
-     691             : 
-     692           0 : template<typename I> T_Healpix_Base<I>::T_Healpix_Base ()
-     693           0 :   : order_(-1), nside_(0), npface_(0), ncap_(0), npix_(0),
-     694           0 :     fact1_(0), fact2_(0), scheme_(RING) {}
-     695             : 
-     696          29 : template<typename I> void T_Healpix_Base<I>::Set (int order,
-     697             :   Healpix_Ordering_Scheme scheme)
-     698             :   {
-     699          29 :   planck_assert ((order>=0)&&(order<=order_max), "bad order");
-     700          29 :   order_  = order;
-     701          29 :   nside_  = I(1)<<order;
-     702          29 :   npface_ = nside_<<order_;
-     703          29 :   ncap_   = (npface_-nside_)<<1;
-     704          29 :   npix_   = 12*npface_;
-     705          29 :   fact2_  = 4./npix_;
-     706          29 :   fact1_  = (nside_<<1)*fact2_;
-     707          29 :   scheme_ = scheme;
-     708          29 :   }
-     709           0 : template<typename I> void T_Healpix_Base<I>::SetNside (I nside,
-     710             :   Healpix_Ordering_Scheme scheme)
-     711             :   {
-     712           0 :   order_  = nside2order(nside);
-     713           0 :   planck_assert ((scheme!=NEST) || (order_>=0),
-     714             :     "SetNside: nside must be power of 2 for nested maps");
-     715           0 :   nside_  = nside;
-     716           0 :   npface_ = nside_*nside_;
-     717           0 :   ncap_   = (npface_-nside_)<<1;
-     718           0 :   npix_   = 12*npface_;
-     719           0 :   fact2_  = 4./npix_;
-     720           0 :   fact1_  = (nside_<<1)*fact2_;
-     721           0 :   scheme_ = scheme;
-     722           0 :   }
-     723             : 
-     724           0 : template<typename I> double T_Healpix_Base<I>::ring2z (I ring) const
-     725             :   {
-     726           0 :   if (ring<nside_)
-     727           0 :     return 1 - ring*ring*fact2_;
-     728           0 :   if (ring <=3*nside_)
-     729           0 :     return (2*nside_-ring)*fact1_;
-     730           0 :   ring=4*nside_ - ring;
-     731           0 :   return ring*ring*fact2_ - 1;
-     732             :   }
-     733             : 
-     734           0 : template<typename I> I T_Healpix_Base<I>::pix2ring (I pix) const
-     735             :   {
-     736           0 :   if (scheme_==RING)
-     737             :     {
-     738           0 :     if (pix<ncap_) // North Polar cap
-     739           0 :       return (1+I(isqrt(1+2*pix)))>>1; // counted from North pole
-     740           0 :     else if (pix<(npix_-ncap_)) // Equatorial region
-     741           0 :       return (pix-ncap_)/(4*nside_) + nside_; // counted from North pole
-     742             :     else // South Polar cap
-     743           0 :       return 4*nside_-((1+I(isqrt(2*(npix_-pix)-1)))>>1);
-     744             :     }
-     745             :   else
-     746             :     {
-     747             :     int face_num, ix, iy;
-     748           0 :     nest2xyf(pix,ix,iy,face_num);
-     749           0 :     return (I(jrll[face_num])<<order_) - ix - iy - 1;
-     750             :     }
-     751             :   }
-     752             : 
-     753           0 : template<typename I> I T_Healpix_Base<I>::nest2ring (I pix) const
-     754             :   {
-     755           0 :   planck_assert(order_>=0, "hierarchical map required");
-     756             :   int ix, iy, face_num;
-     757           0 :   nest2xyf (pix, ix, iy, face_num);
-     758           0 :   return xyf2ring (ix, iy, face_num);
-     759             :   }
-     760             : 
-     761         421 : template<typename I> I T_Healpix_Base<I>::ring2nest (I pix) const
-     762             :   {
-     763         421 :   planck_assert(order_>=0, "hierarchical map required");
-     764             :   int ix, iy, face_num;
-     765         421 :   ring2xyf (pix, ix, iy, face_num);
-     766         421 :   return xyf2nest (ix, iy, face_num);
-     767             :   }
-     768             : 
-     769           0 : template<typename I> inline I T_Healpix_Base<I>::nest_peano_helper
-     770             :   (I pix, int dir) const
-     771             :   {
-     772           0 :   int face = pix>>(2*order_);
-     773             :   I result = 0;
-     774           0 :   uint8 path = peano_face2path[dir][face];
-     775             : 
-     776           0 :   for (int shift=2*order_-2; shift>=0; shift-=2)
-     777             :     {
-     778           0 :     uint8 spix = uint8((pix>>shift) & 0x3);
-     779           0 :     result <<= 2;
-     780           0 :     result |= peano_subpix[dir][path][spix];
-     781           0 :     path=peano_subpath[dir][path][spix];
-     782             :     }
-     783             : 
-     784           0 :   return result + (I(peano_face2face[dir][face])<<(2*order_));
-     785             :   }
-     786             : 
-     787           0 : template<typename I> I T_Healpix_Base<I>::nest2peano (I pix) const
-     788           0 :   { return nest_peano_helper(pix,0); }
-     789             : 
-     790           0 : template<typename I> I T_Healpix_Base<I>::peano2nest (I pix) const
-     791           0 :   { return nest_peano_helper(pix,1); }
-     792             : 
-     793       24585 : template<typename I> I T_Healpix_Base<I>::loc2pix (double z, double phi,
-     794             :   double sth, bool have_sth) const
-     795             :   {
-     796             :   double za = abs(z);
-     797       24585 :   double tt = fmodulo(phi*inv_halfpi,4.0); // in [0,4)
-     798             : 
-     799       24585 :   if (scheme_==RING)
-     800             :     {
-     801       24585 :     if (za<=twothird) // Equatorial region
-     802             :       {
-     803       16535 :       I nl4 = 4*nside_;
-     804       16535 :       double temp1 = nside_*(0.5+tt);
-     805       16535 :       double temp2 = nside_*z*0.75;
-     806       16535 :       I jp = I(temp1-temp2); // index of  ascending edge line
-     807       16535 :       I jm = I(temp1+temp2); // index of descending edge line
-     808             : 
-     809             :       // ring number counted from z=2/3
-     810       16535 :       I ir = nside_ + 1 + jp - jm; // in {1,2n+1}
-     811       16535 :       I kshift = 1-(ir&1); // kshift=1 if ir even, 0 otherwise
-     812             : 
-     813       16535 :       I t1 = jp+jm-nside_+kshift+1+nl4+nl4;
-     814       16535 :       I ip = (order_>0) ?
-     815       16535 :         (t1>>1)&(nl4-1) : ((t1>>1)%nl4); // in {0,4n-1}
-     816             : 
-     817       16535 :       return ncap_ + (ir-1)*nl4 + ip;
-     818             :       }
-     819             :     else  // North & South polar caps
-     820             :       {
-     821        8050 :       double tp = tt-I(tt);
-     822        8050 :       double tmp = ((za<0.99)||(!have_sth)) ?
-     823        7809 :                    nside_*sqrt(3*(1-za)) :
-     824         241 :                    nside_*sth/sqrt((1.+za)/3.);
-     825             : 
-     826        8050 :       I jp = I(tp*tmp); // increasing edge line index
-     827        8050 :       I jm = I((1.0-tp)*tmp); // decreasing edge line index
-     828             : 
-     829        8050 :       I ir = jp+jm+1; // ring number counted from the closest pole
-     830        8050 :       I ip = I(tt*ir); // in {0,4*ir-1}
-     831        8050 :       planck_assert((ip>=0)&&(ip<4*ir),"must not happen");
-     832             :       //ip %= 4*ir;
-     833             : 
-     834        8050 :       return (z>0)  ?  2*ir*(ir-1) + ip  :  npix_ - 2*ir*(ir+1) + ip;
-     835             :       }
-     836             :     }
-     837             :   else // scheme_ == NEST
-     838             :     {
-     839           0 :     if (za<=twothird) // Equatorial region
-     840             :       {
-     841           0 :       double temp1 = nside_*(0.5+tt);
-     842           0 :       double temp2 = nside_*(z*0.75);
-     843           0 :       I jp = I(temp1-temp2); // index of  ascending edge line
-     844           0 :       I jm = I(temp1+temp2); // index of descending edge line
-     845           0 :       I ifp = jp >> order_;  // in {0,4}
-     846           0 :       I ifm = jm >> order_;
-     847           0 :       int face_num = (ifp==ifm) ? (ifp|4) : ((ifp<ifm) ? ifp : (ifm+8));
-     848             : 
-     849           0 :       int ix = jm & (nside_-1),
-     850           0 :           iy = nside_ - (jp & (nside_-1)) - 1;
-     851           0 :       return xyf2nest(ix,iy,face_num);
-     852             :       }
-     853             :     else // polar region, za > 2/3
-     854             :       {
-     855           0 :       int ntt = min(3,int(tt));
-     856           0 :       double tp = tt-ntt;
-     857           0 :       double tmp = ((za<0.99)||(!have_sth)) ?
-     858           0 :                    nside_*sqrt(3*(1-za)) :
-     859           0 :                    nside_*sth/sqrt((1.+za)/3.);
-     860             : 
-     861           0 :       I jp = I(tp*tmp); // increasing edge line index
-     862           0 :       I jm = I((1.0-tp)*tmp); // decreasing edge line index
-     863           0 :       jp=min(jp,nside_-1); // for points too close to the boundary
-     864           0 :       jm=min(jm,nside_-1);
-     865           0 :       return (z>=0) ?
-     866           0 :         xyf2nest(nside_-jm -1,nside_-jp-1,ntt) : xyf2nest(jp,jm,ntt+8);
-     867             :       }
-     868             :     }
-     869             :   }
-     870             : 
-     871      135593 : template<typename I> void T_Healpix_Base<I>::pix2loc (I pix, double &z,
-     872             :   double &phi, double &sth, bool &have_sth) const
-     873             :   {
-     874      135593 :   have_sth=false;
-     875      135593 :   if (scheme_==RING)
-     876             :     {
-     877      135172 :     if (pix<ncap_) // North Polar cap
-     878             :       {
-     879       22080 :       I iring = (1+I(isqrt(1+2*pix)))>>1; // counted from North pole
-     880       22080 :       I iphi  = (pix+1) - 2*iring*(iring-1);
-     881             : 
-     882       22080 :       double tmp=(iring*iring)*fact2_;
-     883       22080 :       z = 1.0 - tmp;
-     884       22080 :       if (z>0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
-     885       22080 :       phi = (iphi-0.5) * halfpi/iring;
-     886             :       }
-     887      113092 :     else if (pix<(npix_-ncap_)) // Equatorial region
-     888             :       {
-     889       91010 :       I nl4 = 4*nside_;
-     890       91010 :       I ip  = pix - ncap_;
-     891       91010 :       I tmp = (order_>=0) ? ip>>(order_+2) : ip/nl4;
-     892       91010 :       I iring = tmp + nside_,
-     893       91010 :         iphi = ip-nl4*tmp+1;
-     894             :       // 1 if iring+nside is odd, 1/2 otherwise
-     895       91010 :       double fodd = ((iring+nside_)&1) ? 1 : 0.5;
-     896             : 
-     897       91010 :       z = (2*nside_-iring)*fact1_;
-     898       91010 :       phi = (iphi-fodd) * pi*0.75*fact1_;
-     899             :       }
-     900             :     else // South Polar cap
-     901             :       {
-     902       22082 :       I ip = npix_ - pix;
-     903       22082 :       I iring = (1+I(isqrt(2*ip-1)))>>1; // counted from South pole
-     904       22082 :       I iphi  = 4*iring + 1 - (ip - 2*iring*(iring-1));
-     905             : 
-     906       22082 :       double tmp=(iring*iring)*fact2_;
-     907       22082 :       z = tmp - 1.0;
-     908       22082 :       if (z<-0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
-     909       22082 :       phi = (iphi-0.5) * halfpi/iring;
-     910             :       }
-     911             :     }
-     912             :   else
-     913             :     {
-     914             :     int face_num, ix, iy;
-     915         421 :     nest2xyf(pix,ix,iy,face_num);
-     916             : 
-     917         421 :     I jr = (I(jrll[face_num])<<order_) - ix - iy - 1;
-     918             : 
-     919             :     I nr;
-     920         421 :     if (jr<nside_)
-     921             :       {
-     922             :       nr = jr;
-     923           0 :       double tmp=(nr*nr)*fact2_;
-     924           0 :       z = 1 - tmp;
-     925           0 :       if (z>0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
-     926             :       }
-     927         421 :     else if (jr > 3*nside_)
-     928             :       {
-     929           0 :       nr = nside_*4-jr;
-     930           0 :       double tmp=(nr*nr)*fact2_;
-     931           0 :       z = tmp - 1;
-     932           0 :       if (z<-0.99) { sth=sqrt(tmp*(2.-tmp)); have_sth=true; }
-     933             :       }
-     934             :     else
-     935             :       {
-     936             :       nr = nside_;
-     937         421 :       z = (2*nside_-jr)*fact1_;
-     938             :       }
-     939             : 
-     940         421 :     I tmp=I(jpll[face_num])*nr+ix-iy;
-     941         421 :     planck_assert(tmp<8*nr,"must not happen");
-     942         421 :     if (tmp<0) tmp+=8*nr;
-     943         421 :     phi = (nr==nside_) ? 0.75*halfpi*tmp*fact1_ :
-     944           0 :                          (0.5*halfpi*tmp)/nr;
-     945             :     }
-     946      135593 :   }
-     947             : 
-     948             : template<typename I> template<typename I2>
-     949           0 :   void T_Healpix_Base<I>::query_polygon_internal
-     950             :   (const vector<pointing> &vertex, int fact, rangeset<I2> &pixset) const
-     951             :   {
-     952             :   bool inclusive = (fact!=0);
-     953             :   tsize nv=vertex.size();
-     954           0 :   tsize ncirc = inclusive ? nv+1 : nv;
-     955           0 :   planck_assert(nv>=3,"not enough vertices in polygon");
-     956             :   arr<vec3> vv(nv);
-     957           0 :   for (tsize i=0; i<nv; ++i)
-     958           0 :     vv[i]=vertex[i].to_vec3();
-     959             :   arr<vec3> normal(ncirc);
-     960             :   int flip=0;
-     961           0 :   for (tsize i=0; i<nv; ++i)
-     962             :     {
-     963           0 :     normal[i]=crossprod(vv[i],vv[(i+1)%nv]);
-     964           0 :     double hnd=dotprod(normal[i],vv[(i+2)%nv]);
-     965           0 :     planck_assert(abs(hnd)>1e-10,"degenerate corner");
-     966           0 :     if (i==0)
-     967           0 :       flip = (hnd<0.) ? -1 : 1;
-     968             :     else
-     969           0 :       planck_assert(flip*hnd>0,"polygon is not convex");
-     970           0 :     normal[i]*=flip/normal[i].Length();
-     971             :     }
-     972             :   arr<double> rad(ncirc,halfpi);
-     973           0 :   if (inclusive)
-     974             :     {
-     975             :     double cosrad;
-     976           0 :     find_enclosing_circle (vv, normal[nv], cosrad);
-     977           0 :     rad[nv]=acos(cosrad);
-     978             :     }
-     979           0 :   query_multidisc(normal,rad,fact,pixset);
-     980           0 :   }
-     981             : 
-     982           0 : template<typename I> void T_Healpix_Base<I>::query_polygon
-     983             :   (const vector<pointing> &vertex, rangeset<I> &pixset) const
-     984             :   {
-     985           0 :   query_polygon_internal(vertex, 0, pixset);
-     986           0 :   }
-     987             : 
-     988           0 : template<typename I> void T_Healpix_Base<I>::query_polygon_inclusive
-     989             :   (const vector<pointing> &vertex, rangeset<I> &pixset, int fact) const
-     990             :   {
-     991           0 :   planck_assert(fact>0,"fact must be a positive integer");
-     992           0 :   if ((sizeof(I)<8) && (((I(1)<<order_max)/nside_)<fact))
-     993             :     {
-     994           0 :     T_Healpix_Base<int64> base2(nside_,scheme_,SET_NSIDE);
-     995           0 :     base2.query_polygon_internal(vertex,fact,pixset);
-     996             :     return;
-     997             :     }
-     998           0 :   query_polygon_internal(vertex, fact, pixset);
-     999             :   }
-    1000             : 
-    1001           0 : template<typename I> void T_Healpix_Base<I>::query_strip_internal
-    1002             :   (double theta1, double theta2, bool inclusive, rangeset<I> &pixset) const
-    1003             :   {
-    1004           0 :   if (scheme_==RING)
-    1005             :     {
-    1006           0 :     I ring1 = max(I(1),1+ring_above(cos(theta1))),
-    1007           0 :       ring2 = min(4*nside_-1,ring_above(cos(theta2)));
-    1008           0 :     if (inclusive)
-    1009             :       {
-    1010           0 :       ring1 = max(I(1),ring1-1);
-    1011           0 :       ring2 = min(4*nside_-1,ring2+1);
-    1012             :       }
-    1013             : 
-    1014             :     I sp1,rp1,sp2,rp2;
-    1015             :     bool dummy;
-    1016           0 :     get_ring_info_small(ring1,sp1,rp1,dummy);
-    1017           0 :     get_ring_info_small(ring2,sp2,rp2,dummy);
-    1018           0 :     I pix1 = sp1,
-    1019           0 :       pix2 = sp2+rp2;
-    1020           0 :     if (pix1<=pix2) pixset.append(pix1,pix2);
-    1021             :     }
-    1022             :   else
-    1023           0 :     planck_fail("query_strip not yet implemented for NESTED");
-    1024           0 :   }
-    1025             : 
-    1026           0 : template<typename I> void T_Healpix_Base<I>::query_strip (double theta1,
-    1027             :   double theta2, bool inclusive, rangeset<I> &pixset) const
-    1028             :   {
-    1029             :   pixset.clear();
-    1030             : 
-    1031           0 :   if (theta1<theta2)
-    1032           0 :     query_strip_internal(theta1,theta2,inclusive,pixset);
-    1033             :   else
-    1034             :     {
-    1035           0 :     query_strip_internal(0.,theta2,inclusive,pixset);
-    1036             :     rangeset<I> ps2;
-    1037           0 :     query_strip_internal(theta1,pi,inclusive,ps2);
-    1038           0 :     pixset.append(ps2);
-    1039             :     }
-    1040           0 :   }
-    1041             : 
-    1042           0 : template<typename I> inline void T_Healpix_Base<I>::get_ring_info_small
-    1043             :   (I ring, I &startpix, I &ringpix, bool &shifted) const
-    1044             :   {
-    1045           0 :   if (ring < nside_)
-    1046             :     {
-    1047           0 :     shifted = true;
-    1048           0 :     ringpix = 4*ring;
-    1049           0 :     startpix = 2*ring*(ring-1);
-    1050             :     }
-    1051           0 :   else if (ring < 3*nside_)
-    1052             :     {
-    1053           0 :     shifted = ((ring-nside_) & 1) == 0;
-    1054           0 :     ringpix = 4*nside_;
-    1055           0 :     startpix = ncap_ + (ring-nside_)*ringpix;
-    1056             :     }
-    1057             :   else
-    1058             :     {
-    1059           0 :     shifted = true;
-    1060           0 :     I nr= 4*nside_-ring;
-    1061           0 :     ringpix = 4*nr;
-    1062           0 :     startpix = npix_-2*nr*(nr+1);
-    1063             :     }
-    1064           0 :   }
-    1065             : 
-    1066           0 : template<typename I> void T_Healpix_Base<I>::get_ring_info (I ring, I &startpix,
-    1067             :   I &ringpix, double &costheta, double &sintheta, bool &shifted) const
-    1068             :   {
-    1069           0 :   I northring = (ring>2*nside_) ? 4*nside_-ring : ring;
-    1070           0 :   if (northring < nside_)
-    1071             :     {
-    1072           0 :     double tmp = northring*northring*fact2_;
-    1073           0 :     costheta = 1 - tmp;
-    1074           0 :     sintheta = sqrt(tmp*(2-tmp));
-    1075           0 :     ringpix = 4*northring;
-    1076           0 :     shifted = true;
-    1077           0 :     startpix = 2*northring*(northring-1);
-    1078             :     }
-    1079             :   else
-    1080             :     {
-    1081           0 :     costheta = (2*nside_-northring)*fact1_;
-    1082           0 :     sintheta = sqrt((1+costheta)*(1-costheta));
-    1083           0 :     ringpix = 4*nside_;
-    1084           0 :     shifted = ((northring-nside_) & 1) == 0;
-    1085           0 :     startpix = ncap_ + (northring-nside_)*ringpix;
-    1086             :     }
-    1087           0 :   if (northring != ring) // southern hemisphere
-    1088             :     {
-    1089           0 :     costheta = -costheta;
-    1090           0 :     startpix = npix_ - startpix - ringpix;
-    1091             :     }
-    1092           0 :   }
-    1093           0 : template<typename I> void T_Healpix_Base<I>::get_ring_info2 (I ring,
-    1094             :   I &startpix, I &ringpix, double &theta, bool &shifted) const
-    1095             :   {
-    1096           0 :   I northring = (ring>2*nside_) ? 4*nside_-ring : ring;
-    1097           0 :   if (northring < nside_)
-    1098             :     {
-    1099           0 :     double tmp = northring*northring*fact2_;
-    1100           0 :     double costheta = 1 - tmp;
-    1101           0 :     double sintheta = sqrt(tmp*(2-tmp));
-    1102           0 :     theta = atan2(sintheta,costheta);
-    1103           0 :     ringpix = 4*northring;
-    1104           0 :     shifted = true;
-    1105           0 :     startpix = 2*northring*(northring-1);
-    1106             :     }
-    1107             :   else
-    1108             :     {
-    1109           0 :     theta = acos((2*nside_-northring)*fact1_);
-    1110           0 :     ringpix = 4*nside_;
-    1111           0 :     shifted = ((northring-nside_) & 1) == 0;
-    1112           0 :     startpix = ncap_ + (northring-nside_)*ringpix;
-    1113             :     }
-    1114           0 :   if (northring != ring) // southern hemisphere
-    1115             :     {
-    1116           0 :     theta = pi-theta;
-    1117           0 :     startpix = npix_ - startpix - ringpix;
-    1118             :     }
-    1119           0 :   }
-    1120             : 
-    1121           0 : template<typename I> void T_Healpix_Base<I>::neighbors (I pix,
-    1122             :   fix_arr<I,8> &result) const
-    1123             :   {
-    1124             :   int ix, iy, face_num;
-    1125           0 :   (scheme_==RING) ?
-    1126           0 :     ring2xyf(pix,ix,iy,face_num) : nest2xyf(pix,ix,iy,face_num);
-    1127             : 
-    1128           0 :   const I nsm1 = nside_-1;
-    1129           0 :   if ((ix>0)&&(ix<nsm1)&&(iy>0)&&(iy<nsm1))
-    1130             :     {
-    1131           0 :     if (scheme_==RING)
-    1132           0 :       for (int m=0; m<8; ++m)
-    1133           0 :         result[m] = xyf2ring(ix+nb_xoffset[m],iy+nb_yoffset[m],face_num);
-    1134             :     else
-    1135             :       {
-    1136           0 :       I fpix = I(face_num)<<(2*order_),
-    1137           0 :         px0=spread_bits(ix  ), py0=spread_bits(iy  )<<1,
-    1138           0 :         pxp=spread_bits(ix+1), pyp=spread_bits(iy+1)<<1,
-    1139           0 :         pxm=spread_bits(ix-1), pym=spread_bits(iy-1)<<1;
-    1140             : 
-    1141           0 :       result[0] = fpix+pxm+py0; result[1] = fpix+pxm+pyp;
-    1142           0 :       result[2] = fpix+px0+pyp; result[3] = fpix+pxp+pyp;
-    1143           0 :       result[4] = fpix+pxp+py0; result[5] = fpix+pxp+pym;
-    1144           0 :       result[6] = fpix+px0+pym; result[7] = fpix+pxm+pym;
-    1145             :       }
-    1146             :     }
-    1147             :   else
-    1148             :     {
-    1149           0 :     for (int i=0; i<8; ++i)
-    1150             :       {
-    1151           0 :       int x=ix+nb_xoffset[i], y=iy+nb_yoffset[i];
-    1152             :       int nbnum=4;
-    1153           0 :       if (x<0)
-    1154           0 :         { x+=nside_; nbnum-=1; }
-    1155           0 :       else if (x>=nside_)
-    1156           0 :         { x-=nside_; nbnum+=1; }
-    1157           0 :       if (y<0)
-    1158           0 :         { y+=nside_; nbnum-=3; }
-    1159           0 :       else if (y>=nside_)
-    1160           0 :         { y-=nside_; nbnum+=3; }
-    1161             : 
-    1162           0 :       int f = nb_facearray[nbnum][face_num];
-    1163           0 :       if (f>=0)
-    1164             :         {
-    1165           0 :         int bits = nb_swaparray[nbnum][face_num>>2];
-    1166           0 :         if (bits&1) x=nside_-x-1;
-    1167           0 :         if (bits&2) y=nside_-y-1;
-    1168           0 :         if (bits&4) std::swap(x,y);
-    1169           0 :         result[i] = (scheme_==RING) ? xyf2ring(x,y,f) : xyf2nest(x,y,f);
-    1170             :         }
-    1171             :       else
-    1172           0 :         result[i] = -1;
-    1173             :       }
-    1174             :     }
-    1175           0 :   }
-    1176             : 
-    1177           0 : template<typename I> void T_Healpix_Base<I>::get_interpol (const pointing &ptg,
-    1178             :   fix_arr<I,4> &pix, fix_arr<double,4> &wgt) const
-    1179             :   {
-    1180           0 :   planck_assert((ptg.theta>=0)&&(ptg.theta<=pi),"invalid theta value");
-    1181           0 :   double z = cos (ptg.theta);
-    1182           0 :   I ir1 = ring_above(z);
-    1183           0 :   I ir2 = ir1+1;
-    1184             :   double theta1, theta2, w1, tmp, dphi;
-    1185             :   I sp,nr;
-    1186             :   bool shift;
-    1187             :   I i1,i2;
-    1188           0 :   if (ir1>0)
-    1189             :     {
-    1190           0 :     get_ring_info2 (ir1, sp, nr, theta1, shift);
-    1191           0 :     dphi = twopi/nr;
-    1192           0 :     tmp = (ptg.phi/dphi - .5*shift);
-    1193           0 :     i1 = (tmp<0) ? I(tmp)-1 : I(tmp);
-    1194           0 :     w1 = (ptg.phi-(i1+.5*shift)*dphi)/dphi;
-    1195           0 :     i2 = i1+1;
-    1196           0 :     if (i1<0) i1 +=nr;
-    1197           0 :     if (i2>=nr) i2 -=nr;
-    1198           0 :     pix[0] = sp+i1; pix[1] = sp+i2;
-    1199           0 :     wgt[0] = 1-w1; wgt[1] = w1;
-    1200             :     }
-    1201           0 :   if (ir2<(4*nside_))
-    1202             :     {
-    1203           0 :     get_ring_info2 (ir2, sp, nr, theta2, shift);
-    1204           0 :     dphi = twopi/nr;
-    1205           0 :     tmp = (ptg.phi/dphi - .5*shift);
-    1206           0 :     i1 = (tmp<0) ? I(tmp)-1 : I(tmp);
-    1207           0 :     w1 = (ptg.phi-(i1+.5*shift)*dphi)/dphi;
-    1208           0 :     i2 = i1+1;
-    1209           0 :     if (i1<0) i1 +=nr;
-    1210           0 :     if (i2>=nr) i2 -=nr;
-    1211           0 :     pix[2] = sp+i1; pix[3] = sp+i2;
-    1212           0 :     wgt[2] = 1-w1; wgt[3] = w1;
-    1213             :     }
-    1214             : 
-    1215           0 :   if (ir1==0)
-    1216             :     {
-    1217           0 :     double wtheta = ptg.theta/theta2;
-    1218           0 :     wgt[2] *= wtheta; wgt[3] *= wtheta;
-    1219           0 :     double fac = (1-wtheta)*0.25;
-    1220           0 :     wgt[0] = fac; wgt[1] = fac; wgt[2] += fac; wgt[3] +=fac;
-    1221           0 :     pix[0] = (pix[2]+2)&3;
-    1222           0 :     pix[1] = (pix[3]+2)&3;
-    1223             :     }
-    1224           0 :   else if (ir2==4*nside_)
-    1225             :     {
-    1226           0 :     double wtheta = (ptg.theta-theta1)/(pi-theta1);
-    1227           0 :     wgt[0] *= (1-wtheta); wgt[1] *= (1-wtheta);
-    1228           0 :     double fac = wtheta*0.25;
-    1229           0 :     wgt[0] += fac; wgt[1] += fac; wgt[2] = fac; wgt[3] =fac;
-    1230           0 :     pix[2] = ((pix[0]+2)&3)+npix_-4;
-    1231           0 :     pix[3] = ((pix[1]+2)&3)+npix_-4;
-    1232             :     }
-    1233             :   else
-    1234             :     {
-    1235           0 :     double wtheta = (ptg.theta-theta1)/(theta2-theta1);
-    1236           0 :     wgt[0] *= (1-wtheta); wgt[1] *= (1-wtheta);
-    1237           0 :     wgt[2] *= wtheta; wgt[3] *= wtheta;
-    1238             :     }
-    1239             : 
-    1240           0 :   if (scheme_==NEST)
-    1241           0 :     for (tsize m=0; m<pix.size(); ++m)
-    1242           0 :       pix[m] = ring2nest(pix[m]);
-    1243           0 :   }
-    1244             : 
-    1245           0 : template<typename I> void T_Healpix_Base<I>::swap (T_Healpix_Base &other)
-    1246             :   {
-    1247             :   std::swap(order_,other.order_);
-    1248             :   std::swap(nside_,other.nside_);
-    1249             :   std::swap(npface_,other.npface_);
-    1250             :   std::swap(ncap_,other.ncap_);
-    1251             :   std::swap(npix_,other.npix_);
-    1252             :   std::swap(fact1_,other.fact1_);
-    1253             :   std::swap(fact2_,other.fact2_);
-    1254             :   std::swap(scheme_,other.scheme_);
-    1255           0 :   }
-    1256             : 
-    1257           0 : template<typename I> double T_Healpix_Base<I>::max_pixrad() const
-    1258             :   {
-    1259             :   vec3 va,vb;
-    1260           0 :   va.set_z_phi (2./3., pi/(4*nside_));
-    1261           0 :   double t1 = 1.-1./nside_;
-    1262           0 :   t1*=t1;
-    1263           0 :   vb.set_z_phi (1-t1/3, 0);
-    1264           0 :   return v_angle(va,vb);
-    1265             :   }
-    1266             : 
-    1267           0 : template<typename I> double T_Healpix_Base<I>::max_pixrad(I ring) const
-    1268             :   {
-    1269           0 :   if (ring>=2*nside_) ring=4*nside_-ring;
-    1270           0 :   double z=ring2z(ring), z_up=(ring>1) ? ring2z(ring-1) : 1.;
-    1271             :   vec3 mypos, uppos;
-    1272           0 :   uppos.set_z_phi(z_up,0);
-    1273           0 :   if (ring<=nside_)
-    1274             :     {
-    1275           0 :     mypos.set_z_phi(z,pi/(4*ring));
-    1276           0 :     return v_angle(mypos,uppos);
-    1277             :     }
-    1278           0 :   mypos.set_z_phi(z,0);
-    1279           0 :   double vdist=v_angle(mypos,uppos);
-    1280           0 :   double hdist=sqrt(1.-z*z)*pi/(4*nside_);
-    1281           0 :   return max(hdist,vdist);
-    1282             :   }
-    1283             : 
-    1284           0 : template<typename I> void T_Healpix_Base<I>::xyf2loc (double x, double y,
-    1285             :   int face, double &z, double &phi, double &sth, bool &have_sth) const
-    1286             :   {
-    1287           0 :   have_sth = false;
-    1288           0 :   double jr = jrll[face] - x - y;
-    1289             :   double nr;
-    1290           0 :   if (jr<1)
-    1291             :     {
-    1292             :     nr = jr;
-    1293           0 :     double tmp = nr*nr/3.;
-    1294           0 :     z = 1 - tmp;
-    1295           0 :     if (z > 0.99)
-    1296             :       {
-    1297           0 :       sth = std::sqrt(tmp*(2.0-tmp));
-    1298           0 :       have_sth = true;
-    1299             :       }
-    1300             :     }
-    1301           0 :   else if (jr>3)
-    1302             :     {
-    1303           0 :     nr = 4-jr;
-    1304           0 :     double tmp = nr*nr/3.;
-    1305           0 :     z = tmp - 1;
-    1306           0 :     if (z<-0.99)
-    1307             :       {
-    1308           0 :       sth = std::sqrt(tmp*(2.-tmp));
-    1309           0 :       have_sth = true;
-    1310             :       }
-    1311             :     }
-    1312             :   else
-    1313             :     {
-    1314             :     nr = 1;
-    1315           0 :     z = (2-jr)*2./3.;
-    1316             :     }
-    1317             : 
-    1318           0 :   double tmp=jpll[face]*nr+x-y;
-    1319           0 :   if (tmp<0) tmp+=8;
-    1320           0 :   if (tmp>=8) tmp-=8;
-    1321           0 :   phi = (nr<1e-15) ? 0 : (0.5*halfpi*tmp)/nr;
-    1322           0 :   }
-    1323             : 
-    1324             : namespace {
-    1325             : 
-    1326           0 : vec3 locToVec3 (double z, double phi, double sth, bool have_sth)
-    1327             :   {
-    1328           0 :   if (have_sth)
-    1329           0 :     return vec3(sth*cos(phi),sth*sin(phi),z);
-    1330             :   else
-    1331             :     {
-    1332             :     vec3 res;
-    1333           0 :     res.set_z_phi (z, phi);
-    1334           0 :     return res;
-    1335             :     }
-    1336             :   }
-    1337             : 
-    1338             : } // unnamed namespace
-    1339             : 
-    1340           0 : template<typename I> void T_Healpix_Base<I>::boundaries(I pix, tsize step,
-    1341             :   vector<vec3> &out) const
-    1342             :   {
-    1343           0 :   out.resize(4*step);
-    1344             :   int ix, iy, face;
-    1345           0 :   pix2xyf(pix, ix, iy, face);
-    1346           0 :   double dc = 0.5 / nside_;
-    1347           0 :   double xc = (ix + 0.5)/nside_, yc = (iy + 0.5)/nside_;
-    1348           0 :   double d = 1.0/(step*nside_);
-    1349           0 :   for (tsize i=0; i<step; ++i)
-    1350             :     {
-    1351             :     double z, phi, sth;
-    1352             :     bool have_sth;
-    1353           0 :     xyf2loc(xc+dc-i*d, yc+dc, face, z, phi, sth, have_sth);
-    1354           0 :     out[i] = locToVec3(z, phi, sth, have_sth);
-    1355           0 :     xyf2loc(xc-dc, yc+dc-i*d, face, z, phi, sth, have_sth);
-    1356           0 :     out[i+step] = locToVec3(z, phi, sth, have_sth);
-    1357           0 :     xyf2loc(xc-dc+i*d, yc-dc, face, z, phi, sth, have_sth);
-    1358           0 :     out[i+2*step] = locToVec3(z, phi, sth, have_sth);
-    1359           0 :     xyf2loc(xc+dc, yc-dc+i*d, face, z, phi, sth, have_sth);
-    1360           0 :     out[i+3*step] = locToVec3(z, phi, sth, have_sth);
-    1361             :     }
-    1362           0 :   }
-    1363             : 
-    1364           0 : template<typename I> arr<int> T_Healpix_Base<I>::swap_cycles() const
-    1365             :   {
-    1366           0 :   planck_assert(order_>=0, "need hierarchical map");
-    1367           0 :   planck_assert(order_<=13, "map too large");
-    1368           0 :   arr<int> result(swap_clen[order_]);
-    1369             :   tsize ofs=0;
-    1370           0 :   for (int m=0; m<order_;++m) ofs+=swap_clen[m];
-    1371           0 :   for (tsize m=0; m<result.size();++m) result[m]=swap_cycle[m+ofs];
-    1372           0 :   return result;
-    1373             :   }
-    1374             : 
-    1375             : template class T_Healpix_Base<int>;
-    1376             : template class T_Healpix_Base<int64>;
-    1377             : } // namespace healpix
-    1378             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html deleted file mode 100644 index 7fadb1a05..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func-sort-c.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/alloc_utils.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - alloc_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIiEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIlEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_6vec3_tIdEEE5allocEm0
_ZNK7healpix13normalAlloc__IdE5allocEm0
_ZNK7healpix13normalAlloc__IiE5allocEm0
_ZNK7healpix13normalAlloc__ImE5allocEm0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html deleted file mode 100644 index 4e93cb259..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.func.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/alloc_utils.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - alloc_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIiEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_14T_Healpix_BaseIlEEE5allocEm0
_ZNK7healpix13normalAlloc__INS_6vec3_tIdEEE5allocEm0
_ZNK7healpix13normalAlloc__IdE5allocEm0
_ZNK7healpix13normalAlloc__IiE5allocEm0
_ZNK7healpix13normalAlloc__ImE5allocEm0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html deleted file mode 100644 index 6d1cc4bf4..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/alloc_utils.h.gcov.html +++ /dev/null @@ -1,154 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/alloc_utils.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - alloc_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : 
-       2             : /*
-       3             :  *  This file is part of libcxxsupport.
-       4             :  *
-       5             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       6             :  *  it under the terms of the GNU General Public License as published by
-       7             :  *  the Free Software Foundation; either version 2 of the License, or
-       8             :  *  (at your option) any later version.
-       9             :  *
-      10             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      11             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      12             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      13             :  *  GNU General Public License for more details.
-      14             :  *
-      15             :  *  You should have received a copy of the GNU General Public License
-      16             :  *  along with libcxxsupport; if not, write to the Free Software
-      17             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      18             :  */
-      19             : 
-      20             : /*
-      21             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      22             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      23             :  *  (DLR).
-      24             :  */
-      25             : 
-      26             : /*! \file alloc_utils.h
-      27             :  *  Classes providing raw memory allocation and deallocation support.
-      28             :  *
-      29             :  *  Copyright (C) 2011 Max-Planck-Society
-      30             :  *  \author Martin Reinecke
-      31             :  */
-      32             : 
-      33             : #ifndef PLANCK_ALLOC_UTILS_H
-      34             : #define PLANCK_ALLOC_UTILS_H
-      35             : 
-      36             : #include <cstdlib>
-      37             : #include "healpix_base/datatypes.h"
-      38             : 
-      39             : namespace healpix{
-      40             : template <typename T> class normalAlloc__
-      41             :   {
-      42             :   public:
-      43           0 :     T *alloc(tsize sz) const { return (sz>0) ? new T[sz] : 0; }
-      44           0 :     void dealloc (T *ptr) const { delete[] ptr; }
-      45             :   };
-      46             : 
-      47             : template <typename T, int align> class alignAlloc__
-      48             :   {
-      49             :   public:
-      50             :     T *alloc(tsize sz) const
-      51             :       {
-      52             :       using namespace std;
-      53             :       if (sz==0) return 0;
-      54             :       planck_assert((align&(align-1))==0,"alignment must be power of 2");
-      55             :       void *res;
-      56             : /* OSX up to version 10.5 does not define posix_memalign(), but fortunately
-      57             :    the normal malloc() returns 16 byte aligned storage */
-      58             : #ifdef __APPLE__
-      59             :       planck_assert(align<=16, "bad alignment requested");
-      60             :       res=malloc(sz*sizeof(T));
-      61             :       planck_assert(res!=0,"error in malloc()");
-      62             : #else
-      63             :       planck_assert(posix_memalign(&res,align,sz*sizeof(T))==0,
-      64             :         "error in posix_memalign()");
-      65             : #endif
-      66             :       return static_cast<T *>(res);
-      67             :       }
-      68             :     void dealloc(T *ptr) const
-      69             :       {
-      70             :       using namespace std;
-      71             :       free(ptr);
-      72             :       }
-      73             :   };
-      74             : 
-      75             : 
-      76             : } // namespace healpix
-      77             : 
-      78             : #endif
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html deleted file mode 100644 index 9bd6e3a5a..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/arr.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - arr.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0150.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix4arrTIdNS_13normalAlloc__IdEEEC2EmRKd0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html deleted file mode 100644 index 782efedc9..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/arr.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - arr.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0150.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix4arrTIdNS_13normalAlloc__IdEEEC2EmRKd0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html deleted file mode 100644 index b9803ade1..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/arr.h.gcov.html +++ /dev/null @@ -1,734 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/arr.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - arr.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0150.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*! \file arr.h
-      26             :  *  Various high-performance array classes used by the Planck LevelS package.
-      27             :  *
-      28             :  *  Copyright (C) 2002-2012 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #ifndef PLANCK_ARR_H
-      33             : #define PLANCK_ARR_H
-      34             : 
-      35             : #include <algorithm>
-      36             : #include <vector>
-      37             : #include <cstdlib>
-      38             : #include "healpix_base/alloc_utils.h"
-      39             : #include "healpix_base/datatypes.h"
-      40             : #include "healpix_base/math_utils.h"
-      41             : 
-      42             : namespace healpix{
-      43             : 
-      44             : /*! \defgroup arraygroup Array classes */
-      45             : /*! \{ */
-      46             : 
-      47             : /*! View of a 1D array */
-      48             : template <typename T> class arr_ref
-      49             :   {
-      50             :   protected:
-      51             :     tsize s;
-      52             :     T *d;
-      53             : 
-      54             :   public:
-      55             :     /*! Constructs an \a arr_ref of size \a s_, starting at \a d_. */
-      56           0 :     arr_ref(T *d_, tsize s_) : s(s_),d(d_) {}
-      57             : 
-      58             :     /*! Returns the current array size. */
-      59           0 :     tsize size() const { return s; }
-      60             : 
-      61             :     /*! Writes \a val into every element of the array. */
-      62             :     void fill (const T &val)
-      63           0 :       { for (tsize m=0; m<s; ++m) d[m]=val; }
-      64             : 
-      65             :     /*! Returns a reference to element \a n */
-      66           0 :     template<typename T2> T &operator[] (T2 n) {return d[n];}
-      67             :     /*! Returns a constant reference to element \a n */
-      68           0 :     template<typename T2> const T &operator[] (T2 n) const {return d[n];}
-      69             : 
-      70             :     /*! Returns a pointer to the first array element, or NULL if the array
-      71             :         is zero-sized. */
-      72             :     T *begin() { return d; }
-      73             :     /*! Returns a pointer to the one-past-last array element, or NULL if the
-      74             :         array is zero-sized. */
-      75             :     T *end() { return d+s; }
-      76             :     /*! Returns a constant pointer to the first array element, or NULL if the
-      77             :         array is zero-sized. */
-      78             :     const T *begin() const { return d; }
-      79             :     /*! Returns a constant pointer to the one-past-last array element, or NULL
-      80             :         if the array is zero-sized. */
-      81             :     const T *end() const { return d+s; }
-      82             : 
-      83             :     /*! Copies all array elements to \a ptr. */
-      84             :     template<typename T2> void copyToPtr (T *ptr) const
-      85             :       { for (tsize m=0; m<s; ++m) ptr[m]=d[m]; }
-      86             : 
-      87             :     /*! Sorts the elements in the array, in ascending order. */
-      88             :     void sort()
-      89             :       { std::sort (d,d+s); }
-      90             : 
-      91             :     /*! Sorts the elements in the array, such that \a comp(d[i],d[j])==true
-      92             :         for \a i<j. */
-      93             :     template<typename Comp> void sort(Comp comp)
-      94             :       { std::sort (d,d+s,comp); }
-      95             : 
-      96             :     /*! Helper function for linear interpolation (or extrapolation).
-      97             :         \a idx and \a val are computed such that
-      98             :         \a val=d[idx]+frac*(d[idx+1]-d[idx]). If \a val<d[0], \a frac will be
-      99             :         negative, if \a val>d[s-1], frac will be larger than 1. In all other
-     100             :         cases \a 0<=frac<=1.
-     101             : 
-     102             :         The array must be ordered in ascending order; no two values may be
-     103             :         equal. */
-     104             :     void interpol_helper (const T &val, tsize &idx, double &frac) const
-     105             :       { healpix::interpol_helper (d, d+s, val, idx, frac); }
-     106             : 
-     107             :     /*! Helper function for linear interpolation (or extrapolation).
-     108             :         \a idx and \a val are computed such that
-     109             :         \a val=d[idx]+frac*(d[idx+1]-d[idx]). If \a comp(val,d[0])==true,
-     110             :         \a frac will be negative, if \a comp(val,d[s-1])==false, frac will be
-     111             :         larger than 1. In all other cases \a 0<=frac<=1.
-     112             : 
-     113             :         The array must be ordered such that \a comp(d[i],d[j])==true
-     114             :         for \a i<j; no two values may be equal. */
-     115             :     template<typename Comp> void interpol_helper (const T &val, Comp comp,
-     116             :       tsize &idx, double &frac) const
-     117             :       { healpix::interpol_helper (d, d+s, val, comp, idx, frac); }
-     118             : 
-     119             :     /*! Returns the minimum and maximum entry in \a minv and \a maxv,
-     120             :         respectively. Throws an exception if the array is zero-sized. */
-     121             :     void minmax (T &minv, T &maxv) const
-     122             :       {
-     123             :       planck_assert(s>0,"trying to find min and max of a zero-sized array");
-     124             :       minv=maxv=d[0];
-     125             :       for (tsize m=1; m<s; ++m)
-     126             :         {
-     127             :         if (d[m]<minv) minv=d[m];
-     128             :         else if (d[m]>maxv) maxv=d[m];
-     129             :         }
-     130             :       }
-     131             : 
-     132             :     /*! Returns \a true, if \a val is found in the array, else \a false. */
-     133             :     bool contains (const T &val) const
-     134             :       {
-     135             :       for (tsize m=0; m<s; ++m)
-     136             :         if (d[m]==val) return true;
-     137             :       return false;
-     138             :       }
-     139             : 
-     140             :     /*! Returns the index of the first occurrence of \a val in the array.
-     141             :         If it is not found, an exception is thrown. */
-     142             :     tsize find (const T &val) const
-     143             :       {
-     144             :       for (tsize m=0; m<s; ++m)
-     145             :         if (d[m]==val) return m;
-     146             :       planck_fail ("entry not found in array");
-     147             :       }
-     148             : 
-     149             :     /*! Returns \a true if the array has the same size as \a other and all
-     150             :         elements of both arrays are equal, else \a false. */
-     151             :     bool contentsEqual(const arr_ref &other) const
-     152             :       {
-     153             :       if (s!=other.s) return false;
-     154             :       for (tsize i=0; i<s; ++i)
-     155             :         if (d[i]!=other.d[i]) return false;
-     156             :       return true;
-     157             :       }
-     158             :   };
-     159             : 
-     160             : /*! An array whose size is known at compile time. Very useful for storing
-     161             :     small arrays on the stack, without need for \a new and \a delete(). */
-     162             : template <typename T, tsize sz> class fix_arr
-     163             :   {
-     164             :   private:
-     165             :     T d[sz];
-     166             : 
-     167             :   public:
-     168             :     /*! Returns the size of the array. */
-     169             :     tsize size() const { return sz; }
-     170             : 
-     171             :     /*! Returns a reference to element \a n */
-     172             :     template<typename T2> T &operator[] (T2 n) {return d[n];}
-     173             :     /*! Returns a constant reference to element \a n */
-     174             :     template<typename T2> const T &operator[] (T2 n) const {return d[n];}
-     175             :   };
-     176             : 
-     177             : 
-     178             : /*! One-dimensional array type, with selectable storage management. */
-     179             : template <typename T, typename storageManager> class arrT: public arr_ref<T>
-     180             :   {
-     181             :   private:
-     182             :     storageManager stm;
-     183             :     bool own;
-     184             : 
-     185             :     void reset()
-     186             :       { this->d=0; this->s=0; own=true; }
-     187             : 
-     188             :   public:
-     189             :     /*! Creates a zero-sized array. */
-     190             :     arrT() : arr_ref<T>(0,0), own(true) {}
-     191             :     /*! Creates an array with \a sz entries. */
-     192           0 :     arrT(tsize sz) : arr_ref<T>(stm.alloc(sz),sz), own(true) {}
-     193             :     /*! Creates an array with \a sz entries, and initializes them with
-     194             :         \a inival. */
-     195           0 :     arrT(tsize sz, const T &inival) : arr_ref<T>(stm.alloc(sz),sz), own(true)
-     196           0 :       { this->fill(inival); }
-     197             :     /*! Creates an array with \a sz entries, which uses the memory pointed
-     198             :         to by \a ptr.
-     199             :         \note \a ptr will <i>not</i> be deallocated by the destructor.
-     200             :         \warning Only use this if you REALLY know what you are doing.
-     201             :         In particular, this is only safely usable if
-     202             :           <ul>
-     203             :           <li>\a T is a POD type</li>
-     204             :           <li>\a ptr survives during the lifetime of the array object</li>
-     205             :           <li>\a ptr is not subject to garbage collection</li>
-     206             :           </ul>
-     207             :         Other restrictions may apply. You have been warned. */
-     208             :     arrT (T *ptr, tsize sz): arr_ref<T>(ptr,sz), own(false) {}
-     209             :     /*! Creates an array which is a copy of \a orig. The data in \a orig
-     210             :         is duplicated. */
-     211             :     arrT (const arrT &orig): arr_ref<T>(stm.alloc(orig.s),orig.s), own(true)
-     212             :       { for (tsize m=0; m<this->s; ++m) this->d[m] = orig.d[m]; }
-     213             :     /*! Frees the memory allocated by the object. */
-     214           0 :     ~arrT() { if (own) stm.dealloc(this->d); }
-     215             : 
-     216             :     /*! Allocates space for \a sz elements. The content of the array is
-     217             :         undefined on exit. \a sz can be 0. If \a sz is the
-     218             :         same as the current size, no reallocation is performed. */
-     219             :     void alloc (tsize sz)
-     220             :       {
-     221             :       if (sz==this->s) return;
-     222             :       if (own) stm.dealloc(this->d);
-     223             :       this->s = sz;
-     224             :       this->d = stm.alloc(sz);
-     225             :       own = true;
-     226             :       }
-     227             :     /*! Allocates space for \a sz elements. If \a sz is the
-     228             :         same as the current size, no reallocation is performed.
-     229             :         All elements are set to \a inival. */
-     230             :     void allocAndFill (tsize sz, const T &inival)
-     231             :       { alloc(sz); this->fill(inival); }
-     232             :     /*! Deallocates the memory held by the array, and sets the array size
-     233             :         to 0. */
-     234             :     void dealloc() {if (own) stm.dealloc(this->d); reset();}
-     235             :     /*! Resizes the array to hold \a sz elements. The existing content of the
-     236             :         array is copied over to the new array to the extent possible.
-     237             :         \a sz can be 0. If \a sz is the same as the current size, no
-     238             :         reallocation is performed. */
-     239             :     void resize (tsize sz)
-     240             :       {
-     241             :       using namespace std;
-     242             :       if (sz==this->s) return;
-     243             :       T *tmp = stm.alloc(sz);
-     244             :       for (tsize m=0; m<min(sz,this->s); ++m)
-     245             :         tmp[m]=this->d[m];
-     246             :       if (own) stm.dealloc(this->d);
-     247             :       this->s = sz;
-     248             :       this->d = tmp;
-     249             :       own = true;
-     250             :       }
-     251             : 
-     252             :     /*! Changes the array to be a copy of \a orig. */
-     253             :     arrT &operator= (const arrT &orig)
-     254             :       {
-     255             :       if (this==&orig) return *this;
-     256             :       alloc (orig.s);
-     257             :       for (tsize m=0; m<this->s; ++m) this->d[m] = orig.d[m];
-     258             :       return *this;
-     259             :       }
-     260             : 
-     261             :     /*! Changes the array to be a copy of the std::vector \a orig. */
-     262             :     template<typename T2> void copyFrom (const std::vector<T2> &orig)
-     263             :       {
-     264             :       alloc (orig.size());
-     265             :       for (tsize m=0; m<this->s; ++m) this->d[m] = orig[m];
-     266             :       }
-     267             :     /*! Changes the std::vector \a vec to be a copy of the object. */
-     268             :     template<typename T2> void copyTo (std::vector<T2> &vec) const
-     269             :       {
-     270             :       vec.clear(); vec.reserve(this->s);
-     271             :       for (tsize m=0; m<this->s; ++m) vec.push_back(this->d[m]);
-     272             :       }
-     273             : 
-     274             :     /*! Reserves space for \a sz elements, then copies \a sz elements
-     275             :         from \a ptr into the array. */
-     276             :     template<typename T2> void copyFromPtr (const T2 *ptr, tsize sz)
-     277             :       {
-     278             :       alloc(sz);
-     279             :       for (tsize m=0; m<this->s; ++m) this->d[m]=ptr[m];
-     280             :       }
-     281             : 
-     282             :     /*! Assigns the contents and size of \a other to the array.
-     283             :         \note On exit, \a other is zero-sized! */
-     284             :     void transfer (arrT &other)
-     285             :       {
-     286             :       if (own) stm.dealloc(this->d);
-     287             :       this->d=other.d;
-     288             :       this->s=other.s;
-     289             :       own=other.own;
-     290             :       other.reset();
-     291             :       }
-     292             :     /*! Swaps contents and size with \a other. */
-     293             :     void swap (arrT &other)
-     294             :       {
-     295             :       std::swap(this->d,other.d);
-     296             :       std::swap(this->s,other.s);
-     297             :       std::swap(own,other.own);
-     298             :       }
-     299             :   };
-     300             : 
-     301             : /*! One-dimensional array type. */
-     302             : template <typename T>
-     303           0 :   class arr: public arrT<T,normalAlloc__<T> >
-     304             :   {
-     305             :   public:
-     306             :     /*! Creates a zero-sized array. */
-     307             :     arr() : arrT<T,normalAlloc__<T> >() {}
-     308             :     /*! Creates an array with \a sz entries. */
-     309             :     arr(tsize sz) : arrT<T,normalAlloc__<T> >(sz) {}
-     310             :     /*! Creates an array with \a sz entries, and initializes them with
-     311             :         \a inival. */
-     312           0 :     arr(tsize sz, const T &inival) : arrT<T,normalAlloc__<T> >(sz,inival) {}
-     313             :     /*! Creates an array with \a sz entries, which uses the memory pointed
-     314             :         to by \a ptr.
-     315             :         \note \a ptr will <i>not</i> be deallocated by the destructor.
-     316             :         \warning Only use this if you REALLY know what you are doing.
-     317             :         In particular, this is only safely usable if
-     318             :           <ul>
-     319             :           <li>\a T is a POD type</li>
-     320             :           <li>\a ptr survives during the lifetime of the array object</li>
-     321             :           <li>\a ptr is not subject to garbage collection</li>
-     322             :           </ul>
-     323             :         Other restrictions may apply. You have been warned. */
-     324             :     arr (T *ptr, tsize sz): arrT<T,normalAlloc__<T> >(ptr,sz) {}
-     325             :     /*! Creates an array which is a copy of \a orig. The data in \a orig
-     326             :         is duplicated. */
-     327             :     arr (const arr &orig): arrT<T,normalAlloc__<T> >(orig) {}
-     328             :   };
-     329             : 
-     330             : /*! One-dimensional array type, with selectable storage alignment. */
-     331             : template <typename T, int align>
-     332             :   class arr_align: public arrT<T,alignAlloc__<T,align> >
-     333             :   {
-     334             :   public:
-     335             :     /*! Creates a zero-sized array. */
-     336             :     arr_align() : arrT<T,alignAlloc__<T,align> >() {}
-     337             :     /*! Creates an array with \a sz entries. */
-     338             :     arr_align(tsize sz) : arrT<T,alignAlloc__<T,align> >(sz) {}
-     339             :     /*! Creates an array with \a sz entries, and initializes them with
-     340             :         \a inival. */
-     341             :     arr_align(tsize sz, const T &inival)
-     342             :       : arrT<T,alignAlloc__<T,align> >(sz,inival) {}
-     343             :   };
-     344             : 
-     345             : 
-     346             : /*! Two-dimensional array type, with selectable storage management.
-     347             :     The storage ordering is the same as in C.
-     348             :     An entry is located by address arithmetic, not by double dereferencing.
-     349             :     The indices start at zero. */
-     350             : template <typename T, typename storageManager> class arr2T
-     351             :   {
-     352             :   private:
-     353             :     tsize s1, s2;
-     354             :     arrT<T, storageManager> d;
-     355             : 
-     356             :   public:
-     357             :     /*! Creates a zero-sized array. */
-     358             :     arr2T() : s1(0), s2(0) {}
-     359             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
-     360             :     arr2T(tsize sz1, tsize sz2)
-     361             :       : s1(sz1), s2(sz2), d(s1*s2) {}
-     362             :     /*! Creates an array with the dimensions  \a sz1 and \a sz2
-     363             :         and initializes them with \a inival. */
-     364             :     arr2T(tsize sz1, tsize sz2, const T &inival)
-     365             :       : s1(sz1), s2(sz2), d (s1*s2)
-     366             :       { fill(inival); }
-     367             :     /*! Creates the array as a copy of \a orig. */
-     368             :     arr2T(const arr2T &orig)
-     369             :       : s1(orig.s1), s2(orig.s2), d(orig.d) {}
-     370             :     /*! Frees the memory associated with the array. */
-     371             :     ~arr2T() {}
-     372             : 
-     373             :     /*! Returns the first array dimension. */
-     374             :     tsize size1() const { return s1; }
-     375             :     /*! Returns the second array dimension. */
-     376             :     tsize size2() const { return s2; }
-     377             :     /*! Returns the total array size, i.e. the product of both dimensions. */
-     378             :     tsize size () const { return s1*s2; }
-     379             : 
-     380             :     /*! Allocates space for an array with \a sz1*sz2 elements.
-     381             :         The content of the array is undefined on exit.
-     382             :         \a sz1 or \a sz2 can be 0. If \a sz1*sz2 is the same as the
-     383             :         currently allocated space, no reallocation is performed. */
-     384             :     void alloc (tsize sz1, tsize sz2)
-     385             :       {
-     386             :       if (sz1*sz2 != d.size())
-     387             :         d.alloc(sz1*sz2);
-     388             :       s1=sz1; s2=sz2;
-     389             :       }
-     390             :     /*! Allocates space for an array with \a sz1*sz2 elements.
-     391             :         All elements are set to \a inival.
-     392             :         \a sz1 or \a sz2 can be 0. If \a sz1*sz2 is the same as the
-     393             :         currently allocated space, no reallocation is performed. */
-     394             :     void allocAndFill (tsize sz1, tsize sz2, const T &inival)
-     395             :       { alloc(sz1,sz2); fill(inival); }
-     396             :     /*! Allocates space for an array with \a sz1*sz2 elements.
-     397             :         The content of the array is undefined on exit.
-     398             :         \a sz1 or \a sz2 can be 0. If \a sz1*sz2 is smaller than the
-     399             :         currently allocated space, no reallocation is performed. */
-     400             :     void fast_alloc (tsize sz1, tsize sz2)
-     401             :       {
-     402             :       if (sz1*sz2<=d.size())
-     403             :         { s1=sz1; s2=sz2; }
-     404             :       else
-     405             :         alloc(sz1,sz2);
-     406             :       }
-     407             :     /*! Deallocates the space and makes the array zero-sized. */
-     408             :     void dealloc () {d.dealloc(); s1=0; s2=0;}
-     409             : 
-     410             :     /*! Sets all array elements to \a val. */
-     411             :     void fill (const T &val)
-     412             :       { for (tsize m=0; m<s1*s2; ++m) d[m]=val; }
-     413             : 
-     414             :     /*! Multiplies all array elements by \a val. */
-     415             :     void scale (const T &val)
-     416             :       { for (tsize m=0; m<s1*s2; ++m) d[m]*=val; }
-     417             : 
-     418             :     /*! Changes the array to be a copy of \a orig. */
-     419             :     arr2T &operator= (const arr2T &orig)
-     420             :       {
-     421             :       if (this==&orig) return *this;
-     422             :       alloc (orig.s1, orig.s2);
-     423             :       d = orig.d;
-     424             :       return *this;
-     425             :       }
-     426             : 
-     427             :     /*! Returns a pointer to the beginning of slice \a n. */
-     428             :     template<typename T2> T *operator[] (T2 n) {return &d[n*s2];}
-     429             :     /*! Returns a constant pointer to the beginning of slice \a n. */
-     430             :     template<typename T2> const T *operator[] (T2 n) const {return &d[n*s2];}
-     431             : 
-     432             :     /*! Returns a reference to the element with the indices \a n1 and \a n2. */
-     433             :     template<typename T2, typename T3> T &operator() (T2 n1, T3 n2)
-     434             :       {return d[n1*s2 + n2];}
-     435             :     /*! Returns a constant reference to the element with the indices
-     436             :         \a n1 and \a n2. */
-     437             :     template<typename T2, typename T3> const T &operator() (T2 n1, T3 n2) const
-     438             :       {return d[n1*s2 + n2];}
-     439             : 
-     440             :     /*! Returns the minimum and maximum entry in \a minv and \a maxv,
-     441             :         respectively. Throws an exception if the array is zero-sized. */
-     442             :     void minmax (T &minv, T &maxv) const
-     443             :       {
-     444             :       planck_assert(s1*s2>0,
-     445             :         "trying to find min and max of a zero-sized array");
-     446             :       minv=maxv=d[0];
-     447             :       for (tsize m=1; m<s1*s2; ++m)
-     448             :         {
-     449             :         if (d[m]<minv) minv=d[m];
-     450             :         if (d[m]>maxv) maxv=d[m];
-     451             :         }
-     452             :       }
-     453             : 
-     454             :     /*! Swaps contents and sizes with \a other. */
-     455             :     void swap (arr2T &other)
-     456             :       {
-     457             :       d.swap(other.d);
-     458             :       std::swap(s1,other.s1);
-     459             :       std::swap(s2,other.s2);
-     460             :       }
-     461             : 
-     462             :     /*! Returns \c true if the array and \a other have the same dimensions,
-     463             :         else \c false. */
-     464             :     template<typename T2, typename T3> bool conformable
-     465             :       (const arr2T<T2,T3> &other) const
-     466             :       { return (other.size1()==s1) && (other.size2()==s2); }
-     467             :   };
-     468             : 
-     469             : /*! Two-dimensional array type. The storage ordering is the same as in C.
-     470             :     An entry is located by address arithmetic, not by double dereferencing.
-     471             :     The indices start at zero. */
-     472             : template <typename T>
-     473             :   class arr2: public arr2T<T,normalAlloc__<T> >
-     474             :   {
-     475             :   public:
-     476             :     /*! Creates a zero-sized array. */
-     477             :     arr2() : arr2T<T,normalAlloc__<T> > () {}
-     478             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
-     479             :     arr2(tsize sz1, tsize sz2) : arr2T<T,normalAlloc__<T> > (sz1,sz2) {}
-     480             :     /*! Creates an array with the dimensions  \a sz1 and \a sz2
-     481             :         and initializes them with \a inival. */
-     482             :     arr2(tsize sz1, tsize sz2, const T &inival)
-     483             :       : arr2T<T,normalAlloc__<T> > (sz1,sz2,inival) {}
-     484             :   };
-     485             : 
-     486             : /*! Two-dimensional array type, with selectable storage alignment.
-     487             :     The storage ordering is the same as in C.
-     488             :     An entry is located by address arithmetic, not by double dereferencing.
-     489             :     The indices start at zero. */
-     490             : template <typename T, int align>
-     491             :   class arr2_align: public arr2T<T,alignAlloc__<T,align> >
-     492             :   {
-     493             :   public:
-     494             :     /*! Creates a zero-sized array. */
-     495             :     arr2_align() : arr2T<T,alignAlloc__<T,align> > () {}
-     496             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
-     497             :     arr2_align(tsize sz1, tsize sz2)
-     498             :       : arr2T<T,alignAlloc__<T,align> > (sz1,sz2) {}
-     499             :     /*! Creates an array with the dimensions  \a sz1 and \a sz2
-     500             :         and initializes them with \a inival. */
-     501             :     arr2_align(tsize sz1, tsize sz2, const T &inival)
-     502             :       : arr2T<T,alignAlloc__<T,align> > (sz1,sz2,inival) {}
-     503             :   };
-     504             : 
-     505             : /*! Two-dimensional array type. An entry is located by double dereferencing,
-     506             :     i.e. via an array of pointers. The indices start at zero. */
-     507             : template <typename T> class arr2b
-     508             :   {
-     509             :   private:
-     510             :     tsize s1, s2;
-     511             :     arr<T> d;
-     512             :     arr<T *> d1;
-     513             : 
-     514             :     void fill_d1()
-     515             :       { for (tsize m=0; m<s1; ++m) d1[m] = &d[m*s2]; }
-     516             : 
-     517             :   public:
-     518             :     /*! Creates a zero-sized array. */
-     519             :     arr2b() : s1(0), s2(0), d(0), d1(0) {}
-     520             :     /*! Creates an array with the dimensions \a sz1 and \a sz2. */
-     521             :     arr2b(tsize sz1, tsize sz2)
-     522             :       : s1(sz1), s2(sz2), d(s1*s2), d1(s1)
-     523             :       { fill_d1(); }
-     524             :     /*! Creates the array as a copy of \a orig. */
-     525             :     arr2b(const arr2b &orig)
-     526             :       : s1(orig.s1), s2(orig.s2), d(orig.d), d1(s1)
-     527             :       { fill_d1(); }
-     528             :     /*! Frees the memory associated with the array. */
-     529             :     ~arr2b() {}
-     530             : 
-     531             :     /*! Returns the first array dimension. */
-     532             :     tsize size1() const { return s1; }
-     533             :     /*! Returns the second array dimension. */
-     534             :     tsize size2() const { return s2; }
-     535             :     /*! Returns the total array size, i.e. the product of both dimensions. */
-     536             :     tsize size () const { return s1*s2; }
-     537             : 
-     538             :     /*! Allocates space for an array with \a sz1*sz2 elements.
-     539             :         The content of the array is undefined on exit. */
-     540             :     void alloc (tsize sz1, tsize sz2)
-     541             :       {
-     542             :       if ((s1==sz1) && (s2==sz2)) return;
-     543             :       s1=sz1; s2=sz2;
-     544             :       d.alloc(s1*s2);
-     545             :       d1.alloc(s1);
-     546             :       fill_d1();
-     547             :       }
-     548             :     /*! Deallocates the space and makes the array zero-sized. */
-     549             :     void dealloc () {d.dealloc(); d1.dealloc(); s1=0; s2=0;}
-     550             : 
-     551             :     /*! Sets all array elements to \a val. */
-     552             :     void fill (const T &val)
-     553             :       { d.fill(val); }
-     554             : 
-     555             :     /*! Changes the array to be a copy of \a orig. */
-     556             :     arr2b &operator= (const arr2b &orig)
-     557             :       {
-     558             :       if (this==&orig) return *this;
-     559             :       alloc (orig.s1, orig.s2);
-     560             :       for (tsize m=0; m<s1*s2; ++m) d[m] = orig.d[m];
-     561             :       return *this;
-     562             :       }
-     563             : 
-     564             :     /*! Returns a pointer to the beginning of slice \a n. */
-     565             :     template<typename T2> T *operator[] (T2 n) {return d1[n];}
-     566             :     /*! Returns a constant pointer to the beginning of slice \a n. */
-     567             :     template<typename T2> const T *operator[] (T2 n) const {return d1[n];}
-     568             : 
-     569             :     /*! Returns a pointer to the beginning of the pointer array. */
-     570             :     T **p0() {return &d1[0];}
-     571             :   };
-     572             : 
-     573             : 
-     574             : /*! Three-dimensional array type. The storage ordering is the same as in C.
-     575             :     An entry is located by address arithmetic, not by multiple dereferencing.
-     576             :     The indices start at zero. */
-     577             : template <typename T> class arr3
-     578             :   {
-     579             :   private:
-     580             :     tsize s1, s2, s3, s2s3;
-     581             :     arr<T> d;
-     582             : 
-     583             :   public:
-     584             :     /*! Creates a zero-sized array. */
-     585             :     arr3() : s1(0), s2(0), s3(0), s2s3(0), d(0) {}
-     586             :     /*! Creates an array with the dimensions \a sz1, \a sz2 and \a sz3. */
-     587           0 :     arr3(tsize sz1, tsize sz2, tsize sz3)
-     588           0 :       : s1(sz1), s2(sz2), s3(sz3), s2s3(s2*s3), d(s1*s2*s3) {}
-     589             :     /*! Creates the array as a copy of \a orig. */
-     590             :     arr3(const arr3 &orig)
-     591             :       : s1(orig.s1), s2(orig.s2), s3(orig.s3), s2s3(orig.s2s3), d(orig.d) {}
-     592             :     /*! Frees the memory associated with the array. */
-     593           0 :     ~arr3() {}
-     594             : 
-     595             :     /*! Returns the first array dimension. */
-     596             :     tsize size1() const { return s1; }
-     597             :     /*! Returns the second array dimension. */
-     598             :     tsize size2() const { return s2; }
-     599             :     /*! Returns the third array dimension. */
-     600             :     tsize size3() const { return s3; }
-     601             :     /*! Returns the total array size, i.e. the product of all dimensions. */
-     602             :     tsize size () const { return s1*s2*s3; }
-     603             : 
-     604             :     /*! Allocates space for an array with \a sz1*sz2*sz3 elements.
-     605             :         The content of the array is undefined on exit. */
-     606             :     void alloc (tsize sz1, tsize sz2, tsize sz3)
-     607             :       {
-     608             :       d.alloc(sz1*sz2*sz3);
-     609             :       s1=sz1; s2=sz2; s3=sz3; s2s3=s2*s3;
-     610             :       }
-     611             :     /*! Deallocates the space and makes the array zero-sized. */
-     612             :     void dealloc () {d.dealloc(); s1=0; s2=0; s3=0; s2s3=0;}
-     613             : 
-     614             :     /*! Sets all array elements to \a val. */
-     615             :     void fill (const T &val)
-     616             :       { d.fill(val); }
-     617             : 
-     618             :     /*! Changes the array to be a copy of \a orig. */
-     619             :     arr3 &operator= (const arr3 &orig)
-     620             :       {
-     621             :       if (this==&orig) return *this;
-     622             :       alloc (orig.s1, orig.s2, orig.s3);
-     623             :       d = orig.d;
-     624             :       return *this;
-     625             :       }
-     626             : 
-     627             :     /*! Returns a reference to the element with the indices
-     628             :         \a n1, \a n2 and \a n3. */
-     629             :     template<typename T2, typename T3, typename T4> T &operator()
-     630             :       (T2 n1, T3 n2, T4 n3)
-     631           0 :       {return d[n1*s2s3 + n2*s3 + n3];}
-     632             :     /*! Returns a constant reference to the element with the indices
-     633             :         \a n1, \a n2 and \a n3. */
-     634             :     template<typename T2, typename T3, typename T4> const T &operator()
-     635             :       (T2 n1, T3 n2, T4 n3) const
-     636             :       {return d[n1*s2s3 + n2*s3 + n3];}
-     637             : 
-     638             :     /*! Swaps contents and sizes with \a other. */
-     639             :     void swap (arr3 &other)
-     640             :       {
-     641             :       d.swap(other.d);
-     642             :       std::swap(s1,other.s1);
-     643             :       std::swap(s2,other.s2);
-     644             :       std::swap(s3,other.s3);
-     645             :       std::swap(s2s3,other.s2s3);
-     646             :       }
-     647             : 
-     648             :     /*! Returns \c true if the array and \a other have the same dimensions,
-     649             :         else \c false. */
-     650             :     template<typename T2> bool conformable (const arr3<T2> &other) const
-     651             :       { return (other.size1()==s1)&&(other.size2()==s2)&&(other.size3()==s3); }
-     652             :   };
-     653             : 
-     654             : /*! \} */
-     655             : 
-     656             : } // namespace healpix
-     657             : #endif
-     658             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html deleted file mode 100644 index 3feba0c8f..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/error_handling.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - error_handling.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix11PlanckError4whatEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html deleted file mode 100644 index 256c36ce3..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/error_handling.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - error_handling.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7healpix11PlanckError4whatEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html deleted file mode 100644 index 5a90a3d3f..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/error_handling.h.gcov.html +++ /dev/null @@ -1,180 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/error_handling.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - error_handling.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:020.0 %
Date:2024-04-08 14:58:22Functions:010.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : 
-       2             : /*
-       3             :  *  This file is part of libcxxsupport.
-       4             :  *
-       5             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       6             :  *  it under the terms of the GNU General Public License as published by
-       7             :  *  the Free Software Foundation; either version 2 of the License, or
-       8             :  *  (at your option) any later version.
-       9             :  *
-      10             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      11             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      12             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      13             :  *  GNU General Public License for more details.
-      14             :  *
-      15             :  *  You should have received a copy of the GNU General Public License
-      16             :  *  along with libcxxsupport; if not, write to the Free Software
-      17             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      18             :  */
-      19             : 
-      20             : /*
-      21             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      22             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      23             :  *  (DLR).
-      24             :  */
-      25             : 
-      26             : /*! \file error_handling.h
-      27             :  *  Utilities for error reporting
-      28             :  *
-      29             :  *  Copyright (C) 2003-2011 Max-Planck-Society
-      30             :  *  Authors: Reinhard Hell, Martin Reinecke
-      31             :  */
-      32             : 
-      33             : #ifndef PLANCK_ERROR_HANDLING_H
-      34             : #define PLANCK_ERROR_HANDLING_H
-      35             : 
-      36             : #include <string>
-      37             : #include <iostream>
-      38             : 
-      39             : namespace healpix{
-      40             : #if defined (__GNUC__)
-      41             : #define PLANCK_FUNC_NAME__ __PRETTY_FUNCTION__
-      42             : #else
-      43             : #define PLANCK_FUNC_NAME__ 0
-      44             : #endif
-      45             : 
-      46             : void planck_failure__(const char *file, int line, const char *func,
-      47             :   const std::string &msg);
-      48             : void planck_failure__(const char *file, int line, const char *func,
-      49             :   const char *msg);
-      50             : void killjob__();
-      51             : 
-      52             : class PlanckError
-      53             :   {
-      54             :   private:
-      55             :     std::string msg;
-      56             : 
-      57             :   public:
-      58             :     explicit PlanckError(const std::string &message);
-      59             :     explicit PlanckError(const char *message);
-      60             : 
-      61           0 :     virtual const char* what() const
-      62           0 :       { return msg.c_str(); }
-      63             : 
-      64             :     virtual ~PlanckError();
-      65             :   };
-      66             : 
-      67             : /*! \defgroup errorgroup Error handling */
-      68             : /*! \{ */
-      69             : 
-      70             : /*! Writes diagnostic output and exits with an error status. */
-      71             : #define planck_fail(msg) \
-      72             : do { planck_failure__(__FILE__,__LINE__,PLANCK_FUNC_NAME__,msg); \
-      73             : throw PlanckError(msg); } while(0)
-      74             : 
-      75             : /*! Throws a PlanckError without diagnostic message. */
-      76             : #define planck_fail_quietly(msg) \
-      77             : do { throw PlanckError(msg); } while(0)
-      78             : 
-      79             : /*! Writes diagnostic output and exits with an error status if \a testval
-      80             :     is \a false. */
-      81             : #define planck_assert(testval,msg) \
-      82             : do { if (testval); else planck_fail(msg); } while(0)
-      83             : 
-      84             : /*! Macro for improving error diagnostics. Should be placed immediately
-      85             :     after the opening brace of \c main(). Must be used in conjunction with
-      86             :     \c PLANCK_DIAGNOSIS_END. */
-      87             : #define PLANCK_DIAGNOSIS_BEGIN try {
-      88             : /*! Macro for improving error diagnostics. Should be placed immediately
-      89             :     before the closing brace of \c main(). Must be used in conjunction with
-      90             :     \c PLANCK_DIAGNOSIS_BEGIN. */
-      91             : #define PLANCK_DIAGNOSIS_END \
-      92             : } \
-      93             : catch (PlanckError &) \
-      94             :   { killjob__(); /* no need for further diagnostics; they were shown already */ } \
-      95             : catch (std::exception &e) \
-      96             :   { std::cerr << "std::exception: " << e.what() << std::endl; killjob__(); } \
-      97             : catch (...) \
-      98             :   { std::cerr << "Unknown exception" << std::endl; killjob__(); }
-      99             : 
-     100             : /*! \} */
-     101             : 
-     102             : } // namespace healpix
-     103             : #endif
-     104             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html deleted file mode 100644 index 19feeba32..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/geom_utils.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - geom_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12cosdist_zphiEdddd0
_ZN7healpix7v_angleERKNS_6vec3_tIdEES3_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html deleted file mode 100644 index be6031adf..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/geom_utils.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - geom_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix12cosdist_zphiEdddd0
_ZN7healpix7v_angleERKNS_6vec3_tIdEES3_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html deleted file mode 100644 index 42f3ff33f..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/geom_utils.h.gcov.html +++ /dev/null @@ -1,161 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/geom_utils.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - geom_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*! \file geom_utils.h
-      26             :  *  Geometric utility functions.
-      27             :  *
-      28             :  *  Copyright (C) 2003-2011 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  *  \author Reinhard Hell
-      31             :  */
-      32             : 
-      33             : #ifndef PLANCK_GEOM_UTILS_H
-      34             : #define PLANCK_GEOM_UTILS_H
-      35             : 
-      36             : #include "healpix_base/math_utils.h"
-      37             : #include "healpix_base/vec3.h"
-      38             : 
-      39             : namespace healpix{
-      40             : 
-      41             : template<typename T> class arr;
-      42             : 
-      43             : /*! Returns the orientation when looking from point \a loc on the unit
-      44             :     sphere in the direction \a dir. \a loc must be normalized. The result
-      45             :     ranges from -pi to pi, is 0 for North and pi/2 for West, i.e. the angle
-      46             :     is given in mathematically positive sense.
-      47             : 
-      48             :     If \a loc is the North or South pole, the returned angle is
-      49             :     \a atan2(dir.y,dir.x). */
-      50             : inline double orientation (const vec3 &loc, const vec3 &dir)
-      51             :   {
-      52             : // FIXME: here is still optimization potential
-      53             :   if (loc.x==0 && loc.y==0)
-      54             :     return (loc.z>0) ? safe_atan2(dir.y,-dir.x) : safe_atan2(dir.y,dir.x);
-      55             :   vec3 east (-loc.y, loc.x, 0);
-      56             :   vec3 north = crossprod(loc,east);
-      57             :   return safe_atan2(-dotprod(dir,east),dotprod(dir,north));
-      58             :   }
-      59             : 
-      60             : /*! Returns the angle between \a v1 and \a v2 in radians. */
-      61           0 : inline double v_angle (const vec3 &v1, const vec3 &v2)
-      62             :   {
-      63             :   using namespace std;
-      64           0 :   return atan2 (crossprod(v1,v2).Length(), dotprod(v1,v2));
-      65             :   }
-      66             : 
-      67             : /*! Returns the cosine of the angle between the two points on the sphere defined
-      68             :     by (\a z1, \a phi1) and (\a z2, \a phi2), respectively. \a z is the cosine
-      69             :     of the colatitude, and \a phi is the longitude. */
-      70           0 : inline double cosdist_zphi (double z1, double phi1, double z2, double phi2)
-      71             :   {
-      72             :   using namespace std;
-      73           0 :   return z1*z2+cos(phi1-phi2)*sqrt((1.-z1*z1)*(1.-z2*z2));
-      74             :   }
-      75             : 
-      76             : /*! Finds the smallest enclosing cone for a point set on the sphere according to
-      77             :     Barequet & Elber: Information Processing Letters 93(2005), p.83.
-      78             :     All points are expected to be passed as unit vectors.
-      79             :     The enclosing cone must have an opening angle <pi/2. */
-      80             : void find_enclosing_circle (const arr<vec3> &point, vec3 &center,
-      81             :   double &cosrad);
-      82             : 
-      83             : } // namespace healpix
-      84             : #endif
-      85             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html deleted file mode 100644 index c2ac9dce4..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func-sort-c.html +++ /dev/null @@ -1,208 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/healpix_base.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - healpix_base.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:165032.0 %
Date:2024-04-08 14:58:22Functions:3348.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZN7healpix14T_Healpix_BaseIlEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2ElNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZNK7healpix14T_Healpix_BaseIiE10query_discERKNS_8pointingEdRSt6vectorIiSaIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIiSaIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIiE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIiE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIiE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIiE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIiE7pix2angEi0
_ZNK7healpix14T_Healpix_BaseIiE7pix2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIiE8pix2zphiEiRdS2_0
_ZNK7healpix14T_Healpix_BaseIiE8zphi2pixEdd0
_ZNK7healpix14T_Healpix_BaseIlE10query_discERKNS_8pointingEdRSt6vectorIlSaIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIlSaIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIlE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIlE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIlE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIlE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIlE7pix2angEl0
_ZNK7healpix14T_Healpix_BaseIlE7pix2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE7vec2pixERKNS_6vec3_tIdEE0
_ZNK7healpix14T_Healpix_BaseIlE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIlE8pix2zphiElRdS2_0
_ZNK7healpix14T_Healpix_BaseIlE8zphi2pixEdd0
_ZNK7healpix14T_Healpix_BaseIlE7pix2vecEl421
_ZNK7healpix14T_Healpix_BaseIiE7vec2pixERKNS_6vec3_tIdEE24585
_ZNK7healpix14T_Healpix_BaseIiE7pix2vecEi135172
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html deleted file mode 100644 index b4d88f50c..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.func.html +++ /dev/null @@ -1,208 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/healpix_base.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - healpix_base.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:165032.0 %
Date:2024-04-08 14:58:22Functions:3348.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIiEC2EiNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZN7healpix14T_Healpix_BaseIlEC2EiNS_23Healpix_Ordering_SchemeE0
_ZN7healpix14T_Healpix_BaseIlEC2ElNS_23Healpix_Ordering_SchemeENS_11nside_dummyE0
_ZNK7healpix14T_Healpix_BaseIiE10query_discERKNS_8pointingEdRSt6vectorIiSaIiEE0
_ZNK7healpix14T_Healpix_BaseIiE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIiE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIiSaIiEEi0
_ZNK7healpix14T_Healpix_BaseIiE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIiE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIiE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIiE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIiE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIiE7pix2angEi0
_ZNK7healpix14T_Healpix_BaseIiE7pix2vecEi135172
_ZNK7healpix14T_Healpix_BaseIiE7pix2xyfEiRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIiE7vec2pixERKNS_6vec3_tIdEE24585
_ZNK7healpix14T_Healpix_BaseIiE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIiE8pix2zphiEiRdS2_0
_ZNK7healpix14T_Healpix_BaseIiE8zphi2pixEdd0
_ZNK7healpix14T_Healpix_BaseIlE10query_discERKNS_8pointingEdRSt6vectorIlSaIlEE0
_ZNK7healpix14T_Healpix_BaseIlE11conformableERKS1_0
_ZNK7healpix14T_Healpix_BaseIlE20query_disc_inclusiveERKNS_8pointingEdRSt6vectorIlSaIlEEi0
_ZNK7healpix14T_Healpix_BaseIlE4NpixEv0
_ZNK7healpix14T_Healpix_BaseIlE5NsideEv0
_ZNK7healpix14T_Healpix_BaseIlE5OrderEv0
_ZNK7healpix14T_Healpix_BaseIlE6SchemeEv0
_ZNK7healpix14T_Healpix_BaseIlE7ang2pixERKNS_8pointingE0
_ZNK7healpix14T_Healpix_BaseIlE7pix2angEl0
_ZNK7healpix14T_Healpix_BaseIlE7pix2vecEl421
_ZNK7healpix14T_Healpix_BaseIlE7pix2xyfElRiS2_S2_0
_ZNK7healpix14T_Healpix_BaseIlE7vec2pixERKNS_6vec3_tIdEE0
_ZNK7healpix14T_Healpix_BaseIlE7xyf2pixEiii0
_ZNK7healpix14T_Healpix_BaseIlE8pix2zphiElRdS2_0
_ZNK7healpix14T_Healpix_BaseIlE8zphi2pixEdd0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html deleted file mode 100644 index c89cc2a4d..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/healpix_base.h.gcov.html +++ /dev/null @@ -1,457 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/healpix_base.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - healpix_base.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:165032.0 %
Date:2024-04-08 14:58:22Functions:3348.8 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of Healpix_cxx.
-       3             :  *
-       4             :  *  Healpix_cxx is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  Healpix_cxx is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with Healpix_cxx; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  *
-      18             :  *  For more information about HEALPix, see http://healpix.sourceforge.net
-      19             :  */
-      20             : 
-      21             : /*
-      22             :  *  Healpix_cxx is being developed at the Max-Planck-Institut fuer Astrophysik
-      23             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      24             :  *  (DLR).
-      25             :  */
-      26             : 
-      27             : /*! \file healpix_base.h
-      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #ifndef HEALPIX_BASE_H
-      33             : #define HEALPIX_BASE_H
-      34             : 
-      35             : #include <vector>
-      36             : #include "healpix_base/healpix_tables.h"
-      37             : #include "healpix_base/pointing.h"
-      38             : #include "healpix_base/arr.h"
-      39             : #include "healpix_base/rangeset.h"
-      40             : 
-      41             : namespace healpix{
-      42             : 
-      43             : /*! Functionality related to the HEALPix pixelisation. */
-      44             : template<typename I> class T_Healpix_Base: public Healpix_Tables
-      45             :   {
-      46             :   protected:
-      47             :     /*! The order of the map; -1 for nonhierarchical map. */
-      48             :     int order_;
-      49             :     /*! The N_side parameter of the map; 0 if not allocated. */
-      50             :     I nside_;
-      51             :     I npface_, ncap_, npix_;
-      52             :     double fact1_, fact2_;
-      53             :     /*! The map's ordering scheme. */
-      54             :     Healpix_Ordering_Scheme scheme_;
-      55             : 
-      56             :     /*! Returns the number of the next ring to the north of \a z=cos(theta).
-      57             :         It may return 0; in this case \a z lies north of all rings. */
-      58             :     inline I ring_above (double z) const;
-      59             :     void in_ring (I iz, double phi0, double dphi, rangeset<I> &pixset) const;
-      60             : 
-      61             :     template<typename I2> void query_multidisc (const arr<vec3> &norm,
-      62             :       const arr<double> &rad, int fact, rangeset<I2> &pixset) const;
-      63             : 
-      64             :     void query_multidisc_general (const arr<vec3> &norm, const arr<double> &rad,
-      65             :       bool inclusive, const std::vector<int> &cmds, rangeset<I> &pixset) const;
-      66             : 
-      67             :     void query_strip_internal (double theta1, double theta2, bool inclusive,
-      68             :       rangeset<I> &pixset) const;
-      69             : 
-      70             :     inline I spread_bits (int v) const;
-      71             :     inline int compress_bits (I v) const;
-      72             : 
-      73             :     I xyf2nest(int ix, int iy, int face_num) const;
-      74             :     void nest2xyf(I pix, int &ix, int &iy, int &face_num) const;
-      75             :     I xyf2ring(int ix, int iy, int face_num) const;
-      76             :     void ring2xyf(I pix, int &ix, int &iy, int &face_num) const;
-      77             : 
-      78             :     I loc2pix (double z, double phi, double sth, bool have_sth) const;
-      79             :     void pix2loc (I pix, double &z, double &phi, double &sth, bool &have_sth)
-      80             :       const;
-      81             : 
-      82             :     void xyf2loc(double x, double y, int face, double &z, double &ph,
-      83             :       double &sth, bool &have_sth) const;
-      84             : 
-      85             :     I nest_peano_helper (I pix, int dir) const;
-      86             : 
-      87             :     typedef I (T_Healpix_Base::*swapfunc)(I pix) const;
-      88             : 
-      89             :   public:
-      90             :     static const int order_max;
-      91             : 
-      92             :     /*! Calculates the map order from its \a N_side parameter.
-      93             :         Returns -1 if \a nside is not a power of 2.
-      94             :         \param nside the \a N_side parameter */
-      95             :     static int nside2order (I nside);
-      96             :     /*! Calculates the \a N_side parameter from the number of pixels.
-      97             :         \param npix the number of pixels */
-      98             :     static I npix2nside (I npix);
-      99             :     /*! Constructs an unallocated object. */
-     100             :     T_Healpix_Base ();
-     101             :     /*! Constructs an object with a given \a order and the ordering
-     102             :         scheme \a scheme. */
-     103          10 :     T_Healpix_Base (int order, Healpix_Ordering_Scheme scheme)
-     104          10 :       { Set (order, scheme); }
-     105             :     /*! Constructs an object with a given \a nside and the ordering
-     106             :         scheme \a scheme. The \a nside_dummy parameter must be set to
-     107             :         SET_NSIDE. */
-     108           0 :     T_Healpix_Base (I nside, Healpix_Ordering_Scheme scheme, const nside_dummy)
-     109           0 :       { SetNside (nside, scheme); }
-     110             : 
-     111             :     /*! Adjusts the object to \a order and \a scheme. */
-     112             :     void Set (int order, Healpix_Ordering_Scheme scheme);
-     113             :     /*! Adjusts the object to \a nside and \a scheme. */
-     114             :     void SetNside (I nside, Healpix_Ordering_Scheme scheme);
-     115             : 
-     116             :     /*! Returns the z-coordinate of the ring \a ring. This also works
-     117             :         for the (not really existing) rings 0 and 4*nside. */
-     118             :     double ring2z (I ring) const;
-     119             :     /*! Returns the number of the ring in which \a pix lies. */
-     120             :     I pix2ring (I pix) const;
-     121             : 
-     122           0 :     I xyf2pix(int ix, int iy, int face_num) const
-     123             :       {
-     124           0 :       return (scheme_==RING) ?
-     125           0 :         xyf2ring(ix,iy,face_num) : xyf2nest(ix,iy,face_num);
-     126             :       }
-     127           0 :     void pix2xyf(I pix, int &ix, int &iy, int &face_num) const
-     128             :       {
-     129           0 :       (scheme_==RING) ?
-     130           0 :         ring2xyf(pix,ix,iy,face_num) : nest2xyf(pix,ix,iy,face_num);
-     131           0 :       }
-     132             : 
-     133             :     /*! Translates a pixel number from NEST to RING. */
-     134             :     I nest2ring (I pix) const;
-     135             :     /*! Translates a pixel number from RING to NEST. */
-     136             :     I ring2nest (I pix) const;
-     137             :     /*! Translates a pixel number from NEST to its Peano index. */
-     138             :     I nest2peano (I pix) const;
-     139             :     /*! Translates a pixel number from its Peano index to NEST. */
-     140             :     I peano2nest (I pix) const;
-     141             : 
-     142             :     /*! Returns the number of the pixel which contains the angular coordinates
-     143             :         (\a z:=cos(theta), \a phi).
-     144             :         \note This method is inaccurate near the poles at high resolutions. */
-     145           0 :     I zphi2pix (double z, double phi) const
-     146           0 :       { return loc2pix(z,phi,0.,false); }
-     147             : 
-     148             :     /*! Returns the number of the pixel which contains the angular coordinates
-     149             :         \a ang. */
-     150           0 :     I ang2pix (const pointing &ang) const
-     151             :       {
-     152             :       const double pi_=3.141592653589793238462643383279502884197;
-     153           0 :       planck_assert((ang.theta>=0)&&(ang.theta<=pi_),"invalid theta value");
-     154           0 :       return ((ang.theta<0.01) || (ang.theta > 3.14159-0.01)) ?
-     155           0 :         loc2pix(cos(ang.theta),ang.phi,sin(ang.theta),true) :
-     156           0 :         loc2pix(cos(ang.theta),ang.phi,0.,false);
-     157             :       }
-     158             :     /*! Returns the number of the pixel which contains the vector \a vec
-     159             :         (\a vec is normalized if necessary). */
-     160       24585 :     I vec2pix (const vec3 &vec) const
-     161             :       {
-     162       24585 :       double xl = 1./vec.Length();
-     163             :       double phi = safe_atan2(vec.y,vec.x);
-     164       24585 :       double nz = vec.z*xl;
-     165       24585 :       if (std::abs(nz)>0.99)
-     166         241 :         return loc2pix (nz,phi,sqrt(vec.x*vec.x+vec.y*vec.y)*xl,true);
-     167             :       else
-     168       24344 :         return loc2pix (nz,phi,0,false);
-     169             :       }
-     170             : 
-     171             :     /*! Returns the angular coordinates (\a z:=cos(theta), \a phi) of the center
-     172             :         of the pixel with number \a pix.
-     173             :         \note This method is inaccurate near the poles at high resolutions. */
-     174           0 :     void pix2zphi (I pix, double &z, double &phi) const
-     175             :       {
-     176             :       bool dum_b;
-     177             :       double dum_d;
-     178           0 :       pix2loc(pix,z,phi,dum_d,dum_b);
-     179           0 :       }
-     180             : 
-     181             :     /*! Returns the angular coordinates of the center of the pixel with
-     182             :         number \a pix. */
-     183           0 :     pointing pix2ang (I pix) const
-     184             :       {
-     185             :       double z, phi, sth;
-     186             :       bool have_sth;
-     187           0 :       pix2loc (pix,z,phi,sth,have_sth);
-     188           0 :       return have_sth ? pointing(atan2(sth,z),phi) : pointing(acos(z),phi);
-     189             :       }
-     190             :     /*! Returns the vector to the center of the pixel with number \a pix. */
-     191      135593 :     vec3 pix2vec (I pix) const
-     192             :       {
-     193             :       double z, phi, sth;
-     194             :       bool have_sth;
-     195      135593 :       pix2loc (pix,z,phi,sth,have_sth);
-     196      135593 :       if (have_sth)
-     197        1417 :         return vec3(sth*cos(phi),sth*sin(phi),z);
-     198             :       else
-     199             :         {
-     200             :         vec3 res;
-     201      134176 :         res.set_z_phi (z, phi);
-     202      134176 :         return res;
-     203             :         }
-     204             :       }
-     205             : 
-     206             :     template<typename I2> void query_disc_internal (pointing ptg, double radius,
-     207             :       int fact, rangeset<I2> &pixset) const;
-     208             : 
-     209             :     /*! Returns the range set of all pixels whose centers lie within the disk
-     210             :         defined by \a dir and \a radius.
-     211             :         \param dir the angular coordinates of the disk center
-     212             :         \param radius the radius (in radians) of the disk
-     213             :         \param pixset a \a rangeset object containing the indices of all pixels
-     214             :            whose centers lie inside the disk
-     215             :         \note This method is more efficient in the RING scheme. */
-     216             :     void query_disc (pointing ptg, double radius, rangeset<I> &pixset) const;
-     217             :     /*! Returns the range set of all pixels which overlap with the disk
-     218             :         defined by \a dir and \a radius.
-     219             :         \param dir the angular coordinates of the disk center
-     220             :         \param radius the radius (in radians) of the disk
-     221             :         \param pixset a \a rangeset object containing the indices of all pixels
-     222             :            overlapping with the disk.
-     223             :         \param fact The overlapping test will be done at the resolution
-     224             :            \a fact*nside. For NESTED ordering, \a fact must be a power of 2,
-     225             :            else it can be any positive integer. A typical choice would be 4.
-     226             :         \note This method may return some pixels which don't overlap with
-     227             :            the disk at all. The higher \a fact is chosen, the fewer false
-     228             :            positives are returned, at the cost of increased run time.
-     229             :         \note This method is more efficient in the RING scheme. */
-     230             :     void query_disc_inclusive (pointing ptg, double radius, rangeset<I> &pixset,
-     231             :       int fact=1) const;
-     232             : 
-     233             :     /*! \deprecated Please use the version based on \a rangeset */
-     234           0 :     void query_disc (const pointing &dir, double radius,
-     235             :       std::vector<I> &listpix) const
-     236             :       {
-     237             :       rangeset<I> pixset;
-     238           0 :       query_disc(dir,radius,pixset);
-     239           0 :       pixset.toVector(listpix);
-     240           0 :       }
-     241             :     /*! \deprecated Please use the version based on \a rangeset */
-     242           0 :     void query_disc_inclusive (const pointing &dir, double radius,
-     243             :       std::vector<I> &listpix, int fact=1) const
-     244             :       {
-     245             :       rangeset<I> pixset;
-     246           0 :       query_disc_inclusive(dir,radius,pixset,fact);
-     247           0 :       pixset.toVector(listpix);
-     248           0 :       }
-     249             : 
-     250             :     template<typename I2> void query_polygon_internal
-     251             :       (const std::vector<pointing> &vertex, int fact,
-     252             :       rangeset<I2> &pixset) const;
-     253             : 
-     254             :     /*! Returns a range set of pixels whose centers lie within the convex
-     255             :         polygon defined by the \a vertex array.
-     256             :         \param vertex array containing the vertices of the polygon.
-     257             :         \param pixset a \a rangeset object containing the indices of all pixels
-     258             :            whose centers lie inside the polygon
-     259             :         \note This method is more efficient in the RING scheme. */
-     260             :     void query_polygon (const std::vector<pointing> &vertex,
-     261             :       rangeset<I> &pixset) const;
-     262             : 
-     263             :     /*! Returns a range set of pixels which overlap with the convex
-     264             :         polygon defined by the \a vertex array.
-     265             :         \param vertex array containing the vertices of the polygon.
-     266             :         \param pixset a \a rangeset object containing the indices of all pixels
-     267             :            overlapping with the polygon.
-     268             :         \param fact The overlapping test will be done at the resolution
-     269             :            \a fact*nside. For NESTED ordering, \a fact must be a power of 2,
-     270             :            else it can be any positive integer. A typical choice would be 4.
-     271             :         \note This method may return some pixels which don't overlap with
-     272             :            the polygon at all. The higher \a fact is chosen, the fewer false
-     273             :            positives are returned, at the cost of increased run time.
-     274             :         \note This method is more efficient in the RING scheme. */
-     275             :     void query_polygon_inclusive (const std::vector<pointing> &vertex,
-     276             :       rangeset<I> &pixset, int fact=1) const;
-     277             : 
-     278             :     /*! Returns a range set of pixels whose centers lie within the colatitude
-     279             :         range defined by \a theta1 and \a theta2 (if \a inclusive==false), or
-     280             :         which overlap with this region (if \a inclusive==true). If
-     281             :         \a theta1<theta2, the region between both angles is considered,
-     282             :         otherwise the regions \a 0<theta<theta2 and \a theta1<theta<pi.
-     283             :         \param theta1 first colatitude
-     284             :         \param theta2 second colatitude
-     285             :         \param inclusive if \a false, return the exact set of pixels whose
-     286             :            pixels centers lie within the region; if \a true, return all pixels
-     287             :            that overlap with the region. */
-     288             :     void query_strip (double theta1, double theta2, bool inclusive,
-     289             :       rangeset<I> &pixset) const;
-     290             : 
-     291             :     /*! Returns useful information about a given ring of the map.
-     292             :         \param ring the ring number (the number of the first ring is 1)
-     293             :         \param startpix the number of the first pixel in the ring
-     294             :                (NOTE: this is always given in the RING numbering scheme!)
-     295             :         \param ringpix the number of pixels in the ring
-     296             :         \param costheta the cosine of the colatitude of the ring
-     297             :         \param sintheta the sine of the colatitude of the ring
-     298             :         \param shifted if \a true, the center of the first pixel is not at
-     299             :                \a phi=0 */
-     300             :     void get_ring_info (I ring, I &startpix, I &ringpix,
-     301             :       double &costheta, double &sintheta, bool &shifted) const;
-     302             :     /*! Returns useful information about a given ring of the map.
-     303             :         \param ring the ring number (the number of the first ring is 1)
-     304             :         \param startpix the number of the first pixel in the ring
-     305             :                (NOTE: this is always given in the RING numbering scheme!)
-     306             :         \param ringpix the number of pixels in the ring
-     307             :         \param theta the colatitude (in radians) of the ring
-     308             :         \param shifted if \a true, the center of the first pixel is not at
-     309             :                \a phi=0 */
-     310             :     void get_ring_info2 (I ring, I &startpix, I &ringpix,
-     311             :       double &theta, bool &shifted) const;
-     312             :     /*! Returns useful information about a given ring of the map.
-     313             :         \param ring the ring number (the number of the first ring is 1)
-     314             :         \param startpix the number of the first pixel in the ring
-     315             :                (NOTE: this is always given in the RING numbering scheme!)
-     316             :         \param ringpix the number of pixels in the ring
-     317             :         \param shifted if \a true, the center of the first pixel is not at
-     318             :                \a phi=0 */
-     319             :     void get_ring_info_small (I ring, I &startpix, I &ringpix,
-     320             :         bool &shifted) const;
-     321             :     /*! Returns the neighboring pixels of \a pix in \a result.
-     322             :         On exit, \a result contains (in this order)
-     323             :         the pixel numbers of the SW, W, NW, N, NE, E, SE and S neighbor
-     324             :         of \a pix. If a neighbor does not exist (this can only be the case
-     325             :         for the W, N, E and S neighbors), its entry is set to -1.
-     326             : 
-     327             :         \note This method works in both RING and NEST schemes, but is
-     328             :           considerably faster in the NEST scheme. */
-     329             :     void neighbors (I pix, fix_arr<I,8> &result) const;
-     330             :     /*! Returns interpolation information for the direction \a ptg.
-     331             :         The surrounding pixels are returned in \a pix, their corresponding
-     332             :         weights in \a wgt.
-     333             :         \note This method works in both RING and NEST schemes, but is
-     334             :           considerably faster in the RING scheme. */
-     335             :     void get_interpol (const pointing &ptg, fix_arr<I,4> &pix,
-     336             :                        fix_arr<double,4> &wgt) const;
-     337             : 
-     338             :     /*! Returns the order parameter of the object. */
-     339         421 :     int Order() const { return order_; }
-     340             :     /*! Returns the \a N_side parameter of the object. */
-     341           0 :     I Nside() const { return nside_; }
-     342             :     /*! Returns the number of pixels of the object. */
-     343    10403763 :     I Npix() const { return npix_; }
-     344             :     /*! Returns the ordering scheme of the object. */
-     345           0 :     Healpix_Ordering_Scheme Scheme() const { return scheme_; }
-     346             : 
-     347             :     /*! Returns \a true, if both objects have the same nside and scheme,
-     348             :         else \a false. */
-     349           0 :     bool conformable (const T_Healpix_Base &other) const
-     350           0 :       { return ((nside_==other.nside_) && (scheme_==other.scheme_)); }
-     351             : 
-     352             :     /*! Swaps the contents of two Healpix_Base objects. */
-     353             :     void swap (T_Healpix_Base &other);
-     354             : 
-     355             :     /*! Returns the maximum angular distance (in radian) between any pixel
-     356             :         center and its corners. */
-     357             :     double max_pixrad() const;
-     358             : 
-     359             :     /*! Returns the maximum angular distance (in radian) between any pixel
-     360             :         center and its corners in a given ring. */
-     361             :     double max_pixrad(I ring) const;
-     362             : 
-     363             :     /*! Returns a set of points along the boundary of the given pixel.
-     364             :         \a step=1 gives 4 points on the corners. The first point corresponds
-     365             :         to the northernmost corner, the subsequent points follow the pixel
-     366             :         boundary through west, south and east corners.
-     367             :         \param pix pixel index number
-     368             :         \param step the number of returned points is 4*step. */
-     369             :     void boundaries (I pix, tsize step, std::vector<vec3> &out) const;
-     370             : 
-     371             :     arr<int> swap_cycles() const;
-     372             :   };
-     373             : 
-     374             : /*! T_Healpix_Base for Nside up to 2^13. */
-     375             : typedef T_Healpix_Base<int> Healpix_Base;
-     376             : /*! T_Healpix_Base for Nside up to 2^29. */
-     377             : typedef T_Healpix_Base<int64> Healpix_Base2;
-     378             : 
-     379             : } // namespace healpix
-     380             : #endif
-     381             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html deleted file mode 100644 index 0195d8cd1..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-f.html +++ /dev/null @@ -1,173 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:3317319.1 %
Date:2024-04-08 14:58:22Functions:5628.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.h -
0.0%
-
0.0 %0 / 20.0 %0 / 1
arr.h -
0.0%
-
0.0 %0 / 150.0 %0 / 1
geom_utils.h -
0.0%
-
0.0 %0 / 40.0 %0 / 2
alloc_utils.h -
0.0%
-
0.0 %0 / 20.0 %0 / 6
rangeset.h -
0.0%
-
0.0 %0 / 510.0 %0 / 12
healpix_base.h -
32.0%32.0%
-
32.0 %16 / 508.8 %3 / 34
math_utils.h -
30.4%30.4%
-
30.4 %7 / 2325.0 %1 / 4
vec3.h -
45.5%45.5%
-
45.5 %10 / 2250.0 %1 / 2
pointing.h -
0.0%
-
0.0 %0 / 4-0 / 0
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html deleted file mode 100644 index 19da9ac89..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/index-sort-l.html +++ /dev/null @@ -1,173 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:3317319.1 %
Date:2024-04-08 14:58:22Functions:5628.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.h -
0.0%
-
0.0 %0 / 20.0 %0 / 1
alloc_utils.h -
0.0%
-
0.0 %0 / 20.0 %0 / 6
geom_utils.h -
0.0%
-
0.0 %0 / 40.0 %0 / 2
pointing.h -
0.0%
-
0.0 %0 / 4-0 / 0
arr.h -
0.0%
-
0.0 %0 / 150.0 %0 / 1
rangeset.h -
0.0%
-
0.0 %0 / 510.0 %0 / 12
math_utils.h -
30.4%30.4%
-
30.4 %7 / 2325.0 %1 / 4
healpix_base.h -
32.0%32.0%
-
32.0 %16 / 508.8 %3 / 34
vec3.h -
45.5%45.5%
-
45.5 %10 / 2250.0 %1 / 2
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/index.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/index.html deleted file mode 100644 index ce3223c46..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/index.html +++ /dev/null @@ -1,173 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:3317319.1 %
Date:2024-04-08 14:58:22Functions:5628.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
alloc_utils.h -
0.0%
-
0.0 %0 / 20.0 %0 / 6
arr.h -
0.0%
-
0.0 %0 / 150.0 %0 / 1
error_handling.h -
0.0%
-
0.0 %0 / 20.0 %0 / 1
geom_utils.h -
0.0%
-
0.0 %0 / 40.0 %0 / 2
healpix_base.h -
32.0%32.0%
-
32.0 %16 / 508.8 %3 / 34
math_utils.h -
30.4%30.4%
-
30.4 %7 / 2325.0 %1 / 4
pointing.h -
0.0%
-
0.0 %0 / 4-0 / 0
rangeset.h -
0.0%
-
0.0 %0 / 510.0 %0 / 12
vec3.h -
45.5%45.5%
-
45.5 %10 / 2250.0 %1 / 2
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html deleted file mode 100644 index 822b61bad..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func-sort-c.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/math_utils.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - math_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:72330.4 %
Date:2024-04-08 14:58:22Functions:1425.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14isqrt_helper__IlLb1EE5isqrtEl0
_ZN7healpix5ilog2IiEEiT_0
_ZN7healpix5ilog2IlEEiT_0
_ZN7healpix7fmoduloEdd24585
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html deleted file mode 100644 index 0fdeff09e..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.func.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/math_utils.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - math_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:72330.4 %
Date:2024-04-08 14:58:22Functions:1425.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix14isqrt_helper__IlLb1EE5isqrtEl0
_ZN7healpix5ilog2IiEEiT_0
_ZN7healpix5ilog2IlEEiT_0
_ZN7healpix7fmoduloEdd24585
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html deleted file mode 100644 index badf8789f..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/math_utils.h.gcov.html +++ /dev/null @@ -1,259 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/math_utils.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - math_utils.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:72330.4 %
Date:2024-04-08 14:58:22Functions:1425.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*! \file math_utils.h
-      26             :  *  Various convenience mathematical functions.
-      27             :  *
-      28             :  *  Copyright (C) 2002-2012 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #ifndef PLANCK_MATH_UTILS_H
-      33             : #define PLANCK_MATH_UTILS_H
-      34             : 
-      35             : #include <cmath>
-      36             : #include <algorithm>
-      37             : #include "healpix_base/datatypes.h"
-      38             : 
-      39             : namespace healpix{
-      40             : 
-      41             : /*! \defgroup mathutilsgroup Mathematical helper functions */
-      42             : /*! \{ */
-      43             : 
-      44             : /*! Returns \e true if | \a a-b | <= \a epsilon * | \a b |, else \e false. */
-      45             : template<typename F> inline bool approx (F a, F b, F epsilon=1e-5)
-      46             :   {
-      47             :   using namespace std;
-      48             :   return abs(a-b) <= (epsilon*abs(b));
-      49             :   }
-      50             : 
-      51             : /*! Returns \e true if | \a a-b | <= \a epsilon, else \e false. */
-      52             : template<typename F> inline bool abs_approx (F a, F b, F epsilon=1e-5)
-      53             :   {
-      54             :   using namespace std;
-      55             :   return abs(a-b) <= epsilon;
-      56             :   }
-      57             : 
-      58             : /*! Returns the largest integer which is smaller than (or equal to) \a arg. */
-      59             : template<typename I, typename F> inline I ifloor (F arg)
-      60             :   {
-      61             :   using namespace std;
-      62           0 :   return I(floor(arg));
-      63             :   }
-      64             : 
-      65             : /*! Returns the integer which is nearest to \a arg. */
-      66             : template<typename I, typename F> inline I nearest (F arg)
-      67             :   { return ifloor<I>(arg+0.5); }
-      68             : 
-      69             : /*! Returns the remainder of the division \a v1/v2.
-      70             :     The result is non-negative.
-      71             :     \a v1 can be positive or negative; \a v2 must be positive. */
-      72       24585 : inline double fmodulo (double v1, double v2)
-      73             :   {
-      74             :   using namespace std;
-      75       24585 :   if (v1>=0)
-      76       12356 :     return (v1<v2) ? v1 : fmod(v1,v2);
-      77       12229 :   double tmp=fmod(v1,v2)+v2;
-      78       12229 :   return (tmp==v2) ? 0. : tmp;
-      79             : //  return (v1>=0) ? ((v1<v2) ? v1 : fmod(v1,v2)) : (fmod(v1,v2)+v2);
-      80             :   }
-      81             : 
-      82             : /*! Returns the remainder of the division \a v1/v2.
-      83             :     The result is non-negative.
-      84             :     \a v1 can be positive or negative; \a v2 must be positive. */
-      85             : template<typename I> inline I imodulo (I v1, I v2)
-      86             :   { I v=v1%v2; return (v>=0) ? v : v+v2; }
-      87             : 
-      88             : /*! Returns -1 if \a signvalue is negative, else +1. */
-      89             : template<typename T> inline T sign (const T& signvalue)
-      90             :   { return (signvalue>=0) ? 1 : -1; }
-      91             : 
-      92             : /*! Returns \a val*pow(-1,m) */
-      93             : template<typename T, typename I> inline T xpow (I m, T val)
-      94             :   { return (m&1) ? -val : val; }
-      95             : 
-      96             : template<typename I, bool g4> struct isqrt_helper__
-      97             :   {};
-      98             : template<typename I> struct isqrt_helper__ <I, false>
-      99             :   {
-     100             :   static uint32 isqrt (I arg)
-     101             :     {
-     102             :     using namespace std;
-     103       44162 :     return uint32 (sqrt(arg+0.5));
-     104             :     }
-     105             :   };
-     106             : template<typename I> struct isqrt_helper__ <I, true>
-     107             :   {
-     108           0 :   static uint32 isqrt (I arg)
-     109             :     {
-     110             :     using namespace std;
-     111           0 :     I res = sqrt(double(arg)+0.5);
-     112           0 :     if (arg<(int64(1)<<50)) return uint32(res);
-     113           0 :     if (res*res>arg)
-     114           0 :       --res;
-     115           0 :     else if ((res+1)*(res+1)<=arg)
-     116             :       ++res;
-     117           0 :     return uint32(res);
-     118             :     }
-     119             :   };
-     120             : 
-     121             : /*! Returns the integer \a n, which fulfills \a n*n<=arg<(n+1)*(n+1). */
-     122             : template<typename I> inline uint32 isqrt (I arg)
-     123           0 :   { return isqrt_helper__<I,(sizeof(I)>4)>::isqrt(arg); }
-     124             : 
-     125             : /*! Returns the largest integer \a n that fulfills \a 2^n<=arg. */
-     126           0 : template<typename I> inline int ilog2 (I arg)
-     127             :   {
-     128             :   int res=0;
-     129           0 :   while (arg > 0x0000FFFF) { res+=16; arg>>=16; }
-     130           0 :   if (arg > 0x000000FF) { res|=8; arg>>=8; }
-     131           0 :   if (arg > 0x0000000F) { res|=4; arg>>=4; }
-     132           0 :   if (arg > 0x00000003) { res|=2; arg>>=2; }
-     133           0 :   if (arg > 0x00000001) { res|=1; }
-     134           0 :   return res;
-     135             :   }
-     136             : 
-     137             : /*! Returns \a atan2(y,x) if \a x!=0 or \a y!=0; else returns 0. */
-     138             : inline double safe_atan2 (double y, double x)
-     139             :   {
-     140             :   using namespace std;
-     141       61874 :   return ((x==0.) && (y==0.)) ? 0.0 : atan2(y,x);
-     142             :   }
-     143             : 
-     144             : /*! Helper function for linear interpolation (or extrapolation).
-     145             :     The array must be ordered in ascending order; no two values may be equal. */
-     146             : template<typename T, typename Iter, typename Comp> inline void interpol_helper
-     147             :   (const Iter &begin, const Iter &end, const T &val, Comp comp, tsize &idx,
-     148             :   T &frac)
-     149             :   {
-     150             :   using namespace std;
-     151             :   planck_assert((end-begin)>1,"sequence too small for interpolation");
-     152             :   idx = lower_bound(begin,end,val,comp)-begin;
-     153             :   if (idx>0) --idx;
-     154             :   idx = min(tsize(end-begin-2),idx);
-     155             :   frac = (val-begin[idx])/(begin[idx+1]-begin[idx]);
-     156             :   }
-     157             : 
-     158             : /*! Helper function for linear interpolation (or extrapolation).
-     159             :     The array must be ordered in ascending order; no two values may be equal. */
-     160             : template<typename T, typename Iter> inline void interpol_helper
-     161             :   (const Iter &begin, const Iter &end, const T &val, tsize &idx, T &frac)
-     162             :   { interpol_helper (begin,end,val,std::less<T>(),idx,frac); }
-     163             : 
-     164             : /*! \} */
-     165             : 
-     166             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c)
-     167             :   { return (a==b) && (a==c); }
-     168             : 
-     169             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c,
-     170             :   const T &d)
-     171             :   { return (a==b) && (a==c) && (a==d); }
-     172             : 
-     173             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c,
-     174             :   const T &d, const T &e)
-     175             :   { return (a==b) && (a==c) && (a==d) && (a==e); }
-     176             : 
-     177             : template<typename T> inline bool multiequal (const T &a, const T &b, const T &c,
-     178             :   const T &d, const T &e, const T &f)
-     179             :   { return (a==b) && (a==c) && (a==d) && (a==e) && (a==f); }
-     180             : 
-     181             : } // namespace healpix
-     182             : #endif
-     183             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html deleted file mode 100644 index bd57abfaa..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func-sort-c.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/pointing.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - pointing.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html deleted file mode 100644 index 1bde73dd1..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.func.html +++ /dev/null @@ -1,72 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/pointing.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - pointing.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- -
- - - - - - -

Function Name Sort by function nameHit count Sort by hit count
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html deleted file mode 100644 index 59e765ab6..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/pointing.h.gcov.html +++ /dev/null @@ -1,161 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/pointing.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - pointing.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:040.0 %
Date:2024-04-08 14:58:22Functions:00-
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*! \file pointing.h
-      26             :  *  Class representing a direction in 3D space
-      27             :  *
-      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #ifndef PLANCK_POINTING_H
-      33             : #define PLANCK_POINTING_H
-      34             : 
-      35             : #include <cmath>
-      36             : #include "healpix_base/vec3.h"
-      37             : 
-      38             : namespace healpix{
-      39             : 
-      40             : /*! \defgroup pointinggroup Pointings */
-      41             : /*! \{ */
-      42             : 
-      43             : /*! Class representing a direction in 3D space or a location on the
-      44             :     unit sphere. All angles in radians. */
-      45             : class pointing
-      46             :   {
-      47             :   public:
-      48             :     /*! Colatitude of the pointing (i.e. the North pole is at \a theta=0). */
-      49             :     double theta;
-      50             :     /*! Longitude of the pointing. */
-      51             :     double phi;
-      52             : 
-      53             :     /*! Default constructor. \a theta and \a phi are not initialized. */
-      54           0 :     pointing() {}
-      55             :     /*! Creates a pointing with \a Theta and \a Phi. */
-      56           0 :     pointing (double Theta, double Phi) : theta(Theta), phi(Phi) {}
-      57             : 
-      58             : // FIXME: should become "explicit" some time
-      59             :     /*! Creates a pointing from the vector \a inp. \a inp need not be
-      60             :         normalized. */
-      61             :     pointing (const vec3 &inp)
-      62           0 :       { from_vec3(inp); }
-      63             : // FIXME: should be removed some time
-      64             :     /*! Returns a normalized vector pointing in the same direction. */
-      65             :     operator vec3() const
-      66           0 :       { return to_vec3(); }
-      67             :     /*! Returns a normalized vector pointing in the same direction. */
-      68             :     vec3 to_vec3() const;
-      69             :     /*! Converts \a inp to \a ptg. \a inp need not be normalized. */
-      70             :     void from_vec3 (const vec3 &inp);
-      71             :     /*! Changes the angles so that \a 0<=theta<=pi. */
-      72             :     void normalize_theta();
-      73             :     /*! Changes the angles so that \a 0<=theta<=pi and \a 0<=phi<2*pi. */
-      74             :     void normalize();
-      75             :   };
-      76             : 
-      77             : /*! Writes \a p to \a os.
-      78             :     \relates pointing */
-      79             : std::ostream &operator<< (std::ostream &os, const pointing &p);
-      80             : 
-      81             : /*! \} */
-      82             : 
-      83             : } // namespace healpix
-      84             : #endif
-      85             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html deleted file mode 100644 index 9daab7962..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func-sort-c.html +++ /dev/null @@ -1,120 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/rangeset.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - rangeset.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0510.0 %
Date:2024-04-08 14:58:22Functions:0120.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8rangesetIiE6appendERKS1_0
_ZN7healpix8rangesetIiE6appendERKiS3_0
_ZN7healpix8rangesetIiE9addRemoveEiil0
_ZN7healpix8rangesetIiE9intersectERKiS3_0
_ZN7healpix8rangesetIlE6appendERKS1_0
_ZN7healpix8rangesetIlE6appendERKlS3_0
_ZN7healpix8rangesetIlE9addRemoveElll0
_ZN7healpix8rangesetIlE9intersectERKlS3_0
_ZNK7healpix8rangesetIiE3iivERKi0
_ZNK7healpix8rangesetIiE8toVectorERSt6vectorIiSaIiEE0
_ZNK7healpix8rangesetIlE3iivERKl0
_ZNK7healpix8rangesetIlE8toVectorERSt6vectorIlSaIlEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html deleted file mode 100644 index 8a90294c3..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.func.html +++ /dev/null @@ -1,120 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/rangeset.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - rangeset.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0510.0 %
Date:2024-04-08 14:58:22Functions:0120.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8rangesetIiE6appendERKS1_0
_ZN7healpix8rangesetIiE6appendERKiS3_0
_ZN7healpix8rangesetIiE9addRemoveEiil0
_ZN7healpix8rangesetIiE9intersectERKiS3_0
_ZN7healpix8rangesetIlE6appendERKS1_0
_ZN7healpix8rangesetIlE6appendERKlS3_0
_ZN7healpix8rangesetIlE9addRemoveElll0
_ZN7healpix8rangesetIlE9intersectERKlS3_0
_ZNK7healpix8rangesetIiE3iivERKi0
_ZNK7healpix8rangesetIiE8toVectorERSt6vectorIiSaIiEE0
_ZNK7healpix8rangesetIlE3iivERKl0
_ZNK7healpix8rangesetIlE8toVectorERSt6vectorIlSaIlEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html deleted file mode 100644 index 177519f90..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/rangeset.h.gcov.html +++ /dev/null @@ -1,363 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/rangeset.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - rangeset.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0510.0 %
Date:2024-04-08 14:58:22Functions:0120.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*! \file rangeset.h
-      26             :  *  Class for storing sets of ranges of integer numbers
-      27             :  *
-      28             :  *  Copyright (C) 2011, 2012 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #ifndef PLANCK_RANGESET_H
-      33             : #define PLANCK_RANGESET_H
-      34             : 
-      35             : #include <algorithm>
-      36             : #include <vector>
-      37             : #include <utility>
-      38             : #include <iostream>
-      39             : #include "healpix_base/datatypes.h"
-      40             : #include "healpix_base/error_handling.h"
-      41             : 
-      42             : namespace healpix{
-      43             : 
-      44             : /*! Class for storing sets of ranges of integer numbers */
-      45           0 : template<typename T> class rangeset
-      46             :   {
-      47             :   private:
-      48             :     typedef std::vector<T> rtype;
-      49             :     typedef typename rtype::iterator iterator;
-      50             :     typedef typename rtype::const_iterator c_iterator;
-      51             :     rtype r;
-      52             : 
-      53           0 :     tdiff iiv (const T &val) const
-      54           0 :       { return tdiff(std::upper_bound(r.begin(),r.end(),val)-r.begin())-1; }
-      55             : 
-      56           0 :     void addRemove (T a, T b, tdiff v)
-      57             :       {
-      58           0 :       tdiff pos1=iiv(a), pos2=iiv(b);
-      59           0 :       if ((pos1>=0) && (r[pos1]==a)) --pos1;
-      60             :       // first to delete is at pos1+1; last is at pos2
-      61           0 :       bool insert_a = (pos1&1)==v;
-      62           0 :       bool insert_b = (pos2&1)==v;
-      63           0 :       int rmstart=pos1+1+(insert_a ? 1 : 0);
-      64           0 :       int rmend  =pos2-(insert_b?1:0);
-      65             : 
-      66           0 :       planck_assert((rmend-rmstart)&1,"cannot happen");
-      67             : 
-      68           0 :       if (insert_a && insert_b && (pos1+1>pos2)) // insert
-      69             :         {
-      70           0 :         r.insert(r.begin()+pos1+1,2,a);
-      71           0 :         r[pos1+2]=b;
-      72             :         }
-      73             :       else
-      74             :         {
-      75           0 :         if (insert_a) r[pos1+1]=a;
-      76           0 :         if (insert_b) r[pos2]=b;
-      77           0 :         r.erase(r.begin()+rmstart,r.begin()+rmend+1);
-      78             :         }
-      79           0 :       }
-      80             : 
-      81             :     static void generalUnion (const rtype &a, const rtype &b,
-      82             :       bool flip_a, bool flip_b, rtype &c)
-      83             :       {
-      84             :       planck_assert((&c!=&a)&&(&c!=&b), "cannot overwrite the rangeset");
-      85             :       c.clear();
-      86             :       bool state_a=flip_a, state_b=flip_b, state_res=state_a||state_b;
-      87             :       tsize ia=0, ea=a.size(), ib=0, eb=b.size();
-      88             :       bool runa = ia!=ea, runb = ib!=eb;
-      89             :       while(runa||runb)
-      90             :         {
-      91             :         bool adv_a=false, adv_b=false;
-      92             :         T val,va=T(),vb=T();
-      93             :         if (runa) va = a[ia];
-      94             :         if (runb) vb = b[ib];
-      95             :         if (runa && (!runb || (va<=vb))) { adv_a=true; val=va; }
-      96             :         if (runb && (!runa || (vb<=va))) { adv_b=true; val=vb; }
-      97             :         if (adv_a) { state_a=!state_a; ++ia; runa = ia!=ea; }
-      98             :         if (adv_b) { state_b=!state_b; ++ib; runb = ib!=eb; }
-      99             :         if ((state_a||state_b)!=state_res)
-     100             :           { c.push_back(val); state_res = !state_res; }
-     101             :         }
-     102             :       }
-     103             : 
-     104             :   public:
-     105             :     /*! Removes all rangeset entries. */
-     106             :     void clear() { r.clear(); }
-     107             :     /*! Reserves space for \a n ranges. */
-     108             :     void reserve(tsize n) { r.reserve(2*n); }
-     109             :     /*! Returns the current number of ranges. */
-     110           0 :     tsize size() const { return r.size()>>1; }
-     111             :     /*! Returns the current vector of ranges. */
-     112             :     const rtype &data() const { return r; }
-     113             : 
-     114             :     /*! Returns the first value of range \a i. */
-     115           0 :     const T &ivbegin (tdiff i) const { return r[2*i]; }
-     116             :     /*! Returns the one-past-last value of range \a i. */
-     117           0 :     const T &ivend (tdiff i) const { return r[2*i+1]; }
-     118             :     /*! Returns the length of range \a i. */
-     119             :     T ivlen (tdiff i) const { return r[2*i+1]-r[2*i]; }
-     120             : 
-     121             :     /*! Appends \a [v1;v2[ to the rangeset. \a v1 must be larger
-     122             :         than the minimum of the last range in the rangeset. */
-     123           0 :     void append(const T &v1, const T &v2)
-     124             :       {
-     125           0 :       if (v2<=v1) return;
-     126           0 :       if ((!r.empty()) && (v1<=r.back()))
-     127             :         {
-     128           0 :         planck_assert (v1>=r[r.size()-2],"bad append operation");
-     129           0 :         if (v2>r.back()) r.back()=v2;
-     130             :         }
-     131             :       else
-     132           0 :         { r.push_back(v1); r.push_back(v2); }
-     133             :       }
-     134             :     /*! Appends \a [v;v+1[ to the rangeset. \a v must be larger
-     135             :         than the minimum of the last range in the rangeset. */
-     136             :     void append(const T &v)
-     137           0 :       { append(v,v+1); }
-     138             : 
-     139             :     /*! Appends \a other to the rangeset. All values in \a other must be larger
-     140             :         than the minimum of the last range in the rangeset. */
-     141           0 :     void append (const rangeset &other)
-     142             :       {
-     143           0 :       for (tsize j=0; j<other.size(); ++j)
-     144           0 :         append(other.ivbegin(j),other.ivend(j));
-     145           0 :       }
-     146             : 
-     147             :     /*! After this operation, the rangeset contains the union of itself
-     148             :         with \a [v1;v2[. */
-     149             :     void add(const T &v1, const T &v2) { addRemove(v1,v2,1); }
-     150             :     /*! After this operation, the rangeset contains the union of itself
-     151             :         with \a [v;v+1[. */
-     152             :     void add(const T &v) { addRemove(v,v+1,1); }
-     153             : 
-     154             :     /*! Removes all values within \a [v1;v2[ from the rangeset. */
-     155           0 :     void remove(const T &v1, const T &v2) { addRemove(v1,v2,0); }
-     156             :     /*! Removes the value \a v from the rangeset. */
-     157             :     void remove(const T &v) { addRemove(v,v+1,0); }
-     158             : 
-     159             :     /*! Removes all values not within \a [v1;v2[ from the rangeset. */
-     160           0 :     void intersect (const T &a, const T &b)
-     161             :       {
-     162           0 :       tdiff pos1=iiv(a), pos2=iiv(b);
-     163           0 :       if ((pos2>=0) && (r[pos2]==b)) --pos2;
-     164             :       // delete all up to pos1 (inclusive); and starting from pos2+1
-     165           0 :       bool insert_a = (pos1&1)==0;
-     166           0 :       bool insert_b = (pos2&1)==0;
-     167             : 
-     168             :       // cut off end
-     169           0 :       r.erase(r.begin()+pos2+1,r.end());
-     170           0 :       if (insert_b) r.push_back(b);
-     171             : 
-     172             :       // erase start
-     173           0 :       if (insert_a) r[pos1--]=a;
-     174           0 :       if (pos1>=0)
-     175             :         r.erase(r.begin(),r.begin()+pos1+1);
-     176           0 :       }
-     177             : 
-     178             :     /*! Returns the total number of elements in the rangeset. */
-     179             :     T nval() const
-     180             :       {
-     181             :       T result=T(0);
-     182           0 :       for (tsize i=0; i<r.size(); i+=2)
-     183           0 :         result+=r[i+1]-r[i];
-     184             :       return result;
-     185             :       }
-     186             : 
-     187             :     /*! After this opration, \a res contains all elements of the rangeset
-     188             :         in ascending order. */
-     189           0 :     void toVector (std::vector<T> &res) const
-     190             :       {
-     191             :       res.clear();
-     192           0 :       res.reserve(nval());
-     193           0 :       for (tsize i=0; i<r.size(); i+=2)
-     194           0 :         for (T m(r[i]); m<r[i+1]; ++m)
-     195           0 :           res.push_back(m);
-     196           0 :       }
-     197             : 
-     198             :     /*! After this operation, the rangeset contains the union of itself
-     199             :         and \a other. */
-     200             :     void unite (const rangeset &other)
-     201             :       {
-     202             :       rtype tmp;
-     203             :       generalUnion (r,other.r,false,false,tmp);
-     204             :       std::swap(r,tmp);
-     205             :       }
-     206             :     /*! After this operation, the rangeset contains the intersection of itself
-     207             :         and \a other. */
-     208             :     void intersect (const rangeset &other)
-     209             :       {
-     210             :       rtype tmp;
-     211             :       generalUnion (r,other.r,true,true,tmp);
-     212             :       std::swap(r,tmp);
-     213             :       }
-     214             :     /*! After this operation, the rangeset contains the union of itself
-     215             :         with the inverse of \a other. */
-     216             :     void subtract (const rangeset &other)
-     217             :       {
-     218             :       rtype tmp;
-     219             :       generalUnion (r,other.r,true,false,tmp);
-     220             :       std::swap(r,tmp);
-     221             :       }
-     222             :     /*! After this operation, the rangeset contains the union of \a a
-     223             :         and \a b. */
-     224             :     void setToUnion (const rangeset &a, const rangeset &b)
-     225             :       { generalUnion (a.r,b.r,false,false,r); }
-     226             :     /*! After this operation, the rangeset contains the intersection of \a a
-     227             :         and \a b. */
-     228             :     void setToIntersection (const rangeset &a, const rangeset &b)
-     229             :       { generalUnion (a.r,b.r,true,true,r); }
-     230             :     /*! After this operation, the rangeset contains the union of \a a
-     231             :         with the inverse of \a b. */
-     232             :     void setToDifference (const rangeset &a, const rangeset &b)
-     233             :       { generalUnion (a.r,b.r,true,false,r); }
-     234             : 
-     235             :     /*! Returns the index of the interval containing \a v; if no such interval
-     236             :         exists, -1 is returned. */
-     237             :     tdiff findInterval (const T &v) const
-     238             :       {
-     239             :       tdiff res = iiv(v);
-     240             :       return (res&1) ? -1 : res>>1;
-     241             :       }
-     242             : 
-     243             :     /*! Returns \a true if the rangeset is identical to \a other, else \a false.
-     244             :         */
-     245             :     bool equals (const rangeset &other) const
-     246             :       { return r==other.data(); }
-     247             : 
-     248             :     /*! Returns \a true if the rangeset contains all values in the range
-     249             :         \a [a;b[, else \a false. */
-     250             :     bool containsAll (T a,T b) const
-     251             :       {
-     252             :       tdiff res=iiv(a);
-     253             :       if (res&1) return false;
-     254             :       return (b<=r[res+1]);
-     255             :       }
-     256             :     /*! Returns \a true if the rangeset contains the value \a v,
-     257             :         else \a false. */
-     258             :     bool contains (T v) const
-     259             :       { return !(iiv(v)&1); }
-     260             :     /*! Returns \a true if the rangeset contains all values stored in \a other,
-     261             :         else \a false. */
-     262             :     bool contains (const rangeset &other) const
-     263             :       {
-     264             :       tsize im=0, em=r.size();
-     265             :       for (tsize i=0; i<other.r.size(); i+=2)
-     266             :         {
-     267             :         T a=other.r[i], b=other.r[i+1];
-     268             :         while ((im!=em) && (r[im+1] < a)) im+=2;
-     269             :         if (im==em) return false;
-     270             :         if ((r[im]>a) || (r[im+1]<b)) return false;
-     271             :         }
-     272             :       return true;
-     273             :       }
-     274             :   };
-     275             : 
-     276             : template<typename T> inline std::ostream &operator<< (std::ostream &os,
-     277             :   const rangeset<T> &rs)
-     278             :   {
-     279             :   os << "{ ";
-     280             :   for (tsize i=0; i<rs.size(); ++i)
-     281             :     os << "["<<rs.ivbegin(i)<<";"<<rs.ivend(i)<<"[ ";
-     282             :   return os << "}";
-     283             :   }
-     284             : 
-     285             : } // namespace healpix
-     286             : #endif
-     287             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html deleted file mode 100644 index 50398e10d..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/vec3.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - vec3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:102245.5 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix6vec3_tIdE9NormalizeEv0
_ZN7healpix6vec3_tIdE9set_z_phiEdd134176
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html deleted file mode 100644 index 633dc74e4..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/vec3.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - vec3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:102245.5 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix6vec3_tIdE9NormalizeEv0
_ZN7healpix6vec3_tIdE9set_z_phiEdd134176
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html b/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html deleted file mode 100644 index 78b942fb1..000000000 --- a/doc/coverageReport/libs/healpix_base/include/healpix_base/vec3.h.gcov.html +++ /dev/null @@ -1,229 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/include/healpix_base/vec3.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base/include/healpix_base - vec3.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:102245.5 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*! \file vec3.h
-      26             :  *  Class representing 3D cartesian vectors
-      27             :  *
-      28             :  *  Copyright (C) 2003, 2006 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #ifndef PLANCK_VEC3_H
-      33             : #define PLANCK_VEC3_H
-      34             : 
-      35             : #include <cmath>
-      36             : #include <iostream>
-      37             : #include "healpix_base/datatypes.h"
-      38             : 
-      39             : namespace healpix{
-      40             : 
-      41             : /*! \defgroup vec3group 3D vectors */
-      42             : /*! \{ */
-      43             : 
-      44             : /*! Class representing a 3D cartesian vector. */
-      45             : template<typename T>class vec3_t
-      46             :   {
-      47             :   public:
-      48             :     T x, /*!< x-coordinate */
-      49             :       y, /*!< y-coordinate */
-      50             :       z; /*!< z-coordinate */
-      51             : 
-      52             :     /*! Default constructor. Does not initialize \a x, \a y, and \a z. */
-      53      244781 :     vec3_t () {}
-      54             :     /*! Creates a vector with the coordinates \a xc, \a yc, and \a zc. */
-      55        1417 :     vec3_t (T xc, T yc, T zc)
-      56        1417 :       : x(xc), y(yc), z(zc) {}
-      57             :     template<typename T2> explicit vec3_t (const vec3_t<T2> &orig)
-      58             :       : x(orig.x), y(orig.y), z(orig.z) {}
-      59             : 
-      60             :     /*! Sets the vector components to \a xc, \a yc, and \a zc. */
-      61             :     void Set (T xc, T yc, T zc)
-      62             :       { x=xc; y=yc; z=zc; }
-      63             :     /*! Creates a unit vector from a z coordinate and an azimuthal angle. */
-      64      134176 :     void set_z_phi (T z_, T phi)
-      65             :       {
-      66             :       using namespace std;
-      67      134176 :       T sintheta = sqrt((T(1)-z_)*(T(1)+z_));
-      68      134176 :       x = sintheta*cos(phi);
-      69      134176 :       y = sintheta*sin(phi);
-      70      134176 :       z = z_;
-      71      134176 :       }
-      72             : 
-      73             :     /*! Normalizes the vector to length 1. */
-      74           0 :     void Normalize ()
-      75             :       {
-      76             :       using namespace std;
-      77           0 :       T l = T(1)/sqrt (x*x + y*y + z*z);
-      78           0 :       x*=l; y*=l; z*=l;
-      79           0 :       }
-      80             : 
-      81             :     vec3_t Norm() const
-      82             :       {
-      83           0 :       vec3_t res(*this);
-      84           0 :       res.Normalize();
-      85             :       return res;
-      86             :       }
-      87             : 
-      88             :     /*! Returns the length of the vector. */
-      89             :     T Length () const
-      90       24585 :       { return sqrt (x*x + y*y + z*z); }
-      91             : 
-      92             :     /*! Returns the squared length of the vector. */
-      93             :     T SquaredLength () const
-      94             :       { return (x*x + y*y + z*z); }
-      95             :     /*! Returns the vector with the signs of all coordinates flipped. */
-      96             :     const vec3_t operator- () const
-      97             :       { return vec3_t (-x, -y, -z); }
-      98             :     /*! Flips the signs of all coordinates. */
-      99             :     void Flip ()
-     100           0 :       { x=-x; y=-y; z=-z; }
-     101             :     /*! Returns (\a *this + \a vec). */
-     102             :     const vec3_t operator+ (const vec3_t &vec) const
-     103           0 :       { return vec3_t (x+vec.x, y+vec.y, z+vec.z); }
-     104             :     /*! Adds \a vec to \a *this. */
-     105             :     vec3_t &operator+= (const vec3_t &vec)
-     106             :       { x+=vec.x; y+=vec.y; z+=vec.z; return *this; }
-     107             :     /*! Returns (\a *this - \a vec). */
-     108             :     const vec3_t operator- (const vec3_t &vec) const
-     109           0 :       { return vec3_t (x-vec.x, y-vec.y, z-vec.z); }
-     110             :     /*! Subtracts \a vec from \a *this. */
-     111             :     vec3_t &operator-= (const vec3_t &vec)
-     112             :       { x-=vec.x; y-=vec.y; z-=vec.z; return *this; }
-     113             :     /*! Returns the vector scaled by \a fact. */
-     114             :     const vec3_t operator* (T fact) const
-     115             :       { return vec3_t (x*fact, y*fact, z*fact); }
-     116             :     /*! Returns the vector scaled by \a 1/fact. */
-     117             :     const vec3_t operator/ (T fact) const
-     118             :       { T xfact = T(1)/fact; return vec3_t (x*xfact, y*xfact, z*xfact); }
-     119             :     /*! Scales the vector by \a fact. */
-     120             :     vec3_t &operator*= (T fact)
-     121           0 :       { x*=fact; y*=fact; z*=fact; return *this; }
-     122             :   };
-     123             : 
-     124             : /*! Returns the dot product of \a v1 and \a v2.
-     125             :     \relates vec3_t */
-     126             : template<typename T> inline T dotprod(const vec3_t<T> &v1, const vec3_t<T> &v2)
-     127           0 :   { return v1.x*v2.x + v1.y*v2.y + v1.z*v2.z; }
-     128             : 
-     129             : /*! Returns the cross product of \a a and \a b.
-     130             :     \relates vec3_t */
-     131             : template<typename T> inline vec3_t<T> crossprod
-     132             :   (const vec3_t<T> &a, const vec3_t<T> &b)
-     133           0 :   { return vec3_t<T>(a.y*b.z - a.z*b.y, a.z*b.x - a.x*b.z, a.x*b.y - a.y*b.x); }
-     134             : 
-     135             : /*! Writes \a v to \a os.
-     136             :     \relates vec3_t */
-     137             : template<typename T> inline std::ostream &operator<<
-     138             :   (std::ostream &os, const vec3_t<T> &v)
-     139             :   {
-     140             :   os << v.x << ", " << v.y << ", " << v.z << std::endl;
-     141             :   return os;
-     142             :   }
-     143             : 
-     144             : /*! Specialisation of vec3_t for 64-bit floating point components */
-     145             : typedef vec3_t<float64> vec3;
-     146             : /*! Specialisation of vec3_t for 32-bit floating point components */
-     147             : typedef vec3_t<float32> vec3f;
-     148             : 
-     149             : /*! \} */
-     150             : 
-     151             : } // namespace healpix
-     152             : #endif
-     153             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/index-sort-f.html b/doc/coverageReport/libs/healpix_base/index-sort-f.html deleted file mode 100644 index 90582d17c..000000000 --- a/doc/coverageReport/libs/healpix_base/index-sort-f.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:11279214.1 %
Date:2024-04-08 14:58:22Functions:101069.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
geom_utils.cc -
0.0%
-
0.0 %0 / 250.0 %0 / 3
pointing.cc -
0.0%
-
0.0 %0 / 210.0 %0 / 5
error_handling.cc -
0.0%
-
0.0 %0 / 120.0 %0 / 7
healpix_base.cc -
15.3%15.3%
-
15.3 %112 / 73411.0 %10 / 91
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/index-sort-l.html b/doc/coverageReport/libs/healpix_base/index-sort-l.html deleted file mode 100644 index 51b835471..000000000 --- a/doc/coverageReport/libs/healpix_base/index-sort-l.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:11279214.1 %
Date:2024-04-08 14:58:22Functions:101069.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.cc -
0.0%
-
0.0 %0 / 120.0 %0 / 7
pointing.cc -
0.0%
-
0.0 %0 / 210.0 %0 / 5
geom_utils.cc -
0.0%
-
0.0 %0 / 250.0 %0 / 3
healpix_base.cc -
15.3%15.3%
-
15.3 %112 / 73411.0 %10 / 91
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/index.html b/doc/coverageReport/libs/healpix_base/index.html deleted file mode 100644 index 5078da2bf..000000000 --- a/doc/coverageReport/libs/healpix_base/index.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_baseHitTotalCoverage
Test:coverage.info.cleanedLines:11279214.1 %
Date:2024-04-08 14:58:22Functions:101069.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
error_handling.cc -
0.0%
-
0.0 %0 / 120.0 %0 / 7
geom_utils.cc -
0.0%
-
0.0 %0 / 250.0 %0 / 3
healpix_base.cc -
15.3%15.3%
-
15.3 %112 / 73411.0 %10 / 91
pointing.cc -
0.0%
-
0.0 %0 / 210.0 %0 / 5
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html b/doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html deleted file mode 100644 index 4499d9636..000000000 --- a/doc/coverageReport/libs/healpix_base/pointing.cc.func-sort-c.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/pointing.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - pointing.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:050.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8pointing15normalize_thetaEv0
_ZN7healpix8pointing9from_vec3ERKNS_6vec3_tIdEE0
_ZN7healpix8pointing9normalizeEv0
_ZN7healpixlsERSoRKNS_8pointingE0
_ZNK7healpix8pointing7to_vec3Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/pointing.cc.func.html b/doc/coverageReport/libs/healpix_base/pointing.cc.func.html deleted file mode 100644 index 473f90349..000000000 --- a/doc/coverageReport/libs/healpix_base/pointing.cc.func.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/pointing.cc - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - pointing.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:050.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7healpix8pointing15normalize_thetaEv0
_ZN7healpix8pointing9from_vec3ERKNS_6vec3_tIdEE0
_ZN7healpix8pointing9normalizeEv0
_ZN7healpixlsERSoRKNS_8pointingE0
_ZNK7healpix8pointing7to_vec3Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html b/doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html deleted file mode 100644 index 678a7db26..000000000 --- a/doc/coverageReport/libs/healpix_base/pointing.cc.gcov.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/healpix_base/pointing.cc - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/healpix_base - pointing.cc (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0210.0 %
Date:2024-04-08 14:58:22Functions:050.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /*
-       2             :  *  This file is part of libcxxsupport.
-       3             :  *
-       4             :  *  libcxxsupport is free software; you can redistribute it and/or modify
-       5             :  *  it under the terms of the GNU General Public License as published by
-       6             :  *  the Free Software Foundation; either version 2 of the License, or
-       7             :  *  (at your option) any later version.
-       8             :  *
-       9             :  *  libcxxsupport is distributed in the hope that it will be useful,
-      10             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      11             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      12             :  *  GNU General Public License for more details.
-      13             :  *
-      14             :  *  You should have received a copy of the GNU General Public License
-      15             :  *  along with libcxxsupport; if not, write to the Free Software
-      16             :  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
-      17             :  */
-      18             : 
-      19             : /*
-      20             :  *  libcxxsupport is being developed at the Max-Planck-Institut fuer Astrophysik
-      21             :  *  and financially supported by the Deutsches Zentrum fuer Luft- und Raumfahrt
-      22             :  *  (DLR).
-      23             :  */
-      24             : 
-      25             : /*! \file pointing.cc
-      26             :  *  Class representing a direction in 3D space
-      27             :  *
-      28             :  *  Copyright (C) 2003-2012 Max-Planck-Society
-      29             :  *  \author Martin Reinecke
-      30             :  */
-      31             : 
-      32             : #include "healpix_base/pointing.h"
-      33             : #include "healpix_base/lsconstants.h"
-      34             : #include "healpix_base/math_utils.h"
-      35             : 
-      36             : namespace healpix{
-      37             : 
-      38             : using namespace std;
-      39             : 
-      40           0 : vec3 pointing::to_vec3() const
-      41             :   {
-      42           0 :   double st=sin(theta);
-      43           0 :   return vec3 (st*cos(phi), st*sin(phi), cos(theta));
-      44             :   }
-      45           0 : void pointing::from_vec3 (const vec3 &inp)
-      46             :   {
-      47           0 :   theta = atan2(sqrt(inp.x*inp.x+inp.y*inp.y),inp.z);
-      48           0 :   phi = safe_atan2 (inp.y,inp.x);
-      49           0 :   if (phi<0.) phi += twopi;
-      50           0 :   }
-      51           0 : void pointing::normalize_theta()
-      52             :   {
-      53           0 :   theta=fmodulo(theta,twopi);
-      54           0 :   if (theta>pi)
-      55             :     {
-      56           0 :     phi+=pi;
-      57           0 :     theta=twopi-theta;
-      58             :     }
-      59           0 :   }
-      60           0 : void pointing::normalize()
-      61             :   {
-      62           0 :   normalize_theta();
-      63           0 :   phi=fmodulo(phi,twopi);
-      64           0 :   }
-      65             : 
-      66           0 : ostream &operator<< (ostream &os, const pointing &p)
-      67             :   {
-      68           0 :   os << p.theta << ", " << p.phi << std::endl;
-      69           0 :   return os;
-      70             :   }
-      71             : } // namespace healpix
-      72             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html b/doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html deleted file mode 100644 index 3091b54e8..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/convert.h.func-sort-c.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss/convert.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kiss - convert.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:71070.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss3strIiEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKT_2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html b/doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html deleted file mode 100644 index df4061a5f..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/convert.h.func.html +++ /dev/null @@ -1,76 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss/convert.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kiss - convert.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:71070.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- -
- - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss3strIiEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKT_2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html b/doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html deleted file mode 100644 index 6a912c12a..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/convert.h.gcov.html +++ /dev/null @@ -1,150 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss/convert.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kiss - convert.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:71070.0 %
Date:2024-04-08 14:58:22Functions:11100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef KISS_CONVERT_H
-       2             : #define KISS_CONVERT_H
-       3             : 
-       4             : #include <iostream>
-       5             : #include <sstream>
-       6             : #include <string>
-       7             : #include <typeinfo>
-       8             : #include <stdexcept>
-       9             : 
-      10             : namespace kiss {
-      11             : 
-      12             : class bad_conversion: public std::runtime_error {
-      13             : public:
-      14           0 :         bad_conversion(std::string const& s) :
-      15           0 :                         std::runtime_error(s) {
-      16             :         }
-      17             : };
-      18             : 
-      19             : template<typename T>
-      20           2 : inline std::string str(T const& x) {
-      21           2 :         std::ostringstream o;
-      22           2 :         o.imbue(std::locale("C"));
-      23           2 :         o << x;
-      24           2 :         if (!o) {
-      25             : #ifdef DEBUG
-      26             :                 std::cerr << "bad_conversion: str(" << typeid(x).name() << ")";
-      27             : #endif
-      28           0 :                 throw bad_conversion(std::string("str(") + typeid(x).name() + ")");
-      29             :         }
-      30           2 :         return o.str();
-      31           2 : }
-      32             : 
-      33             : template<typename T>
-      34             : inline void convert(const char *s, T& x) {
-      35             :         if (s == 0) {
-      36             : #ifdef DEBUG
-      37             :                 std::cerr << "bad_conversion: convert, null pointer";
-      38             : #endif
-      39             :                 throw bad_conversion("null pointer");
-      40             :         }
-      41             :         std::istringstream i(s);
-      42             :         i.imbue(std::locale("C"));
-      43             :         i >> x;
-      44             :         if (!i) {
-      45             : #ifdef DEBUG
-      46             :                 std::cerr << "bad_conversion: convert (" << s << ")";
-      47             : #endif
-      48             :                 throw bad_conversion(std::string(s) + " to " + typeid(x).name());
-      49             :         }
-      50             : }
-      51             : 
-      52             : template<typename T>
-      53             : inline void convert(std::string const& s, T& x) {
-      54             :         std::istringstream i(s);
-      55             :         i.imbue(std::locale("C"));
-      56             :         i >> x;
-      57             :         if (!i) {
-      58             : #ifdef DEBUG
-      59             :                 std::cerr << "bad_conversion: convert (" << s << ")";
-      60             : #endif
-      61             :                 throw bad_conversion(s + " to " + typeid(x).name());
-      62             :         }
-      63             : }
-      64             : 
-      65             : template<typename T>
-      66             : inline T convertTo(std::string const& s, bool failIfLeftoverChars = true) {
-      67             :         T x;
-      68             :         convert(s, x, failIfLeftoverChars);
-      69             :         return x;
-      70             : }
-      71             : 
-      72             : } // namespace kiss
-      73             : 
-      74             : #endif /* KISSCONVERT_H */
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html b/doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html deleted file mode 100644 index bb06075e7..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/index-sort-f.html +++ /dev/null @@ -1,103 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kissHitTotalCoverage
Test:coverage.info.cleanedLines:111957.9 %
Date:2024-04-08 14:58:22Functions:146720.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
logger.h -
44.4%44.4%
-
44.4 %4 / 919.7 %13 / 66
convert.h -
70.0%70.0%
-
70.0 %7 / 10100.0 %1 / 1
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html b/doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html deleted file mode 100644 index b047c279f..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/index-sort-l.html +++ /dev/null @@ -1,103 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kissHitTotalCoverage
Test:coverage.info.cleanedLines:111957.9 %
Date:2024-04-08 14:58:22Functions:146720.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
logger.h -
44.4%44.4%
-
44.4 %4 / 919.7 %13 / 66
convert.h -
70.0%70.0%
-
70.0 %7 / 10100.0 %1 / 1
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/index.html b/doc/coverageReport/libs/kiss/include/kiss/index.html deleted file mode 100644 index c4b160333..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/index.html +++ /dev/null @@ -1,103 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kissHitTotalCoverage
Test:coverage.info.cleanedLines:111957.9 %
Date:2024-04-08 14:58:22Functions:146720.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
convert.h -
70.0%70.0%
-
70.0 %7 / 10100.0 %1 / 1
logger.h -
44.4%44.4%
-
44.4 %4 / 919.7 %13 / 66
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html b/doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html deleted file mode 100644 index 35772c48a..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/logger.h.func-sort-c.html +++ /dev/null @@ -1,336 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss/logger.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kiss - logger.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4944.4 %
Date:2024-04-08 14:58:22Functions:136619.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6LoggerlsEPFRSoS1_E0
_ZN4kiss6LoggerlsIA11_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA12_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA135_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA14_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA156_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA15_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA16_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA18_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA197_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA231_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA23_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA256_cEERS0_RT_0
_ZN4kiss6LoggerlsIA25_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA26_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA27_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA33_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA34_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA35_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA39_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA40_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA41_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA42_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA46_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA47_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA49_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA53_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA54_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA55_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA69_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA6_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA70_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA71_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA72_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA73_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA74_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA75_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA81_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA82_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA83_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA8_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA93_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA9_KcEERS0_RT_0
_ZN4kiss6LoggerlsIKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIKbEERS0_RT_0
_ZN4kiss6LoggerlsIKiEERS0_RT_0
_ZN4kiss6LoggerlsIKmEERS0_RT_0
_ZN4kiss6LoggerlsIN7crpropa7Vector3IdEEEERS0_RT_0
_ZN4kiss6LoggerlsINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIbEERS0_RT_0
_ZN4kiss6LoggerlsIdEERS0_RT_0
_ZN4kiss6LoggerlsImEERS0_RT_0
_ZN4kiss6LoggerlsIyEERS0_RT_0
_ZN4kiss6LoggerlsIA166_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA3_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA59_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA5_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA7_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA2_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA58_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA64_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA67_KcEERS0_RT_2
_ZN4kiss6LoggerlsIiEERS0_RT_2
_ZN4kiss6LoggerlsIA51_KcEERS0_RT_3
_ZN4kiss6LoggerlsIA131_KcEERS0_RT_4
_ZN4kiss6LoggerlsIA50_KcEERS0_RT_4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html b/doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html deleted file mode 100644 index 1f4061bc2..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/logger.h.func.html +++ /dev/null @@ -1,336 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss/logger.h - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kiss - logger.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4944.4 %
Date:2024-04-08 14:58:22Functions:136619.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6LoggerlsEPFRSoS1_E0
_ZN4kiss6LoggerlsIA11_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA12_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA131_KcEERS0_RT_4
_ZN4kiss6LoggerlsIA135_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA14_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA156_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA15_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA166_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA16_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA18_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA197_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA231_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA23_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA256_cEERS0_RT_0
_ZN4kiss6LoggerlsIA25_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA26_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA27_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA2_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA33_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA34_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA35_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA39_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA3_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA40_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA41_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA42_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA46_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA47_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA49_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA50_KcEERS0_RT_4
_ZN4kiss6LoggerlsIA51_KcEERS0_RT_3
_ZN4kiss6LoggerlsIA53_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA54_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA55_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA58_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA59_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA5_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA64_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA67_KcEERS0_RT_2
_ZN4kiss6LoggerlsIA69_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA6_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA70_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA71_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA72_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA73_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA74_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA75_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA7_KcEERS0_RT_1
_ZN4kiss6LoggerlsIA81_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA82_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA83_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA8_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA93_KcEERS0_RT_0
_ZN4kiss6LoggerlsIA9_KcEERS0_RT_0
_ZN4kiss6LoggerlsIKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIKbEERS0_RT_0
_ZN4kiss6LoggerlsIKiEERS0_RT_0
_ZN4kiss6LoggerlsIKmEERS0_RT_0
_ZN4kiss6LoggerlsIN7crpropa7Vector3IdEEEERS0_RT_0
_ZN4kiss6LoggerlsINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEEERS0_RT_0
_ZN4kiss6LoggerlsIbEERS0_RT_0
_ZN4kiss6LoggerlsIdEERS0_RT_0
_ZN4kiss6LoggerlsIiEERS0_RT_2
_ZN4kiss6LoggerlsImEERS0_RT_0
_ZN4kiss6LoggerlsIyEERS0_RT_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html b/doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html deleted file mode 100644 index a7402eee3..000000000 --- a/doc/coverageReport/libs/kiss/include/kiss/logger.h.gcov.html +++ /dev/null @@ -1,131 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/include/kiss/logger.h - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/include/kiss - logger.h (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4944.4 %
Date:2024-04-08 14:58:22Functions:136619.7 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifndef KISS_LOG_H
-       2             : #define KISS_LOG_H
-       3             : 
-       4             : #include <iostream>
-       5             : 
-       6             : namespace kiss {
-       7             : 
-       8             : enum eLogLevel {
-       9             :         LOG_LEVEL_ERROR, LOG_LEVEL_WARNING, LOG_LEVEL_INFO, LOG_LEVEL_DEBUG
-      10             : };
-      11             : 
-      12             : class Logger {
-      13             :         static std::ostream *stream;
-      14             :         static eLogLevel level;
-      15             : public:
-      16             :         Logger(eLogLevel level);
-      17             :         ~Logger();
-      18             :         static std::ostream &getLogStream();
-      19             :         static void setLogStream(std::ostream *s);
-      20             :         static void setLogStream(std::ostream &s);
-      21             : 
-      22             :         static void setLogLevel(eLogLevel level);
-      23             :         static eLogLevel getLogLevel();
-      24             : 
-      25             :         static void loadEnvLogLevel();
-      26             : 
-      27             :         operator std::ostream &() {
-      28           0 :                 return getLogStream();
-      29             :         }
-      30             : 
-      31          26 :         template<typename T> inline Logger& operator<<(T& data) {
-      32          52 :                 #pragma omp critical (KISS_LOGGER)
-      33             :                 {
-      34          26 :                 getLogStream() << data;
-      35             :                 }
-      36          26 :                 return *this;
-      37             :         }
-      38             : 
-      39           0 :         inline Logger& operator<<(std::ostream& (*func)(std::ostream&)) {
-      40           0 :                 #pragma omp critical (KISS_LOGGER)
-      41             :                 {
-      42           0 :                 getLogStream() << func;
-      43             :                 }
-      44           0 :                 return *this;
-      45             :         }
-      46             : };
-      47             : 
-      48             : } // namespace kiss
-      49             : 
-      50             : #define KISS_LOG_ERROR if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_ERROR) {} else kiss::Logger(kiss::LOG_LEVEL_ERROR)
-      51             : #define KISS_LOG_WARNING if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_WARNING) {} else kiss::Logger(kiss::LOG_LEVEL_WARNING)
-      52             : #define KISS_LOG_INFO if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_INFO) {} else kiss::Logger(kiss::LOG_LEVEL_INFO)
-      53             : #define KISS_LOG_DEBUG if (kiss::Logger::getLogLevel() < kiss::LOG_LEVEL_DEBUG) {} else kiss::Logger(kiss::LOG_LEVEL_DEBUG)
-      54             : 
-      55             : #endif /* KISSLOG_H */
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/index-sort-f.html b/doc/coverageReport/libs/kiss/src/index-sort-f.html deleted file mode 100644 index ec409f400..000000000 --- a/doc/coverageReport/libs/kiss/src/index-sort-f.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/srcHitTotalCoverage
Test:coverage.info.cleanedLines:3412128.1 %
Date:2024-04-08 14:58:22Functions:92339.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
string.cpp -
14.8%14.8%
-
14.8 %4 / 2714.3 %1 / 7
path.cpp -
24.5%24.5%
-
24.5 %13 / 5337.5 %3 / 8
logger.cpp -
41.5%41.5%
-
41.5 %17 / 4162.5 %5 / 8
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/index-sort-l.html b/doc/coverageReport/libs/kiss/src/index-sort-l.html deleted file mode 100644 index 4cac3f96c..000000000 --- a/doc/coverageReport/libs/kiss/src/index-sort-l.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/srcHitTotalCoverage
Test:coverage.info.cleanedLines:3412128.1 %
Date:2024-04-08 14:58:22Functions:92339.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
string.cpp -
14.8%14.8%
-
14.8 %4 / 2714.3 %1 / 7
path.cpp -
24.5%24.5%
-
24.5 %13 / 5337.5 %3 / 8
logger.cpp -
41.5%41.5%
-
41.5 %17 / 4162.5 %5 / 8
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/index.html b/doc/coverageReport/libs/kiss/src/index.html deleted file mode 100644 index d44e18167..000000000 --- a/doc/coverageReport/libs/kiss/src/index.html +++ /dev/null @@ -1,113 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/srcHitTotalCoverage
Test:coverage.info.cleanedLines:3412128.1 %
Date:2024-04-08 14:58:22Functions:92339.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
logger.cpp -
41.5%41.5%
-
41.5 %17 / 4162.5 %5 / 8
path.cpp -
24.5%24.5%
-
24.5 %13 / 5337.5 %3 / 8
string.cpp -
14.8%14.8%
-
14.8 %4 / 2714.3 %1 / 7
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html b/doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html deleted file mode 100644 index a72ea02f2..000000000 --- a/doc/coverageReport/libs/kiss/src/logger.cpp.func-sort-c.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/logger.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - logger.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:174141.5 %
Date:2024-04-08 14:58:22Functions:5862.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6Logger11setLogLevelENS_9eLogLevelE0
_ZN4kiss6Logger12setLogStreamEPSo0
_ZN4kiss6Logger12setLogStreamERSo0
_ZN4kiss6LoggerC2ENS_9eLogLevelE12
_ZN4kiss6LoggerD2Ev12
_ZN4kiss6Logger15loadEnvLogLevelEv19
_ZN4kiss6Logger12getLogStreamEv26
_ZN4kiss6Logger11getLogLevelEv290
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/logger.cpp.func.html b/doc/coverageReport/libs/kiss/src/logger.cpp.func.html deleted file mode 100644 index c740d5ca4..000000000 --- a/doc/coverageReport/libs/kiss/src/logger.cpp.func.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/logger.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - logger.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:174141.5 %
Date:2024-04-08 14:58:22Functions:5862.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss6Logger11getLogLevelEv290
_ZN4kiss6Logger11setLogLevelENS_9eLogLevelE0
_ZN4kiss6Logger12getLogStreamEv26
_ZN4kiss6Logger12setLogStreamEPSo0
_ZN4kiss6Logger12setLogStreamERSo0
_ZN4kiss6Logger15loadEnvLogLevelEv19
_ZN4kiss6LoggerC2ENS_9eLogLevelE12
_ZN4kiss6LoggerD2Ev12
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html b/doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html deleted file mode 100644 index 212278290..000000000 --- a/doc/coverageReport/libs/kiss/src/logger.cpp.gcov.html +++ /dev/null @@ -1,161 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/logger.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - logger.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:174141.5 %
Date:2024-04-08 14:58:22Functions:5862.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "kiss/logger.h"
-       2             : 
-       3             : #include <stdlib.h>
-       4             : #include <iostream>
-       5             : 
-       6             : namespace kiss {
-       7             : 
-       8             : std::ostream *Logger::stream = &std::cerr;
-       9             : eLogLevel Logger::level = LOG_LEVEL_WARNING;
-      10             : const char* sLoggerLevel[] = { " ERROR ", "WARNING", " INFO  ", " DEBUG " };
-      11             : 
-      12             : class EnvLogger {
-      13             : public:
-      14             :         EnvLogger() {
-      15             :                 Logger::loadEnvLogLevel();
-      16             :         }
-      17             : };
-      18             : static EnvLogger _env_log_;
-      19             : 
-      20          12 : Logger::Logger(eLogLevel level) {
-      21             :         time_t rawtime;
-      22             :         struct tm * timeinfo;
-      23             :         char buffer[80];
-      24             : 
-      25          12 :         time(&rawtime);
-      26          12 :         timeinfo = localtime(&rawtime);
-      27             : 
-      28          12 :         strftime(buffer, 80, "%Y-%m-%d %H:%M:%S ", timeinfo);
-      29          12 :         *stream << buffer;
-      30          12 :         *stream << "[" << sLoggerLevel[level] << "] ";
-      31          12 : }
-      32             : 
-      33          12 : Logger::~Logger() {
-      34          12 :         *stream << std::endl;
-      35          12 : }
-      36             : 
-      37          26 : std::ostream &Logger::getLogStream() {
-      38          26 :         return (*stream);
-      39             : }
-      40             : 
-      41           0 : void Logger::setLogStream(std::ostream *s) {
-      42           0 :         stream = s;
-      43           0 : }
-      44             : 
-      45           0 : void Logger::setLogStream(std::ostream &s) {
-      46           0 :         stream = &s;
-      47           0 : }
-      48             : 
-      49           0 : void Logger::setLogLevel(eLogLevel l) {
-      50           0 :         level = l;
-      51           0 : }
-      52         290 : eLogLevel Logger::getLogLevel() {
-      53         290 :         return (level);
-      54             : }
-      55             : 
-      56             : 
-      57             : 
-      58             : 
-      59          19 : void Logger::loadEnvLogLevel() {
-      60          19 :         if (::getenv("KISS_LOG_LEVEL")) {
-      61             :                 
-      62           0 :                 int level = atoi(::getenv("KISS_LOG_LEVEL"));
-      63           0 :                 switch (level) {
-      64           0 :                 case LOG_LEVEL_ERROR:
-      65           0 :                         Logger::setLogLevel(LOG_LEVEL_ERROR);
-      66           0 :                         break;
-      67           0 :                 case LOG_LEVEL_WARNING:
-      68           0 :                         Logger::setLogLevel(LOG_LEVEL_WARNING);
-      69           0 :                         break;
-      70           0 :                 case LOG_LEVEL_INFO:
-      71           0 :                         Logger::setLogLevel(LOG_LEVEL_INFO);
-      72           0 :                         break;
-      73           0 :                 case LOG_LEVEL_DEBUG:
-      74           0 :                         Logger::setLogLevel(LOG_LEVEL_DEBUG);
-      75           0 :                         break;
-      76             :                 default:
-      77             :                         std::cerr << "kiss::Logger: unknown log level in KISS_LOG_LEVEL '"
-      78           0 :                                         << level << " values from 0-3 expected." << std::endl;
-      79             :                         break;
-      80             :                 }
-      81             :         }
-      82          19 : }
-      83             : 
-      84             : } // namespace kiss
-      85             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html b/doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html deleted file mode 100644 index 496484b29..000000000 --- a/doc/coverageReport/libs/kiss/src/path.cpp.func-sort-c.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/path.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - path.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:135324.5 %
Date:2024-04-08 14:58:22Functions:3837.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_Z11append_fileRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_b0
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_S6_0
_Z14list_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS4_SaIS4_EE0
_Z16create_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
_Z26create_directory_recursiveRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
_Z15executable_pathB5cxx11v13
_Z12is_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE26
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_547
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/path.cpp.func.html b/doc/coverageReport/libs/kiss/src/path.cpp.func.html deleted file mode 100644 index e354ac988..000000000 --- a/doc/coverageReport/libs/kiss/src/path.cpp.func.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/path.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - path.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:135324.5 %
Date:2024-04-08 14:58:22Functions:3837.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_Z11append_fileRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_b0
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_547
_Z11concat_pathRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_S6_0
_Z12is_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE26
_Z14list_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS4_SaIS4_EE0
_Z15executable_pathB5cxx11v13
_Z16create_directoryRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
_Z26create_directory_recursiveRKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEmmm0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/path.cpp.gcov.html b/doc/coverageReport/libs/kiss/src/path.cpp.gcov.html deleted file mode 100644 index 7cc7b933a..000000000 --- a/doc/coverageReport/libs/kiss/src/path.cpp.gcov.html +++ /dev/null @@ -1,245 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/path.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - path.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:135324.5 %
Date:2024-04-08 14:58:22Functions:3837.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "kiss/path.h"
-       2             : 
-       3             : #ifdef WIN32
-       4             : #  include "windows.h"
-       5             : #  ifndef S_ISREG
-       6             : #    define S_ISREG(x) (((x) & S_IFMT) == S_IFREG)
-       7             : #  endif
-       8             : #  ifndef S_ISDIR
-       9             : #    define S_ISDIR(x) (((x) & S_IFMT) == S_IFDIR)
-      10             : #  endif
-      11             : #  include "sys/stat.h"
-      12             : #else
-      13             : #include <sys/types.h>
-      14             : #include <fcntl.h>
-      15             : #include <unistd.h>
-      16             : #include <dirent.h>
-      17             : #include "sys/stat.h"
-      18             : #endif
-      19             : 
-      20             : #include <stdexcept>
-      21             : #include <cstdio>
-      22             : 
-      23           0 : bool create_directory(const std::string &path, size_t user_permission,
-      24             :                 size_t group_permission, size_t other_permission) {
-      25             : #ifdef WIN32
-      26             :         BOOL result = ::CreateDirectoryA(path.c_str(), 0);
-      27             :         return result == TRUE;
-      28             : #else
-      29             :         mode_t m = 0;
-      30           0 :         m |= (user_permission << 6);
-      31           0 :         m |= (group_permission << 3);
-      32           0 :         m |= (other_permission << 0);
-      33           0 :         int result = mkdir(path.c_str(), m);
-      34           0 :         return (result == 0);
-      35             : #endif
-      36             : }
-      37             : 
-      38          26 : bool is_directory(const std::string &path) {
-      39             : #ifdef WIN32
-      40             :         struct _stat buf;
-      41             :         int result = _stat(path.c_str(), &buf);
-      42             :         if (result == 0 && S_ISDIR(buf.st_mode))
-      43             :                 return true;
-      44             :         else
-      45             :                 return false;
-      46             : #else
-      47             :         struct stat buf;
-      48          26 :         int result = stat(path.c_str(), &buf);
-      49          26 :         if (result == 0 && S_ISDIR(buf.st_mode))
-      50             :         return true;
-      51             :         else
-      52          26 :         return false;
-      53             : #endif
-      54             : }
-      55             : 
-      56           0 : bool list_directory(const std::string &directory,
-      57             :                 std::vector<std::string> &elements) {
-      58             : #ifdef WIN32
-      59             :         WIN32_FIND_DATA findData;
-      60             :         HANDLE hFind = FindFirstFileA((directory + "\\*.*").c_str(), &findData);
-      61             :         if (hFind == INVALID_HANDLE_VALUE)
-      62             :                 throw std::runtime_error("Failed to get directory list");
-      63             :         for (;;) {
-      64             :                 if (findData.cFileName[0] != '.') {
-      65             :                         elements.push_back(findData.cFileName);
-      66             :                 }
-      67             :                 if (FindNextFileA(hFind, &findData) == 0)
-      68             :                         break;
-      69             :         }
-      70             :         FindClose(hFind);
-      71             : #else
-      72           0 :         DIR* dir = opendir(directory.c_str());
-      73           0 :         if (dir == NULL)
-      74             :         return false;
-      75             :         dirent* entry;
-      76           0 :         while ((entry = readdir(dir)) != NULL) {
-      77           0 :                 if (entry->d_name[0] != '.') {
-      78           0 :                         elements.push_back(entry->d_name);
-      79             :                 }
-      80             :         }
-      81           0 :         closedir(dir);
-      82             : #endif
-      83           0 :         return true;
-      84             : }
-      85             : 
-      86           0 : bool create_directory_recursive(const std::string &dir, size_t user_permission,
-      87             :                 size_t group_permission, size_t other_permission) {
-      88             :         // split path
-      89           0 :         const char seperators[] = "\\/";
-      90             :         std::vector<std::string> elements;
-      91             :         std::string::size_type a, b;
-      92             :         a = dir.find_first_not_of(seperators), b = dir.find_first_of(seperators, a);
-      93           0 :         while (a != std::string::npos) {
-      94           0 :                 elements.push_back(dir.substr(a, b - a));
-      95             :                 a = dir.find_first_not_of(seperators, b), b = dir.find_first_of(
-      96             :                                 seperators, a);
-      97             :         }
-      98             : 
-      99             :         // create all non existing parts
-     100             :         std::string path;
-     101           0 :         for (size_t i = 0; i < elements.size(); i++) {
-     102             :                 path += elements[i];
-     103             :                 path += path_seperator;
-     104           0 :                 if (is_directory(path) == false)
-     105           0 :                         create_directory(path);
-     106             :         }
-     107             : 
-     108           0 :         return is_directory(dir);
-     109           0 : }
-     110             : 
-     111         547 : std::string concat_path(const std::string &a, const std::string &b) {
-     112         547 :         char last = *a.rbegin();
-     113         547 :         if (last == '\\' || last == '/')
-     114           0 :                 return a + b;
-     115             :         else
-     116        1094 :                 return a + path_seperator + b;
-     117             : 
-     118             : }
-     119             : 
-     120           0 : std::string concat_path(const std::string &a, const std::string &b,
-     121             :                 const std::string &c) {
-     122             :         std::string p = a;
-     123           0 :         if (*p.rbegin() != '\\' && *p.rbegin() != '/')
-     124             :                 p += path_seperator;
-     125             :         p += b;
-     126           0 :         if (*p.rbegin() != '\\' && *p.rbegin() != '/')
-     127             :                 p += path_seperator;
-     128             :         p += c;
-     129           0 :         return p;
-     130             : }
-     131             : 
-     132           0 : void append_file(const std::string &target, const std::string &source,
-     133             :                 bool binary) {
-     134           0 :         FILE *t = fopen(target.c_str(), binary ? "wb+" : "w+");
-     135           0 :         if (t == NULL)
-     136           0 :                 return;
-     137             : 
-     138           0 :         FILE *s = fopen(source.c_str(), binary ? "rb" : "r");
-     139           0 :         if (s == NULL) {
-     140           0 :                 fclose(t);
-     141           0 :                 return;
-     142             :         }
-     143             : 
-     144             :         size_t size = 0;
-     145             :         char buffer[1 << 20];
-     146           0 :         while ((size = fread(buffer, 1, sizeof(buffer), s)) > 0) {
-     147           0 :                 fwrite(buffer, 1, size, t);
-     148             :         }
-     149             : 
-     150           0 :         fclose(t);
-     151           0 :         fclose(s);
-     152             : }
-     153             : 
-     154          13 : std::string executable_path() {
-     155             :         char buf[1024];
-     156             : 
-     157             : //#if linux
-     158          13 :         size_t len = readlink("/proc/self/exe", buf, sizeof(buf)-1);
-     159             : //#else
-     160             : //      size_t len = ::GetModuleFileName(NULL, buf, sizeof(buf)-1 );
-     161             : //#endif
-     162         192 :         for (size_t i = 1; i < len; i++) {
-     163         189 :                 if (buf[len - 1] == path_seperator)
-     164             :                         break;
-     165             :                 else
-     166             :                         len --;
-     167             :         }
-     168          13 :         return std::string(buf, len);
-     169             : }
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html b/doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html deleted file mode 100644 index 43fcf0d21..000000000 --- a/doc/coverageReport/libs/kiss/src/string.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/string.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - string.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:42714.8 %
Date:2024-04-08 14:58:22Functions:1714.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss10trim_rightERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss11starts_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss4trimERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss7explodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS5_SaIS5_EEbS7_0
_ZN4kiss7implodeERKSt6vectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESaIS6_EERKS6_0
_ZN4kiss9trim_leftERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss9ends_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/string.cpp.func.html b/doc/coverageReport/libs/kiss/src/string.cpp.func.html deleted file mode 100644 index a35b5f6ae..000000000 --- a/doc/coverageReport/libs/kiss/src/string.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/string.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - string.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:42714.8 %
Date:2024-04-08 14:58:22Functions:1714.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN4kiss10trim_rightERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss11starts_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss4trimERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
_ZN4kiss7explodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERSt6vectorIS5_SaIS5_EEbS7_0
_ZN4kiss7implodeERKSt6vectorINSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESaIS6_EERKS6_0
_ZN4kiss9ends_withERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_3
_ZN4kiss9trim_leftERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES7_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/libs/kiss/src/string.cpp.gcov.html b/doc/coverageReport/libs/kiss/src/string.cpp.gcov.html deleted file mode 100644 index af1671ddc..000000000 --- a/doc/coverageReport/libs/kiss/src/string.cpp.gcov.html +++ /dev/null @@ -1,165 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - libs/kiss/src/string.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - libs/kiss/src - string.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:42714.8 %
Date:2024-04-08 14:58:22Functions:1714.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "kiss/string.h"
-       2             : 
-       3             : #include <iostream>
-       4             : #include <string>
-       5             : #include <vector>
-       6             : 
-       7             : namespace kiss {
-       8             : 
-       9           0 : std::string trim_right(const std::string &s, const std::string &t) {
-      10             :         std::string::size_type i(s.find_last_not_of(t));
-      11             : 
-      12           0 :         if (i == std::string::npos)
-      13           0 :                 return "";
-      14             :         else
-      15           0 :                 return std::string(s, 0, i);
-      16             : }
-      17             : 
-      18           0 : std::string trim_left(const std::string &s, const std::string &t) {
-      19           0 :         return std::string(s, s.find_first_not_of(t));
-      20             : }
-      21             : 
-      22           0 : std::string trim(const std::string &s, const std::string &t) {
-      23             :         std::string::size_type a = s.find_first_not_of(t);
-      24             :         std::string::size_type b = s.find_last_not_of(t);
-      25             : 
-      26           0 :         if (a == std::string::npos || b == std::string::npos)
-      27           0 :                 return "";
-      28             : 
-      29           0 :         return std::string(s, a, b - a + 1);
-      30             : }
-      31             : 
-      32           0 : void explode(const std::string &s, std::vector<std::string> &v,
-      33             :                 const bool trim_spaces, const std::string &t) {
-      34             :         std::string::size_type a, b;
-      35             : 
-      36             :         a = s.find_first_not_of(t), b = s.find_first_of(t, a);
-      37             : 
-      38           0 :         while (a != std::string::npos) {
-      39           0 :                 if (trim_spaces)
-      40           0 :                         v.push_back(trim(s.substr(a, b - a)));
-      41             :                 else
-      42           0 :                         v.push_back(s.substr(a, b - a));
-      43             : 
-      44             :                 a = s.find_first_not_of(t, b), b = s.find_first_of(t, a);
-      45             :         }
-      46           0 : }
-      47             : 
-      48           0 : std::string implode(const std::vector<std::string> &v, const std::string &t) {
-      49             :         unsigned int i;
-      50             :         std::string s;
-      51             : 
-      52           0 :         for (i = 0; i < (v.size() - 1); i++) {
-      53             :                 s.append(v[i]);
-      54             :                 s.append(t);
-      55             :         }
-      56             : 
-      57           0 :         return s + v[i];
-      58             : }
-      59             : 
-      60           3 : bool ends_with(const std::string &s, const std::string &w) {
-      61           3 :         if (s.size() < w.size())
-      62             :                 return false;
-      63             :         std::string::const_reverse_iterator si = s.rbegin();
-      64             :         std::string::const_reverse_iterator wi = w.rbegin();
-      65           3 :         while (wi != w.rend()) {
-      66           3 :                 if (*wi != *si)
-      67             :                         return false;
-      68             :                 wi++;
-      69             :                 si++;
-      70             :         }
-      71             : 
-      72             :         return true;
-      73             : }
-      74             : 
-      75           0 : bool starts_with(const std::string &s, const std::string &w) {
-      76           0 :         if (s.size() < w.size())
-      77             :                 return false;
-      78             :         std::string::const_iterator si = s.begin();
-      79             :         std::string::const_iterator wi = w.begin();
-      80           0 :         while (wi != w.end()) {
-      81           0 :                 if (*wi != *si)
-      82             :                         return false;
-      83             :                 wi++;
-      84             :                 si++;
-      85             :         }
-      86             :         return true;
-      87             : }
-      88             : 
-      89             : } // namespace kiss
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/ruby.png b/doc/coverageReport/ruby.png deleted file mode 100644 index 991b6d4ec9e78be165e3ef757eed1aada287364d..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 141 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)ga>?NMQuI!iC1^FceV#7`HfI^%F z9+AZi4BSE>%y{W;-5;PJOS+@4BLl<6e(pbstUx|nfKQ0)e^Y%R^MdiLxj>4`)5S5Q b;#P73kj=!v_*DHKNFRfztDnm{r-UW|iOwIS diff --git a/doc/coverageReport/snow.png b/doc/coverageReport/snow.png deleted file mode 100644 index 2cdae107fceec6e7f02ac7acb4a34a82a540caa5..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 141 zcmeAS@N?(olHy`uVBq!ia0vp^j3CU&3?x-=hn)ga>?NMQuI!iC1^MM!lvI6;R0X`wF|Ns97GD8ntt^-nBo-U3d c6}OTTfNUlP#;5A{K>8RwUHx3vIVCg!071?oo&W#< diff --git a/doc/coverageReport/src/Candidate.cpp.func-sort-c.html b/doc/coverageReport/src/Candidate.cpp.func-sort-c.html deleted file mode 100644 index b34d8b8c1..000000000 --- a/doc/coverageReport/src/Candidate.cpp.func-sort-c.html +++ /dev/null @@ -1,212 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Candidate.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Candidate.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12914787.8 %
Date:2024-04-08 14:58:22Functions:333594.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Candidate16clearSecondariesEv0
_ZNK7crpropa9Candidate14getDescriptionB5cxx11Ev0
_ZN7crpropa9Candidate19setNextSerialNumberEm1
_ZN7crpropa9Candidate7restartEv1
_ZN7crpropa9Candidate12addSecondaryEiddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa9Candidate12addSecondaryEPS0_4
_ZN7crpropa9Candidate12updateWeightEd5
_ZN7crpropa9Candidate14removePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE5
_ZN7crpropa9Candidate19getNextSerialNumberEv6
_ZN7crpropa9Candidate15setSerialNumberEm11
_ZNK7crpropa9Candidate11getPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE11
_ZN7crpropa9CandidateC2ERKNS_13ParticleStateE20
_ZNK7crpropa9Candidate11hasPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE30
_ZNK7crpropa9Candidate5cloneEb30
_ZNK7crpropa9Candidate22getCreatedSerialNumberEv48
_ZNK7crpropa9Candidate21getSourceSerialNumberEv49
_ZNK7crpropa9Candidate12getTagOriginB5cxx11Ev61
_ZNK7crpropa9Candidate15getSerialNumberEv84
_ZNK7crpropa9Candidate9getWeightEv1064
_ZN7crpropa9Candidate11setPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantE1143
_ZN7crpropa9Candidate9setActiveEb1742
_ZNK7crpropa9Candidate8isActiveEv21336
_ZNK7crpropa9Candidate14getCurrentStepEv63001
_ZNK7crpropa9Candidate11getNextStepEv499385
_ZN7crpropa9Candidate11setNextStepEd499400
_ZN7crpropa9Candidate14setCurrentStepEd501076
_ZNK7crpropa9Candidate11getRedshiftEv529541
_ZN7crpropa9Candidate13limitNextStepEd530052
_ZNK7crpropa9Candidate19getTrajectoryLengthEv1011718
_ZN7crpropa9Candidate12addSecondaryEidNS_7Vector3IdEEdNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324908
_ZN7crpropa9Candidate12setTagOriginENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324912
_ZN7crpropa9Candidate19setTrajectoryLengthEd3324939
_ZN7crpropa9Candidate9setWeightEd3325923
_ZN7crpropa9Candidate11setRedshiftEd3332752
_ZN7crpropa9CandidateC2EidNS_7Vector3IdEES2_ddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3368851
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Candidate.cpp.func.html b/doc/coverageReport/src/Candidate.cpp.func.html deleted file mode 100644 index 4a0c5e726..000000000 --- a/doc/coverageReport/src/Candidate.cpp.func.html +++ /dev/null @@ -1,212 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Candidate.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Candidate.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12914787.8 %
Date:2024-04-08 14:58:22Functions:333594.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Candidate11setNextStepEd499400
_ZN7crpropa9Candidate11setPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantE1143
_ZN7crpropa9Candidate11setRedshiftEd3332752
_ZN7crpropa9Candidate12addSecondaryEPS0_4
_ZN7crpropa9Candidate12addSecondaryEidNS_7Vector3IdEEdNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324908
_ZN7crpropa9Candidate12addSecondaryEiddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa9Candidate12setTagOriginENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3324912
_ZN7crpropa9Candidate12updateWeightEd5
_ZN7crpropa9Candidate13limitNextStepEd530052
_ZN7crpropa9Candidate14removePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE5
_ZN7crpropa9Candidate14setCurrentStepEd501076
_ZN7crpropa9Candidate15setSerialNumberEm11
_ZN7crpropa9Candidate16clearSecondariesEv0
_ZN7crpropa9Candidate19getNextSerialNumberEv6
_ZN7crpropa9Candidate19setNextSerialNumberEm1
_ZN7crpropa9Candidate19setTrajectoryLengthEd3324939
_ZN7crpropa9Candidate7restartEv1
_ZN7crpropa9Candidate9setActiveEb1742
_ZN7crpropa9Candidate9setWeightEd3325923
_ZN7crpropa9CandidateC2ERKNS_13ParticleStateE20
_ZN7crpropa9CandidateC2EidNS_7Vector3IdEES2_ddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE3368851
_ZNK7crpropa9Candidate11getNextStepEv499385
_ZNK7crpropa9Candidate11getPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE11
_ZNK7crpropa9Candidate11getRedshiftEv529541
_ZNK7crpropa9Candidate11hasPropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE30
_ZNK7crpropa9Candidate12getTagOriginB5cxx11Ev61
_ZNK7crpropa9Candidate14getCurrentStepEv63001
_ZNK7crpropa9Candidate14getDescriptionB5cxx11Ev0
_ZNK7crpropa9Candidate15getSerialNumberEv84
_ZNK7crpropa9Candidate19getTrajectoryLengthEv1011718
_ZNK7crpropa9Candidate21getSourceSerialNumberEv49
_ZNK7crpropa9Candidate22getCreatedSerialNumberEv48
_ZNK7crpropa9Candidate5cloneEb30
_ZNK7crpropa9Candidate8isActiveEv21336
_ZNK7crpropa9Candidate9getWeightEv1064
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Candidate.cpp.gcov.html b/doc/coverageReport/src/Candidate.cpp.gcov.html deleted file mode 100644 index 07a4b2a2a..000000000 --- a/doc/coverageReport/src/Candidate.cpp.gcov.html +++ /dev/null @@ -1,331 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Candidate.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Candidate.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12914787.8 %
Date:2024-04-08 14:58:22Functions:333594.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Candidate.h"
-       2             : #include "crpropa/ParticleID.h"
-       3             : #include "crpropa/Units.h"
-       4             : 
-       5             : #include <stdexcept>
-       6             : 
-       7             : namespace crpropa {
-       8             : 
-       9     3368851 : Candidate::Candidate(int id, double E, Vector3d pos, Vector3d dir, double z, double weight, std::string tagOrigin) :
-      10     3368851 :   redshift(z), trajectoryLength(0), weight(weight), currentStep(0), nextStep(0), active(true), parent(0), tagOrigin(tagOrigin) {
-      11     3368851 :         ParticleState state(id, E, pos, dir);
-      12             :         source = state;
-      13             :         created = state;
-      14             :         previous = state;
-      15             :         current = state;
-      16             : 
-      17             : #if defined(OPENMP_3_1)
-      18             :                 #pragma omp atomic capture
-      19             :                 {serialNumber = nextSerialNumber++;}
-      20             : #elif defined(__GNUC__)
-      21     3368851 :                 {serialNumber = __sync_add_and_fetch(&nextSerialNumber, 1);}
-      22             : #else
-      23             :                 #pragma omp critical
-      24             :                 {serialNumber = nextSerialNumber++;}
-      25             : #endif
-      26             : 
-      27     3368851 : }
-      28             : 
-      29          20 : Candidate::Candidate(const ParticleState &state) :
-      30          20 :                 source(state), created(state), current(state), previous(state), redshift(0), trajectoryLength(0), currentStep(0), nextStep(0), active(true), parent(0), tagOrigin ("PRIM") {
-      31             : 
-      32             : #if defined(OPENMP_3_1)
-      33             :                 #pragma omp atomic capture
-      34             :                 {serialNumber = nextSerialNumber++;}
-      35             : #elif defined(__GNUC__)
-      36          20 :                 {serialNumber = __sync_add_and_fetch(&nextSerialNumber, 1);}
-      37             : #else
-      38             :                 #pragma omp critical
-      39             :                 {serialNumber = nextSerialNumber++;}
-      40             : #endif
-      41             : 
-      42          20 : }
-      43             : 
-      44       21336 : bool Candidate::isActive() const {
-      45       21336 :         return active;
-      46             : }
-      47             : 
-      48        1742 : void Candidate::setActive(bool b) {
-      49        1742 :         active = b;
-      50        1742 : }
-      51             : 
-      52      529541 : double Candidate::getRedshift() const {
-      53      529541 :         return redshift;
-      54             : }
-      55             : 
-      56     1011718 : double Candidate::getTrajectoryLength() const {
-      57     1011718 :         return trajectoryLength;
-      58             : }
-      59             : 
-      60        1064 : double Candidate::getWeight() const {
-      61        1064 :         return weight;
-      62             : }
-      63             : 
-      64       63001 : double Candidate::getCurrentStep() const {
-      65       63001 :         return currentStep;
-      66             : }
-      67             : 
-      68      499385 : double Candidate::getNextStep() const {
-      69      499385 :         return nextStep;
-      70             : }
-      71             : 
-      72     3332752 : void Candidate::setRedshift(double z) {
-      73     3332752 :         redshift = z;
-      74     3332752 : }
-      75             : 
-      76     3324939 : void Candidate::setTrajectoryLength(double a) {
-      77     3324939 :         trajectoryLength = a;
-      78     3324939 : }
-      79             : 
-      80     3325923 : void Candidate::setWeight(double w) {
-      81     3325923 :         weight = w;
-      82     3325923 : }
-      83             : 
-      84           5 : void Candidate::updateWeight(double w) {
-      85           5 :   weight *= w;
-      86           5 : }
-      87             : 
-      88      501076 : void Candidate::setCurrentStep(double lstep) {
-      89      501076 :         currentStep = lstep;
-      90      501076 :         trajectoryLength += lstep;
-      91      501076 : }
-      92             : 
-      93      499400 : void Candidate::setNextStep(double step) {
-      94      499400 :         nextStep = step;
-      95      499400 : }
-      96             : 
-      97      530052 : void Candidate::limitNextStep(double step) {
-      98      530052 :         nextStep = std::min(nextStep, step);
-      99      530052 : }
-     100             : 
-     101        1143 : void Candidate::setProperty(const std::string &name, const Variant &value) {
-     102        1143 :         properties[name] = value;
-     103        1143 : }
-     104             : 
-     105     3324912 : void Candidate::setTagOrigin (std::string tagOrigin) {
-     106     3324912 :         this->tagOrigin = tagOrigin;
-     107     3324912 : }
-     108             : 
-     109          61 : std::string Candidate::getTagOrigin () const {
-     110          61 :         return tagOrigin;
-     111             : }
-     112             : 
-     113          11 : const Variant &Candidate::getProperty(const std::string &name) const {
-     114          11 :         PropertyMap::const_iterator i = properties.find(name);
-     115          11 :         if (i == properties.end())
-     116           0 :                 throw std::runtime_error("Unknown candidate property: " + name);
-     117          11 :         return i->second;
-     118             : }
-     119             : 
-     120           5 : bool Candidate::removeProperty(const std::string& name) {
-     121           5 :         PropertyMap::iterator i = properties.find(name);
-     122           5 :         if (i == properties.end())
-     123             :                 return false;
-     124             :         properties.erase(i);
-     125             :         return true;
-     126             : }
-     127             : 
-     128          30 : bool Candidate::hasProperty(const std::string &name) const {
-     129          30 :         PropertyMap::const_iterator i = properties.find(name);
-     130          30 :         if (i == properties.end())
-     131          10 :                 return false;
-     132             :         return true;
-     133             : }
-     134             : 
-     135           4 : void Candidate::addSecondary(Candidate *c) {
-     136           4 :         secondaries.push_back(c);
-     137           4 : }
-     138             : 
-     139           2 : void Candidate::addSecondary(int id, double energy, double w, std::string tagOrigin) {
-     140           4 :         ref_ptr<Candidate> secondary = new Candidate;
-     141           2 :         secondary->setRedshift(redshift);
-     142           2 :         secondary->setTrajectoryLength(trajectoryLength);
-     143           2 :         secondary->setWeight(weight * w);
-     144           4 :         secondary->setTagOrigin(tagOrigin);
-     145           2 :         for (PropertyMap::const_iterator it = properties.begin(); it != properties.end(); ++it) {
-     146           0 :                 secondary->setProperty(it->first, it->second);         
-     147             :         }
-     148             :         secondary->source = source;
-     149             :         secondary->previous = previous;
-     150             :         secondary->created = previous;
-     151           2 :         secondary->current = current;
-     152           2 :         secondary->current.setId(id);
-     153           2 :         secondary->current.setEnergy(energy);
-     154           2 :         secondary->parent = this;
-     155           2 :         secondaries.push_back(secondary);
-     156           2 : }
-     157             : 
-     158     3324908 : void Candidate::addSecondary(int id, double energy, Vector3d position, double w, std::string tagOrigin) {
-     159     6649816 :         ref_ptr<Candidate> secondary = new Candidate;
-     160     3324908 :         secondary->setRedshift(redshift);
-     161     3324908 :         secondary->setTrajectoryLength(trajectoryLength - (current.getPosition() - position).getR());
-     162     3324908 :         secondary->setWeight(weight * w);
-     163     6649816 :         secondary->setTagOrigin(tagOrigin);
-     164     3324908 :         for (PropertyMap::const_iterator it = properties.begin(); it != properties.end(); ++it) {
-     165           0 :                 secondary->setProperty(it->first, it->second);         
-     166             :         }
-     167             :         secondary->source = source;
-     168             :         secondary->previous = previous;
-     169     3324908 :         secondary->created = previous;
-     170     3324908 :         secondary->current = current;
-     171     3324908 :         secondary->current.setId(id);
-     172     3324908 :         secondary->current.setEnergy(energy);
-     173     3324908 :         secondary->current.setPosition(position);
-     174     3324908 :         secondary->created.setPosition(position);
-     175     3324908 :         secondary->parent = this;
-     176     3324908 :         secondaries.push_back(secondary);
-     177     3324908 : }
-     178             : 
-     179           0 : void Candidate::clearSecondaries() {
-     180           0 :         secondaries.clear();
-     181           0 : }
-     182             : 
-     183           0 : std::string Candidate::getDescription() const {
-     184           0 :         std::stringstream ss;
-     185           0 :         ss << "CosmicRay at z = " << getRedshift() << "\n";
-     186           0 :         ss << "  source:  " << source.getDescription() << "\n";
-     187           0 :         ss << "  current: " << current.getDescription();
-     188           0 :         return ss.str();
-     189           0 : }
-     190             : 
-     191          30 : ref_ptr<Candidate> Candidate::clone(bool recursive) const {
-     192          60 :         ref_ptr<Candidate> cloned = new Candidate;
-     193             :         cloned->source = source;
-     194             :         cloned->created = created;
-     195             :         cloned->current = current;
-     196             :         cloned->previous = previous;
-     197             : 
-     198          30 :         cloned->properties = properties;
-     199          30 :         cloned->active = active;
-     200          30 :         cloned->redshift = redshift;
-     201          30 :         cloned->weight = weight;
-     202          30 :         cloned->trajectoryLength = trajectoryLength;
-     203          30 :         cloned->currentStep = currentStep;
-     204          30 :         cloned->nextStep = nextStep;
-     205          30 :         if (recursive) {
-     206           0 :                 cloned->secondaries.reserve(secondaries.size());
-     207           0 :                 for (size_t i = 0; i < secondaries.size(); i++) {
-     208           0 :                         ref_ptr<Candidate> s = secondaries[i]->clone(recursive);
-     209           0 :                         s->parent = cloned;
-     210           0 :                         cloned->secondaries.push_back(s);
-     211             :                 }
-     212             :         }
-     213          30 :         return cloned;
-     214             : }
-     215             : 
-     216          84 : uint64_t Candidate::getSerialNumber() const {
-     217          84 :         return serialNumber;
-     218             : }
-     219             : 
-     220          11 : void Candidate::setSerialNumber(const uint64_t snr) {
-     221          11 :         serialNumber = snr;
-     222          11 : }
-     223             : 
-     224          49 : uint64_t Candidate::getSourceSerialNumber() const {
-     225          84 :         if (parent)
-     226             :                 return parent->getSourceSerialNumber();
-     227             :         else
-     228          49 :                 return serialNumber;
-     229             : }
-     230             : 
-     231          48 : uint64_t Candidate::getCreatedSerialNumber() const {
-     232          48 :         if (parent)
-     233          35 :                 return parent->getSerialNumber();
-     234             :         else
-     235          13 :                 return serialNumber;
-     236             : }
-     237             : 
-     238           1 : void Candidate::setNextSerialNumber(uint64_t snr) {
-     239           1 :         nextSerialNumber = snr;
-     240           1 : }
-     241             : 
-     242           6 : uint64_t Candidate::getNextSerialNumber() {
-     243           6 :         return nextSerialNumber;
-     244             : }
-     245             : 
-     246             : uint64_t Candidate::nextSerialNumber = 0;
-     247             : 
-     248           1 : void Candidate::restart() {
-     249           1 :         setActive(true);
-     250           1 :         setTrajectoryLength(0);
-     251             :         previous = source;
-     252             :         current = source;
-     253           1 : }
-     254             : 
-     255             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Clock.cpp.func-sort-c.html b/doc/coverageReport/src/Clock.cpp.func-sort-c.html deleted file mode 100644 index 3a192f2e6..000000000 --- a/doc/coverageReport/src/Clock.cpp.func-sort-c.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Clock.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Clock.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:080.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa5Clock11getInstanceEv0
_ZN7crpropa5Clock14getMillisecondEv0
_ZN7crpropa5Clock4Impl7getTimeEv0
_ZN7crpropa5Clock5resetEv0
_ZN7crpropa5Clock9getSecondEv0
_ZN7crpropa5ClockC2Ev0
_ZN7crpropa5ClockD0Ev0
_ZN7crpropa5ClockD2Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Clock.cpp.func.html b/doc/coverageReport/src/Clock.cpp.func.html deleted file mode 100644 index 5e2c004bd..000000000 --- a/doc/coverageReport/src/Clock.cpp.func.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Clock.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Clock.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:080.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa5Clock11getInstanceEv0
_ZN7crpropa5Clock14getMillisecondEv0
_ZN7crpropa5Clock4Impl7getTimeEv0
_ZN7crpropa5Clock5resetEv0
_ZN7crpropa5Clock9getSecondEv0
_ZN7crpropa5ClockC2Ev0
_ZN7crpropa5ClockD0Ev0
_ZN7crpropa5ClockD2Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Clock.cpp.gcov.html b/doc/coverageReport/src/Clock.cpp.gcov.html deleted file mode 100644 index 1175dfb35..000000000 --- a/doc/coverageReport/src/Clock.cpp.gcov.html +++ /dev/null @@ -1,231 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Clock.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Clock.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:080.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Clock.h"
-       2             : 
-       3             : #if defined(WIN32) || defined(_WIN32)
-       4             : 
-       5             : #define USE_WINDOWS_TIMERS
-       6             : #define WIN32_LEAN_AND_MEAN
-       7             : #define NOWINRES
-       8             : #define NOMCX
-       9             : #define NOIME
-      10             : #ifdef _XBOX
-      11             : #include <Xtl.h>
-      12             : #else
-      13             : #include <windows.h>
-      14             : #endif
-      15             : #include <ctime>
-      16             : 
-      17             : #else
-      18             : #include <sys/time.h>
-      19             : #endif
-      20             : 
-      21             : #include <algorithm>
-      22             : #ifdef _OPENMP
-      23             : #include <omp.h>
-      24             : #include <stdexcept>
-      25             : #endif
-      26             : 
-      27             : namespace crpropa {
-      28             : 
-      29             : #ifdef WIN32
-      30             : class Clock::Impl {
-      31             :         LARGE_INTEGER clockFrequency;
-      32             :         DWORD startTick;
-      33             :         LONGLONG prevElapsedTime;
-      34             :         LARGE_INTEGER startTime;
-      35             : public:
-      36             :         Impl() {
-      37             :                 QueryPerformanceFrequency(&clockFrequency);
-      38             :                 reset();
-      39             :         }
-      40             : 
-      41             :         void reset() {
-      42             :                 QueryPerformanceCounter(&startTime);
-      43             :                 startTick = GetTickCount();
-      44             :                 prevElapsedTime = 0;
-      45             :         }
-      46             : 
-      47             :         /// Returns the time in ms since the last call to reset or since
-      48             :         /// the btClock was created.
-      49             :         double getSecond() {
-      50             :                 LARGE_INTEGER currentTime;
-      51             :                 QueryPerformanceCounter(&currentTime);
-      52             :                 LONGLONG elapsedTime = currentTime.QuadPart - startTime.QuadPart;
-      53             : 
-      54             :                 // Compute the number of millisecond ticks elapsed.
-      55             :                 unsigned long msecTicks = (unsigned long) (1000 * elapsedTime
-      56             :                                 / clockFrequency.QuadPart);
-      57             : 
-      58             :                 // Check for unexpected leaps in the Win32 performance counter.
-      59             :                 // (This is caused by unexpected data across the PCI to ISA
-      60             :                 // bridge, aka south bridge.  See Microsoft KB274323.)
-      61             :                 unsigned long elapsedTicks = GetTickCount() - startTick;
-      62             :                 signed long msecOff = (signed long) (msecTicks - elapsedTicks);
-      63             :                 if (msecOff < -100 || msecOff > 100) {
-      64             :                         // Adjust the starting time forwards.
-      65             :                         LONGLONG msecAdjustment = std::min(
-      66             :                                         msecOff * clockFrequency.QuadPart / 1000,
-      67             :                                         elapsedTime - prevElapsedTime);
-      68             :                         startTime.QuadPart += msecAdjustment;
-      69             :                         elapsedTime -= msecAdjustment;
-      70             :                 }
-      71             : 
-      72             :                 // Store the current elapsed time for adjustments next time.
-      73             :                 prevElapsedTime = elapsedTime;
-      74             : 
-      75             :                 // Convert to microseconds.
-      76             :                 unsigned long usecTicks = (unsigned long) (1000000 * elapsedTime
-      77             :                                 / clockFrequency.QuadPart);
-      78             : 
-      79             :                 return double(usecTicks) / 1000000;
-      80             :         }
-      81             : };
-      82             : #else
-      83             : 
-      84             : class Clock::Impl {
-      85             :         struct timeval startTime;
-      86             : public:
-      87           0 :         Impl() {
-      88             :                 reset();
-      89             :         }
-      90             : 
-      91             :         void reset() {
-      92           0 :                 gettimeofday(&startTime, 0);
-      93             :         }
-      94             : 
-      95             :         /// Returns the time in since the last call to reset or since
-      96             :         /// the btClock was created.
-      97           0 :         double getTime() {
-      98             :                 struct timeval currentTime;
-      99           0 :                 gettimeofday(&currentTime, 0);
-     100           0 :                 double t = double(currentTime.tv_sec - startTime.tv_sec);
-     101           0 :                 t += double(currentTime.tv_usec - startTime.tv_usec) / 1000000.;
-     102           0 :                 return t;
-     103             :         }
-     104             : };
-     105             : #endif
-     106             : 
-     107           0 : Clock::Clock() {
-     108           0 :         impl = new Impl;
-     109           0 : }
-     110             : 
-     111           0 : Clock::~Clock() {
-     112           0 :         delete impl;
-     113           0 : }
-     114             : 
-     115           0 : void Clock::reset() {
-     116           0 :         impl->reset();
-     117           0 : }
-     118             : 
-     119           0 : double Clock::getSecond() {
-     120           0 :         return impl->getTime();
-     121             : }
-     122             : 
-     123           0 : double Clock::getMillisecond() {
-     124           0 :         return impl->getTime() * 1000;
-     125             : }
-     126             : 
-     127             : #ifdef _OPENMP
-     128             : 
-     129             : // see http://stackoverflow.com/questions/8051108/using-the-openmp-threadprivate-directive-on-static-instances-of-c-stl-types
-     130             : const static int MAX_THREAD = 256;
-     131             : 
-     132           0 : struct CLOCK_TLS_ITEM {
-     133             :         Clock r;
-     134             :         char padding[(sizeof(Clock) / 64 + 1) * 64 - sizeof(Clock)];
-     135             : };
-     136             : 
-     137           0 : Clock &Clock::getInstance() {
-     138             : #ifdef _MSC_VER
-     139             :         __declspec(align(64)) static CLOCK_TLS_ITEM tls[MAX_THREAD];
-     140             : #else
-     141           0 :         __attribute__ ((aligned(64))) static CLOCK_TLS_ITEM tls[MAX_THREAD];
-     142             : #endif
-     143           0 :         int i = omp_get_thread_num();
-     144           0 :         if (i >= MAX_THREAD)
-     145           0 :         throw std::runtime_error("crpropa::Clock: more than MAX_THREAD threads!");
-     146           0 :         return tls[i].r;
-     147             : }
-     148             : #else
-     149             : Clock &Clock::getInstance() {
-     150             :         static Clock r;
-     151             :         return r;
-     152             : }
-     153             : #endif
-     154             : 
-     155             : } /* namespace scs */
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Common.cpp.func-sort-c.html b/doc/coverageReport/src/Common.cpp.func-sort-c.html deleted file mode 100644 index 8b8e54c80..000000000 --- a/doc/coverageReport/src/Common.cpp.func-sort-c.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Common.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Common.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486277.4 %
Date:2024-04-08 14:58:22Functions:5683.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16getInstallPrefixB5cxx11Ev0
_ZN7crpropa11getDataPathENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE547
_ZN7crpropa12closestIndexEdRKSt6vectorIdSaIdEE565
_ZN7crpropa22interpolateEquidistantEdddRKSt6vectorIdSaIdEE1528
_ZN7crpropa11interpolateEdRKSt6vectorIdSaIdEES4_158374
_ZN7crpropa13interpolate2dEddRKSt6vectorIdSaIdEES4_S4_9536930
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Common.cpp.func.html b/doc/coverageReport/src/Common.cpp.func.html deleted file mode 100644 index b7cf2d004..000000000 --- a/doc/coverageReport/src/Common.cpp.func.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Common.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Common.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486277.4 %
Date:2024-04-08 14:58:22Functions:5683.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11getDataPathENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE547
_ZN7crpropa11interpolateEdRKSt6vectorIdSaIdEES4_158374
_ZN7crpropa12closestIndexEdRKSt6vectorIdSaIdEE565
_ZN7crpropa13interpolate2dEddRKSt6vectorIdSaIdEES4_S4_9536930
_ZN7crpropa16getInstallPrefixB5cxx11Ev0
_ZN7crpropa22interpolateEquidistantEdddRKSt6vectorIdSaIdEE1528
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Common.cpp.gcov.html b/doc/coverageReport/src/Common.cpp.gcov.html deleted file mode 100644 index 485f15540..000000000 --- a/doc/coverageReport/src/Common.cpp.gcov.html +++ /dev/null @@ -1,212 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Common.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Common.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486277.4 %
Date:2024-04-08 14:58:22Functions:5683.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Common.h"
-       2             : 
-       3             : #include "kiss/path.h"
-       4             : #include "kiss/logger.h"
-       5             : 
-       6             : #include <cstdlib>
-       7             : #include <fstream>
-       8             : #include <string>
-       9             : #include <cmath>
-      10             : #include <algorithm>
-      11             : 
-      12             : #define index(i,j) ((j)+(i)*Y.size())
-      13             : 
-      14             : namespace crpropa {
-      15             : 
-      16         547 : std::string getDataPath(std::string filename) {
-      17         547 :         static std::string dataPath;
-      18         547 :         if (dataPath.size())
-      19         534 :                 return concat_path(dataPath, filename);
-      20             : 
-      21          13 :         const char *env_path = getenv("CRPROPA_DATA_PATH");
-      22          13 :         if (env_path) {
-      23           0 :                 if (is_directory(env_path)) {
-      24             :                         dataPath = env_path;
-      25           0 :                         KISS_LOG_INFO << "getDataPath: use environment variable, "
-      26           0 :                                         << dataPath << std::endl;
-      27           0 :                         return concat_path(dataPath, filename);
-      28             :                 }
-      29             :         }
-      30             : 
-      31             : #ifdef CRPROPA_INSTALL_PREFIX
-      32             :         {
-      33          13 :                 std::string _path = CRPROPA_INSTALL_PREFIX "/share/crpropa";
-      34          13 :                 if (is_directory(_path)) {
-      35             :                         dataPath = _path;
-      36           0 :                         KISS_LOG_INFO
-      37           0 :                         << "getDataPath: use install prefix, " << dataPath << std::endl;
-      38           0 :                         return concat_path(dataPath, filename);
-      39             :                 }
-      40             :         }
-      41             : #endif
-      42             : 
-      43             :         {
-      44          13 :                 std::string _path = executable_path() + "../data";
-      45          13 :                 if (is_directory(_path)) {
-      46             :                         dataPath = _path;
-      47           0 :                         KISS_LOG_INFO << "getDataPath: use executable path, " << dataPath
-      48           0 :                                         << std::endl;
-      49           0 :                         return concat_path(dataPath, filename);
-      50             :                 }
-      51             :         }
-      52             : 
-      53             :         dataPath = "data";
-      54          13 :         KISS_LOG_INFO << "getDataPath: use default, " << dataPath << std::endl;
-      55          13 :         return concat_path(dataPath, filename);
-      56             : }
-      57             : 
-      58             : 
-      59           0 : std::string getInstallPrefix()
-      60             : {
-      61           0 :   std::string _path = "";
-      62             :   #ifdef CRPROPA_INSTALL_PREFIX
-      63             :     _path += CRPROPA_INSTALL_PREFIX;
-      64             :   #endif
-      65           0 :   return _path;
-      66             : };
-      67             : 
-      68      158374 : double interpolate(double x, const std::vector<double> &X,
-      69             :                 const std::vector<double> &Y) {
-      70             :         std::vector<double>::const_iterator it = std::upper_bound(X.begin(),
-      71             :                         X.end(), x);
-      72      158374 :         if (it == X.begin())
-      73           1 :                 return Y.front();
-      74      158373 :         if (it == X.end())
-      75           1 :                 return Y.back();
-      76             : 
-      77             :         size_t i = it - X.begin() - 1;
-      78      158372 :         return Y[i] + (x - X[i]) * (Y[i + 1] - Y[i]) / (X[i + 1] - X[i]);
-      79             : }
-      80             : 
-      81     9536930 : double interpolate2d(double x, double y, const std::vector<double> &X,
-      82             :                 const std::vector<double> &Y, const std::vector<double> &Z) {
-      83             : 
-      84             :         std::vector<double>::const_iterator itx = std::upper_bound(X.begin(), X.end(), x);
-      85             :         std::vector<double>::const_iterator ity = std::upper_bound(Y.begin(), Y.end(), y);
-      86             : 
-      87     9536930 :         if (x > X.back() || x < X.front())
-      88             :                 return 0;
-      89     9536930 :         if (y > Y.back() || y < Y.front())
-      90             :                 return 0;
-      91             : 
-      92     9536930 :         if (itx == X.begin() && ity == Y.begin())
-      93           0 :                 return Z.front();
-      94     9536930 :         if (itx == X.end() && ity == Y.end())
-      95          73 :                 return Z.back();
-      96             : 
-      97     9536857 :         size_t i = itx - X.begin() - 1;
-      98     9536857 :         size_t j = ity - Y.begin() - 1;
-      99             : 
-     100     9536857 :         double Q11 = Z[index(i,j)];
-     101     9536857 :         double Q12 = Z[index(i,j+1)];
-     102     9536857 :         double Q21 = Z[index(i+1,j)];
-     103     9536857 :         double Q22 = Z[index(i+1,j+1)];
-     104             : 
-     105     9536857 :         double R1 = ((X[i+1]-x)/(X[i+1]-X[i]))*Q11+((x-X[i])/(X[i+1]-X[i]))*Q21;
-     106     9536857 :         double R2 = ((X[i+1]-x)/(X[i+1]-X[i]))*Q12+((x-X[i])/(X[i+1]-X[i]))*Q22;
-     107             : 
-     108     9536857 :         return ((Y[j+1]-y)/(Y[j+1]-Y[j]))*R1+((y-Y[j])/(Y[j+1]-Y[j]))*R2;
-     109             : }
-     110             : 
-     111        1528 : double interpolateEquidistant(double x, double lo, double hi,
-     112             :                 const std::vector<double> &Y) {
-     113        1528 :         if (x <= lo)
-     114           1 :                 return Y.front();
-     115        1527 :         if (x >= hi)
-     116           1 :                 return Y.back();
-     117             : 
-     118        1526 :         double dx = (hi - lo) / (Y.size() - 1);
-     119        1526 :         double p = (x - lo) / dx;
-     120        1526 :         size_t i = floor(p);
-     121        1526 :         return Y[i] + (p - i) * (Y[i + 1] - Y[i]);
-     122             : }
-     123             : 
-     124         565 : size_t closestIndex(double x, const std::vector<double> &X) {
-     125         565 :         size_t i1 = std::lower_bound(X.begin(), X.end(), x) - X.begin();
-     126         565 :         if (i1 == 0)
-     127             :                 return i1;
-     128         565 :         size_t i0 = i1 - 1;
-     129         565 :         if (std::fabs(X[i0] - x) < std::fabs(X[i1] - x))
-     130             :                 return i0;
-     131             :         else
-     132         308 :                 return i1;
-     133             : }
-     134             : 
-     135             : } // namespace crpropa
-     136             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Cosmology.cpp.func-sort-c.html b/doc/coverageReport/src/Cosmology.cpp.func-sort-c.html deleted file mode 100644 index 5faf01e27..000000000 --- a/doc/coverageReport/src/Cosmology.cpp.func-sort-c.html +++ /dev/null @@ -1,132 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Cosmology.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Cosmology.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:449247.8 %
Date:2024-04-08 14:58:22Functions:61540.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22setCosmologyParametersEdd0
_ZN7crpropa25redshift2ComovingDistanceEd0
_ZN7crpropa27luminosityDistance2RedshiftEd0
_ZN7crpropa27redshift2LuminosityDistanceEd0
_ZN7crpropa28lightTravelDistance2RedshiftEd0
_ZN7crpropa28redshift2LightTravelDistanceEd0
_ZN7crpropa2H0Ev0
_ZN7crpropa6omegaLEv0
_ZN7crpropa6omegaMEv0
_ZN7crpropa25comovingDistance2RedshiftEd1
_ZN7crpropa28lightTravel2ComovingDistanceEd1
_ZN7crpropa28comoving2LightTravelDistanceEd2
_ZN7crpropa9Cosmology6updateEv19
_ZN7crpropa9CosmologyC2Ev19
_ZN7crpropa10hubbleRateEd7623
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Cosmology.cpp.func.html b/doc/coverageReport/src/Cosmology.cpp.func.html deleted file mode 100644 index ea101710d..000000000 --- a/doc/coverageReport/src/Cosmology.cpp.func.html +++ /dev/null @@ -1,132 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Cosmology.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Cosmology.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:449247.8 %
Date:2024-04-08 14:58:22Functions:61540.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10hubbleRateEd7623
_ZN7crpropa22setCosmologyParametersEdd0
_ZN7crpropa25comovingDistance2RedshiftEd1
_ZN7crpropa25redshift2ComovingDistanceEd0
_ZN7crpropa27luminosityDistance2RedshiftEd0
_ZN7crpropa27redshift2LuminosityDistanceEd0
_ZN7crpropa28comoving2LightTravelDistanceEd2
_ZN7crpropa28lightTravel2ComovingDistanceEd1
_ZN7crpropa28lightTravelDistance2RedshiftEd0
_ZN7crpropa28redshift2LightTravelDistanceEd0
_ZN7crpropa2H0Ev0
_ZN7crpropa6omegaLEv0
_ZN7crpropa6omegaMEv0
_ZN7crpropa9Cosmology6updateEv19
_ZN7crpropa9CosmologyC2Ev19
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Cosmology.cpp.gcov.html b/doc/coverageReport/src/Cosmology.cpp.gcov.html deleted file mode 100644 index f85d7609e..000000000 --- a/doc/coverageReport/src/Cosmology.cpp.gcov.html +++ /dev/null @@ -1,245 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Cosmology.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Cosmology.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:449247.8 %
Date:2024-04-08 14:58:22Functions:61540.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Cosmology.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Common.h"
-       4             : 
-       5             : #include <vector>
-       6             : #include <cmath>
-       7             : #include <stdexcept>
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11             : /**
-      12             :  @class Cosmology
-      13             :  @brief Cosmology calculations
-      14             :  */
-      15             : struct Cosmology {
-      16             :         double H0; // Hubble parameter at z=0
-      17             :         double omegaM; // matter density parameter
-      18             :         double omegaL; // vacuum energy parameter
-      19             : 
-      20             :         static const int n;
-      21             :         static const double zmin;
-      22             :         static const double zmax;
-      23             : 
-      24             :         std::vector<double> Z;  // redshift
-      25             :         std::vector<double> Dc; // comoving distance [m]
-      26             :         std::vector<double> Dl; // luminosity distance [m]
-      27             :         std::vector<double> Dt; // light travel distance [m]
-      28             : 
-      29          19 :         void update() {
-      30          19 :                 double dH = c_light / H0; // Hubble distance
-      31             : 
-      32          19 :                 std::vector<double> E(n);
-      33          19 :                 E[0] = 1;
-      34             : 
-      35             :                 // Relation between comoving distance r and redshift z (cf. J.A. Peacock, Cosmological physics, p. 89 eq. 3.76)
-      36             :                 // dr = c / H(z) dz, integration using midpoint rule
-      37             :                 double dlz = log10(zmax) - log10(zmin);
-      38       19000 :                 for (int i = 1; i < n; i++) {
-      39       18981 :                         Z[i] = zmin * pow(10, i * dlz / (n - 1)); // logarithmic even spacing
-      40       18981 :                         double dz = (Z[i] - Z[i - 1]); // redshift step
-      41       18981 :                         E[i] = sqrt(omegaL + omegaM * pow_integer<3>(1 + Z[i]));
-      42       18981 :                         Dc[i] = Dc[i - 1] + dH * dz * (1 / E[i] + 1 / E[i - 1]) / 2;
-      43       18981 :                         Dl[i] = (1 + Z[i]) * Dc[i];
-      44       18981 :                         Dt[i] = Dt[i - 1]
-      45       18981 :                                         + dH * dz
-      46       18981 :                                                         * (1 / ((1 + Z[i]) * E[i])
-      47       18981 :                                                                         + 1 / ((1 + Z[i - 1]) * E[i - 1])) / 2;
-      48             :                 }
-      49          19 :         }
-      50             : 
-      51          19 :         Cosmology() {
-      52             :         // Cosmological parameters (K.A. Olive et al. (Particle Data Group), Chin. Phys. C, 38, 090001 (2014))
-      53          19 :                 H0 = 67.3 * 1000 * meter / second / Mpc; // default values
-      54          19 :                 omegaM = 0.315;
-      55          19 :                 omegaL = 1 - omegaM;
-      56             : 
-      57          19 :                 Z.resize(n);
-      58          19 :                 Dc.resize(n);
-      59          19 :                 Dl.resize(n);
-      60          19 :                 Dt.resize(n);
-      61             : 
-      62          19 :                 Z[0] = 0;
-      63          19 :                 Dc[0] = 0;
-      64          19 :                 Dl[0] = 0;
-      65          19 :                 Dt[0] = 0;
-      66             : 
-      67          19 :                 update();
-      68          19 :         }
-      69             : 
-      70             :         void setParameters(double h, double oM) {
-      71           0 :                 H0 = h * 1e5 / Mpc;
-      72           0 :                 omegaM = oM;
-      73           0 :                 omegaL = 1 - oM;
-      74           0 :                 update();
-      75             :         }
-      76             : };
-      77             : 
-      78             : const int Cosmology::n = 1000;
-      79             : const double Cosmology::zmin = 0.0001;
-      80             : const double Cosmology::zmax = 100;
-      81             : 
-      82             : static Cosmology cosmology; // instance is created at runtime
-      83             : 
-      84           0 : void setCosmologyParameters(double h, double oM) {
-      85             :         cosmology.setParameters(h, oM);
-      86           0 : }
-      87             : 
-      88        7623 : double hubbleRate(double z) {
-      89        7623 :         return cosmology.H0
-      90        7623 :                         * sqrt(cosmology.omegaL + cosmology.omegaM * pow(1 + z, 3));
-      91             : }
-      92             : 
-      93           0 : double omegaL() {
-      94           0 :         return cosmology.omegaL;
-      95             : }
-      96             : 
-      97           0 : double omegaM() {
-      98           0 :         return cosmology.omegaM;
-      99             : }
-     100             : 
-     101           0 : double H0() {
-     102           0 :         return cosmology.H0;
-     103             : }
-     104             : 
-     105           1 : double comovingDistance2Redshift(double d) {
-     106           1 :         if (d < 0)
-     107           0 :                 throw std::runtime_error("Cosmology: d < 0");
-     108           1 :         if (d > cosmology.Dc.back())
-     109           0 :                 throw std::runtime_error("Cosmology: d > dmax");
-     110           1 :         return interpolate(d, cosmology.Dc, cosmology.Z);
-     111             : }
-     112             : 
-     113           0 : double redshift2ComovingDistance(double z) {
-     114           0 :         if (z < 0)
-     115           0 :                 throw std::runtime_error("Cosmology: z < 0");
-     116           0 :         if (z > cosmology.zmax)
-     117           0 :                 throw std::runtime_error("Cosmology: z > zmax");
-     118           0 :         return interpolate(z, cosmology.Z, cosmology.Dc);
-     119             : }
-     120             : 
-     121           0 : double luminosityDistance2Redshift(double d) {
-     122           0 :         if (d < 0)
-     123           0 :                 throw std::runtime_error("Cosmology: d < 0");
-     124           0 :         if (d > cosmology.Dl.back())
-     125           0 :                 throw std::runtime_error("Cosmology: d > dmax");
-     126           0 :         return interpolate(d, cosmology.Dl, cosmology.Z);
-     127             : }
-     128             : 
-     129           0 : double redshift2LuminosityDistance(double z) {
-     130           0 :         if (z < 0)
-     131           0 :                 throw std::runtime_error("Cosmology: z < 0");
-     132           0 :         if (z > cosmology.zmax)
-     133           0 :                 throw std::runtime_error("Cosmology: z > zmax");
-     134           0 :         return interpolate(z, cosmology.Z, cosmology.Dl);
-     135             : }
-     136             : 
-     137           0 : double lightTravelDistance2Redshift(double d) {
-     138           0 :         if (d < 0)
-     139           0 :                 throw std::runtime_error("Cosmology: d < 0");
-     140           0 :         if (d > cosmology.Dt.back())
-     141           0 :                 throw std::runtime_error("Cosmology: d > dmax");
-     142           0 :         return interpolate(d, cosmology.Dt, cosmology.Z);
-     143             : }
-     144             : 
-     145           0 : double redshift2LightTravelDistance(double z) {
-     146           0 :         if (z < 0)
-     147           0 :                 throw std::runtime_error("Cosmology: z < 0");
-     148           0 :         if (z > cosmology.zmax)
-     149           0 :                 throw std::runtime_error("Cosmology: z > zmax");
-     150           0 :         return interpolate(z, cosmology.Z, cosmology.Dt);
-     151             : }
-     152             : 
-     153           2 : double comoving2LightTravelDistance(double d) {
-     154           2 :         if (d < 0)
-     155           0 :                 throw std::runtime_error("Cosmology: d < 0");
-     156           2 :         if (d > cosmology.Dc.back())
-     157           0 :                 throw std::runtime_error("Cosmology: d > dmax");
-     158           2 :         return interpolate(d, cosmology.Dc, cosmology.Dt);
-     159             : }
-     160             : 
-     161           1 : double lightTravel2ComovingDistance(double d) {
-     162           1 :         if (d < 0)
-     163           0 :                 throw std::runtime_error("Cosmology: d < 0");
-     164           1 :         if (d > cosmology.Dt.back())
-     165           0 :                 throw std::runtime_error("Cosmology: d > dmax");
-     166           1 :         return interpolate(d, cosmology.Dt, cosmology.Dc);
-     167             : }
-     168             : 
-     169             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html b/doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html deleted file mode 100644 index 08e7db8aa..000000000 --- a/doc/coverageReport/src/EmissionMap.cpp.func-sort-c.html +++ /dev/null @@ -1,204 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/EmissionMap.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - EmissionMap.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8315653.2 %
Date:2024-04-08 14:58:22Functions:183354.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11EmissionMap4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap4saveERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap5mergeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap6hasMapEid0
_ZN7crpropa11EmissionMap7fillMapERKNS_13ParticleStateEd0
_ZN7crpropa11EmissionMapC2Emmm0
_ZN7crpropa24CylindricalProjectionMap7getNPhiEv0
_ZN7crpropa24CylindricalProjectionMap9getNThetaEv0
_ZN7crpropa24CylindricalProjectionMapC2Ev0
_ZNK7crpropa11EmissionMap13drawDirectionERKNS_13ParticleStateERNS_7Vector3IdEE0
_ZNK7crpropa11EmissionMap14checkDirectionERKNS_13ParticleStateE0
_ZNK7crpropa11EmissionMap14checkDirectionEidRKNS_7Vector3IdEE0
_ZNK7crpropa24CylindricalProjectionMap14checkDirectionERKNS_7Vector3IdEE0
_ZNK7crpropa24CylindricalProjectionMap6getCdfEv0
_ZNK7crpropa24CylindricalProjectionMap6getPdfEv0
_ZN7crpropa11EmissionMap5mergeEPKS0_1
_ZN7crpropa11EmissionMap7getMapsEv1
_ZN7crpropa11EmissionMapC2Emmmdd1
_ZNK7crpropa11EmissionMap13energyFromBinEm1
_ZNK7crpropa24CylindricalProjectionMap13drawDirectionEv1
_ZNK7crpropa24CylindricalProjectionMap9updateCdfEv1
_ZN7crpropa11EmissionMapC2Ev2
_ZNK7crpropa11EmissionMap7getMapsEv2
_ZNK7crpropa24CylindricalProjectionMap16directionFromBinEm2
_ZNK7crpropa11EmissionMap13drawDirectionEidRNS_7Vector3IdEE3
_ZN7crpropa11EmissionMap7fillMapEidRKNS_7Vector3IdEEd4
_ZN7crpropa24CylindricalProjectionMap7fillBinERKNS_7Vector3IdEEd4
_ZN7crpropa24CylindricalProjectionMap6getPdfEv5
_ZN7crpropa24CylindricalProjectionMapC2Emm6
_ZNK7crpropa24CylindricalProjectionMap16binFromDirectionERKNS_7Vector3IdEE6
_ZN7crpropa11EmissionMap6getMapEid7
_ZNK7crpropa11EmissionMap13binFromEnergyEd11
_ZN7crpropa24CylindricalProjectionMap7fillBinEmd129604
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/EmissionMap.cpp.func.html b/doc/coverageReport/src/EmissionMap.cpp.func.html deleted file mode 100644 index ca8986910..000000000 --- a/doc/coverageReport/src/EmissionMap.cpp.func.html +++ /dev/null @@ -1,204 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/EmissionMap.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - EmissionMap.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8315653.2 %
Date:2024-04-08 14:58:22Functions:183354.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11EmissionMap4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap4saveERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap5mergeEPKS0_1
_ZN7crpropa11EmissionMap5mergeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa11EmissionMap6getMapEid7
_ZN7crpropa11EmissionMap6hasMapEid0
_ZN7crpropa11EmissionMap7fillMapERKNS_13ParticleStateEd0
_ZN7crpropa11EmissionMap7fillMapEidRKNS_7Vector3IdEEd4
_ZN7crpropa11EmissionMap7getMapsEv1
_ZN7crpropa11EmissionMapC2Emmm0
_ZN7crpropa11EmissionMapC2Emmmdd1
_ZN7crpropa11EmissionMapC2Ev2
_ZN7crpropa24CylindricalProjectionMap6getPdfEv5
_ZN7crpropa24CylindricalProjectionMap7fillBinERKNS_7Vector3IdEEd4
_ZN7crpropa24CylindricalProjectionMap7fillBinEmd129604
_ZN7crpropa24CylindricalProjectionMap7getNPhiEv0
_ZN7crpropa24CylindricalProjectionMap9getNThetaEv0
_ZN7crpropa24CylindricalProjectionMapC2Emm6
_ZN7crpropa24CylindricalProjectionMapC2Ev0
_ZNK7crpropa11EmissionMap13binFromEnergyEd11
_ZNK7crpropa11EmissionMap13drawDirectionERKNS_13ParticleStateERNS_7Vector3IdEE0
_ZNK7crpropa11EmissionMap13drawDirectionEidRNS_7Vector3IdEE3
_ZNK7crpropa11EmissionMap13energyFromBinEm1
_ZNK7crpropa11EmissionMap14checkDirectionERKNS_13ParticleStateE0
_ZNK7crpropa11EmissionMap14checkDirectionEidRKNS_7Vector3IdEE0
_ZNK7crpropa11EmissionMap7getMapsEv2
_ZNK7crpropa24CylindricalProjectionMap13drawDirectionEv1
_ZNK7crpropa24CylindricalProjectionMap14checkDirectionERKNS_7Vector3IdEE0
_ZNK7crpropa24CylindricalProjectionMap16binFromDirectionERKNS_7Vector3IdEE6
_ZNK7crpropa24CylindricalProjectionMap16directionFromBinEm2
_ZNK7crpropa24CylindricalProjectionMap6getCdfEv0
_ZNK7crpropa24CylindricalProjectionMap6getPdfEv0
_ZNK7crpropa24CylindricalProjectionMap9updateCdfEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/EmissionMap.cpp.gcov.html b/doc/coverageReport/src/EmissionMap.cpp.gcov.html deleted file mode 100644 index 59cbfc778..000000000 --- a/doc/coverageReport/src/EmissionMap.cpp.gcov.html +++ /dev/null @@ -1,370 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/EmissionMap.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - EmissionMap.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8315653.2 %
Date:2024-04-08 14:58:22Functions:183354.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/EmissionMap.h"
-       2             : #include "crpropa/Random.h"
-       3             : #include "crpropa/Units.h"
-       4             : 
-       5             : #include "kiss/logger.h"
-       6             : 
-       7             : #include <fstream>
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11           0 : CylindricalProjectionMap::CylindricalProjectionMap() : nPhi(360), nTheta(180), dirty(false), pdf(nPhi* nTheta, 0), cdf(nPhi* nTheta, 0) {
-      12           0 :         sPhi = 2. * M_PI / nPhi;
-      13           0 :         sTheta = 2. / nTheta;
-      14           0 : }
-      15             : 
-      16           6 : CylindricalProjectionMap::CylindricalProjectionMap(size_t nPhi, size_t nTheta) : nPhi(nPhi), nTheta(nTheta), dirty(false), pdf(nPhi* nTheta, 0), cdf(nPhi* nTheta, 0) {
-      17           6 :         sPhi = 2 * M_PI / nPhi;
-      18           6 :         sTheta = 2. / nTheta;
-      19           6 : }
-      20             : 
-      21           4 : void CylindricalProjectionMap::fillBin(const Vector3d& direction, double weight) {
-      22           4 :         size_t bin = binFromDirection(direction);
-      23           4 :         fillBin(bin, weight);
-      24           4 : }
-      25             : 
-      26      129604 : void CylindricalProjectionMap::fillBin(size_t bin, double weight) {
-      27      129604 :         pdf[bin] += weight;
-      28      129604 :         dirty = true;
-      29      129604 : }
-      30             : 
-      31           1 : Vector3d CylindricalProjectionMap::drawDirection() const {
-      32           1 :         if (dirty)
-      33           1 :                 updateCdf();
-      34             : 
-      35           1 :         size_t bin = Random::instance().randBin(cdf);
-      36             : 
-      37           1 :         return directionFromBin(bin);
-      38             : }
-      39             : 
-      40           0 : bool CylindricalProjectionMap::checkDirection(const Vector3d &direction) const {
-      41           0 :         size_t bin = binFromDirection(direction);
-      42           0 :         return pdf[bin];
-      43             : }
-      44             : 
-      45             : 
-      46           0 : const std::vector<double>& CylindricalProjectionMap::getPdf() const {
-      47           0 :         return pdf;
-      48             : }
-      49             : 
-      50           5 : std::vector<double>& CylindricalProjectionMap::getPdf() {
-      51           5 :         return pdf;
-      52             : }
-      53             : 
-      54           0 : const std::vector<double>& CylindricalProjectionMap::getCdf() const {
-      55           0 :         return cdf;
-      56             : }
-      57             : 
-      58           0 : size_t CylindricalProjectionMap::getNPhi() {
-      59           0 :         return nPhi;
-      60             : }
-      61             : 
-      62           0 : size_t CylindricalProjectionMap::getNTheta() {
-      63           0 :         return nTheta;
-      64             : }
-      65             : 
-      66             : /*
-      67             :  * Cylindrical Coordinates
-      68             :  * iPhi -> [0, 2*pi]
-      69             :  * iTheta -> [0, 2]
-      70             :  *
-      71             :  * Spherical Coordinates
-      72             :  * phi -> [-pi, pi]
-      73             :  * theta -> [0, pi]
-      74             :  */
-      75           6 : size_t CylindricalProjectionMap::binFromDirection(const Vector3d& direction) const {
-      76             :         // convert to cylindrical
-      77           6 :         double phi = direction.getPhi() + M_PI;
-      78           6 :         double theta = sin(M_PI_2 - direction.getTheta()) + 1;
-      79             : 
-      80             :         // to indices
-      81           6 :         size_t iPhi = phi / sPhi;
-      82           6 :         size_t iTheta = theta / sTheta;
-      83             : 
-      84             :         // interleave
-      85           6 :         size_t bin =  iTheta * nPhi + iPhi;
-      86           6 :         return bin;
-      87             : }
-      88             : 
-      89           2 : Vector3d CylindricalProjectionMap::directionFromBin(size_t bin) const {
-      90             :         // deinterleave
-      91           2 :         double iPhi = bin % nPhi;
-      92           2 :         double iTheta = bin / nPhi;
-      93             : 
-      94             :         // any where in the bin
-      95           2 :         iPhi += Random::instance().rand();
-      96           2 :         iTheta += Random::instance().rand();
-      97             : 
-      98             :         // cylindrical Coordinates
-      99           2 :         double phi = iPhi * sPhi;
-     100           2 :         double theta = iTheta * sTheta;
-     101             : 
-     102             :         // sphericala Coordinates
-     103           2 :         phi = phi - M_PI;
-     104           2 :         theta = M_PI_2 - asin(theta - 1);
-     105             : 
-     106             :         Vector3d v;
-     107           2 :         v.setRThetaPhi(1.0, theta, phi);
-     108           2 :         return v;
-     109             : }
-     110             : 
-     111           1 : void CylindricalProjectionMap::updateCdf() const {
-     112           1 :         if (dirty) {
-     113           1 :                 cdf[0] = pdf[0];
-     114       64800 :                 for (size_t i = 1; i < pdf.size(); i++) {
-     115       64799 :                         cdf[i] = cdf[i-1] + pdf[i];
-     116             :                 }
-     117           1 :                 dirty = false;
-     118             :         }
-     119           1 : }
-     120             : 
-     121           2 : EmissionMap::EmissionMap() : minEnergy(0.0001 * EeV), maxEnergy(10000 * EeV),
-     122           2 :         nEnergy(8*2), nPhi(360), nTheta(180) {
-     123           2 :         logStep = log10(maxEnergy / minEnergy) / nEnergy;
-     124           2 : }
-     125             : 
-     126           0 : EmissionMap::EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy) : minEnergy(0.0001 * EeV), maxEnergy(10000 * EeV),
-     127           0 :         nEnergy(nEnergy), nPhi(nPhi), nTheta(nTheta) {
-     128           0 :         logStep = log10(maxEnergy / minEnergy) / nEnergy;
-     129           0 : }
-     130             : 
-     131           1 : EmissionMap::EmissionMap(size_t nPhi, size_t nTheta, size_t nEnergy, double minEnergy, double maxEnergy) : minEnergy(minEnergy), maxEnergy(maxEnergy), nEnergy(nEnergy), nPhi(nPhi), nTheta(nTheta) {
-     132           1 :         logStep = log10(maxEnergy / minEnergy) / nEnergy;
-     133           1 : }
-     134             : 
-     135           1 : double EmissionMap::energyFromBin(size_t bin) const {
-     136           1 :         return pow(10, log10(minEnergy) + logStep * bin);
-     137             : }
-     138             : 
-     139          11 : size_t EmissionMap::binFromEnergy(double energy) const {
-     140          11 :         return log10(energy / minEnergy) / logStep;
-     141             : }
-     142             : 
-     143           4 : void EmissionMap::fillMap(int pid, double energy, const Vector3d& direction, double weight) {
-     144           4 :         getMap(pid, energy)->fillBin(direction, weight);
-     145           4 : }
-     146             : 
-     147           0 : void EmissionMap::fillMap(const ParticleState& state, double weight) {
-     148           0 :         fillMap(state.getId(), state.getEnergy(), state.getDirection(), weight);
-     149           0 : }
-     150             : 
-     151           1 : EmissionMap::map_t &EmissionMap::getMaps() {
-     152           1 :         return maps;
-     153             : }
-     154             : 
-     155           2 : const EmissionMap::map_t &EmissionMap::getMaps() const {
-     156           2 :         return maps;
-     157             : }
-     158             : 
-     159           3 : bool EmissionMap::drawDirection(int pid, double energy, Vector3d& direction) const {
-     160           3 :         key_t key(pid, binFromEnergy(energy));
-     161             :         map_t::const_iterator i = maps.find(key);
-     162             : 
-     163           3 :         if (i == maps.end() || !i->second.valid()) {
-     164             :                 return false;
-     165             :         } else {
-     166           1 :                 direction = i->second->drawDirection();
-     167           1 :                 return true;
-     168             :         }
-     169             : }
-     170             : 
-     171           0 : bool EmissionMap::drawDirection(const ParticleState& state, Vector3d& direction) const {
-     172           0 :         return drawDirection(state.getId(), state.getEnergy(), direction);
-     173             : }
-     174             : 
-     175           0 : bool EmissionMap::checkDirection(int pid, double energy, const Vector3d& direction) const {
-     176           0 :         key_t key(pid, binFromEnergy(energy));
-     177             :         map_t::const_iterator i = maps.find(key);
-     178             : 
-     179           0 :         if (i == maps.end() || !i->second.valid()) {
-     180             :                 return false;
-     181             :         } else {
-     182           0 :                 return i->second->checkDirection(direction);
-     183             :         }
-     184             : }
-     185             : 
-     186           0 : bool EmissionMap::checkDirection(const ParticleState& state) const {
-     187           0 :         return checkDirection(state.getId(), state.getEnergy(), state.getDirection());
-     188             : }
-     189             : 
-     190           0 : bool EmissionMap::hasMap(int pid, double energy) {
-     191           0 :     key_t key(pid, binFromEnergy(energy));
-     192             :     map_t::iterator i = maps.find(key);
-     193           0 :     if (i == maps.end() || !i->second.valid())
-     194             :                 return false;
-     195             :         else
-     196           0 :                 return true;
-     197             : }
-     198             : 
-     199           7 : ref_ptr<CylindricalProjectionMap> EmissionMap::getMap(int pid, double energy) {
-     200           7 :         key_t key(pid, binFromEnergy(energy));
-     201             :         map_t::iterator i = maps.find(key);
-     202           7 :         if (i == maps.end() || !i->second.valid()) {
-     203           5 :                 ref_ptr<CylindricalProjectionMap> cpm = new CylindricalProjectionMap(nPhi, nTheta);
-     204           5 :                 maps[key] = cpm;
-     205             :                 return cpm;
-     206             :         } else {
-     207             :                 return i->second;
-     208             :         }
-     209             : }
-     210             : 
-     211           0 : void EmissionMap::save(const std::string &filename) {
-     212           0 :         std::ofstream out(filename.c_str());
-     213           0 :         out.imbue(std::locale("C"));
-     214             : 
-     215           0 :         for (map_t::iterator i = maps.begin(); i != maps.end(); i++) {
-     216           0 :                 if (!i->second.valid())
-     217           0 :                         continue;
-     218           0 :                 out << i->first.first << " " << i->first.second << " " << energyFromBin(i->first.second) << " ";
-     219           0 :                 out << i->second->getNPhi() << " " << i->second->getNTheta();
-     220           0 :                 const std::vector<double> &pdf = i->second->getPdf();
-     221           0 :                 for (size_t i = 0; i < pdf.size(); i++)
-     222           0 :                         out << " " << pdf[i];
-     223             :                 out << std::endl;
-     224             :         }
-     225           0 : }
-     226             : 
-     227           1 : void EmissionMap::merge(const EmissionMap *other) {
-     228           1 :         if (other == 0)
-     229             :                 return;
-     230           1 :         map_t::const_iterator i = other->getMaps().begin();
-     231           1 :         map_t::const_iterator end = other->getMaps().end();
-     232           3 :         for(;i != end; i++) {
-     233           2 :                 if (!i->second.valid())
-     234           0 :                         continue;
-     235             : 
-     236           2 :                 std::vector<double> &otherpdf = i->second->getPdf();
-     237           2 :                 ref_ptr<CylindricalProjectionMap> cpm = getMap(i->first.first, i->first.second);
-     238             : 
-     239           2 :                 if (otherpdf.size() != cpm->getPdf().size()) {
-     240           0 :                         throw std::runtime_error("PDF size mismatch!");
-     241             :                         break;
-     242             :                 }
-     243             : 
-     244      129602 :                 for (size_t k = 0; k < otherpdf.size(); k++) {
-     245      129600 :                         cpm->fillBin(k, otherpdf[k]);
-     246             :                 }
-     247             :         }
-     248             : }
-     249             : 
-     250           0 : void EmissionMap::merge(const std::string &filename) {
-     251           0 :         EmissionMap em;
-     252           0 :         em.load(filename);
-     253           0 :         merge(&em);
-     254           0 : }
-     255             : 
-     256           0 : void EmissionMap::load(const std::string &filename) {
-     257           0 :         std::ifstream in(filename.c_str());
-     258           0 :         in.imbue(std::locale("C"));
-     259             : 
-     260           0 :         while(in.good()) {
-     261           0 :                 key_t key;
-     262             :                 double tmp;
-     263             :                 size_t nPhi_, nTheta_;
-     264           0 :                 in >> key.first >> key.second >> tmp;
-     265             :                 in >> nPhi_ >> nTheta_;
-     266             : 
-     267           0 :                 if (!in.good()) {
-     268           0 :                         KISS_LOG_ERROR << "Invalid line: " << key.first << " " << key.second << " " << nPhi_ << " " << nTheta_;
-     269           0 :                         break;
-     270             :                 }
-     271             : 
-     272           0 :                 if (nPhi != nPhi_) {
-     273           0 :                         KISS_LOG_WARNING << "nPhi mismatch: " << nPhi << " " << nPhi_;
-     274             :                 }
-     275           0 :                 if (nTheta != nTheta_) {
-     276           0 :                         KISS_LOG_WARNING << "nTheta mismatch: " << nTheta << " " << nTheta_;
-     277             :                 }
-     278             : 
-     279           0 :                 ref_ptr<CylindricalProjectionMap> cpm = new CylindricalProjectionMap(nPhi_, nTheta_);
-     280           0 :                 std::vector<double> &pdf = cpm->getPdf();
-     281           0 :                 for (size_t i = 0; i < pdf.size(); i++)
-     282             :                         in >> pdf[i];
-     283             : 
-     284           0 :                 if (in.good()) {
-     285           0 :                         maps[key] = cpm;
-     286             :                         // std::cout << "added " << key.first << " " << key.second << std::endl;
-     287             :                 } else {
-     288           0 :                         KISS_LOG_WARNING << "Invalid data in line: " << key.first << " " << key.second << " " << nPhi_ << " " << nTheta_ << "\n";
-     289             :                 }
-     290             :         }
-     291             : 
-     292           0 : }
-     293             : 
-     294             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Geometry.cpp.func-sort-c.html b/doc/coverageReport/src/Geometry.cpp.func-sort-c.html deleted file mode 100644 index 14ddef6d4..000000000 --- a/doc/coverageReport/src/Geometry.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Geometry.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Geometry.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:185036.0 %
Date:2024-04-08 14:58:22Functions:61346.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_S4_0
_ZNK7crpropa11ParaxialBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ParaxialBox6normalERKNS_7Vector3IdEE0
_ZNK7crpropa5Plane14getDescriptionB5cxx11Ev0
_ZNK7crpropa5Plane6normalERKNS_7Vector3IdEE0
_ZNK7crpropa6Sphere14getDescriptionB5cxx11Ev0
_ZNK7crpropa6Sphere6normalERKNS_7Vector3IdEE0
_ZN7crpropa11ParaxialBoxC2ERKNS_7Vector3IdEES4_1
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_1
_ZNK7crpropa5Plane8distanceERKNS_7Vector3IdEE2
_ZN7crpropa6SphereC2ERKNS_7Vector3IdEEd4
_ZNK7crpropa11ParaxialBox8distanceERKNS_7Vector3IdEE6
_ZNK7crpropa6Sphere8distanceERKNS_7Vector3IdEE12
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Geometry.cpp.func.html b/doc/coverageReport/src/Geometry.cpp.func.html deleted file mode 100644 index ced667ab2..000000000 --- a/doc/coverageReport/src/Geometry.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Geometry.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Geometry.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:185036.0 %
Date:2024-04-08 14:58:22Functions:61346.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11ParaxialBoxC2ERKNS_7Vector3IdEES4_1
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_1
_ZN7crpropa5PlaneC2ERKNS_7Vector3IdEES4_S4_0
_ZN7crpropa6SphereC2ERKNS_7Vector3IdEEd4
_ZNK7crpropa11ParaxialBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ParaxialBox6normalERKNS_7Vector3IdEE0
_ZNK7crpropa11ParaxialBox8distanceERKNS_7Vector3IdEE6
_ZNK7crpropa5Plane14getDescriptionB5cxx11Ev0
_ZNK7crpropa5Plane6normalERKNS_7Vector3IdEE0
_ZNK7crpropa5Plane8distanceERKNS_7Vector3IdEE2
_ZNK7crpropa6Sphere14getDescriptionB5cxx11Ev0
_ZNK7crpropa6Sphere6normalERKNS_7Vector3IdEE0
_ZNK7crpropa6Sphere8distanceERKNS_7Vector3IdEE12
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Geometry.cpp.gcov.html b/doc/coverageReport/src/Geometry.cpp.gcov.html deleted file mode 100644 index 23f52e359..000000000 --- a/doc/coverageReport/src/Geometry.cpp.gcov.html +++ /dev/null @@ -1,200 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Geometry.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Geometry.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:185036.0 %
Date:2024-04-08 14:58:22Functions:61346.2 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include <limits>
-       2             : #include <cmath>
-       3             : #include "kiss/logger.h"
-       4             : #include "crpropa/Geometry.h"
-       5             : 
-       6             : #include <iostream>
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10             : // Plane ------------------------------------------------------------------
-      11           1 : Plane::Plane(const Vector3d& _x0, const Vector3d& _n) : x0(_x0), n(_n) {
-      12           1 : };
-      13             : 
-      14           0 : Plane::Plane(const Vector3d& _x0, const Vector3d& v1,const Vector3d& v2) : x0(_x0), n(0,0,0) {
-      15             :         n = v1.cross(v2);
-      16             :         n /= n.getR();
-      17           0 : };
-      18             : 
-      19           2 : double Plane::distance(const Vector3d &x) const {
-      20             :         Vector3d dX = x - x0;
-      21           2 :         return n.dot(dX);
-      22             : };
-      23             : 
-      24           0 : std::string Plane::getDescription() const {
-      25           0 :         std::stringstream ss;
-      26             :         ss << "Plane: " << std::endl
-      27           0 :            << "   x0: " << x0 << std::endl
-      28           0 :            << "    n: " << n << std::endl;
-      29           0 :         return ss.str();
-      30           0 : };
-      31             : 
-      32           0 : Vector3d Plane::normal(const Vector3d& point) const {
-      33           0 :         return n;
-      34             : }
-      35             : 
-      36             : 
-      37             : // Sphere ------------------------------------------------------------------
-      38           4 : Sphere::Sphere(const Vector3d& _center, double _radius) : center(_center), radius(_radius) {
-      39           4 : };
-      40             : 
-      41          12 : double Sphere::distance(const Vector3d &point) const {
-      42             :         Vector3d dR = point - center;
-      43          12 :         return dR.getR() - radius;
-      44             : }
-      45             : 
-      46           0 : Vector3d Sphere::normal(const Vector3d& point) const {
-      47             :         Vector3d d = point - center;
-      48           0 :         return d.getUnitVector();
-      49             : }
-      50             : 
-      51           0 : std::string Sphere::getDescription() const {
-      52           0 :         std::stringstream ss;
-      53             :         ss << "Sphere: " << std::endl
-      54           0 :                         << "   Center: " << center << std::endl
-      55           0 :                         << "   Radius: " << radius << std::endl;
-      56           0 :         return ss.str();
-      57           0 : };
-      58             : 
-      59             : 
-      60             : // ParaxialBox -------------------------------------------------------------
-      61           1 : ParaxialBox::ParaxialBox(const Vector3d& _corner, const Vector3d& _size) : corner(_corner), size(_size) {
-      62           1 : };
-      63             : 
-      64           6 : double ParaxialBox::distance(const Vector3d &point) const {
-      65             :         Vector3d X = point - corner - size/2.;
-      66             : 
-      67             :         // inside the cube
-      68           6 :         if ((fabs(X.x) <= size.x/2.) and (fabs(X.y) <= size.y/2.) and (fabs(X.z) <= size.z/2.)) { 
-      69             :                 Vector3d Xp = size/2. - X.abs();
-      70           3 :                 double d = std::min(Xp.x, std::min(Xp.y, Xp.z));
-      71             : 
-      72           3 :                 return -1. * d;
-      73             :         }
-      74             : 
-      75           3 :         double a = std::max(0., fabs(X.x) - size.x/2.);
-      76           3 :         double b = std::max(0., fabs(X.y) - size.y/2.);
-      77           3 :         double c = std::max(0., fabs(X.z) - size.z/2.);
-      78             : 
-      79           3 :         return sqrt(a*a + b*b +c*c);
-      80             : }
-      81             : 
-      82           0 : Vector3d ParaxialBox::normal(const Vector3d& point) const {
-      83             :         Vector3d d = (point - corner).abs();
-      84             :         Vector3d d2 = d + size;
-      85             :         Vector3d n;
-      86             :         double dmin = std::numeric_limits<double>::infinity();
-      87           0 :         if (d.x < dmin) {
-      88             :                 dmin = d.x;
-      89             :                 n = Vector3d(-1, 0, 0);
-      90             :         }
-      91           0 :         if (d.y < dmin) {
-      92             :                 dmin = d.y;
-      93             :                 n = Vector3d(0, -1, 0);
-      94             :         }
-      95           0 :         if (d.z < dmin) {
-      96             :                 dmin = d.z;
-      97             :                 n = Vector3d(0, 0, -1);
-      98             :         }
-      99           0 :         if (d2.x < dmin) {
-     100             :                 dmin = d2.x;
-     101             :                 n = Vector3d(1, 0, 0);
-     102             :         }
-     103           0 :         if (d2.y < dmin) {
-     104             :                 dmin = d2.y;
-     105             :                 n = Vector3d(0, 1, 0);
-     106             :         }
-     107           0 :         if (d2.z < dmin) {
-     108             :                 // dmin = d2.z;
-     109             :                 n = Vector3d(0, 0, 1);
-     110             :         }
-     111             : 
-     112           0 :         return n;
-     113             : }
-     114             : 
-     115           0 : std::string ParaxialBox::getDescription() const {
-     116           0 :         std::stringstream ss;
-     117             :         ss << "ParaxialBox: " << std::endl
-     118           0 :                  << "   corner: " << corner << std::endl
-     119           0 :                  << "     size: " << size << std::endl;
-     120           0 :         return ss.str();
-     121           0 : };
-     122             : 
-     123             : 
-     124             : } // namespace
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/GridTools.cpp.func-sort-c.html b/doc/coverageReport/src/GridTools.cpp.func-sort-c.html deleted file mode 100644 index 14424d83d..000000000 --- a/doc/coverageReport/src/GridTools.cpp.func-sort-c.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/GridTools.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - GridTools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6724527.3 %
Date:2024-04-08 14:58:22Functions:71936.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa17fromMagneticFieldENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa17gridPowerSpectrumENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa23rmsFieldStrengthPerAxisENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa25fromMagneticFieldStrengthENS_7ref_ptrINS_4GridIfEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridIfEEEEd0
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa15meanFieldVectorENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE1
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE11
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEd11
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/GridTools.cpp.func.html b/doc/coverageReport/src/GridTools.cpp.func.html deleted file mode 100644 index 0781b93b7..000000000 --- a/doc/coverageReport/src/GridTools.cpp.func.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/GridTools.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - GridTools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6724527.3 %
Date:2024-04-08 14:58:22Functions:71936.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa13dumpGridToTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa15loadGridFromTxtENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa15meanFieldVectorENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE1
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE11
_ZN7crpropa16rmsFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa17fromMagneticFieldENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa17gridPowerSpectrumENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17meanFieldStrengthENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa23rmsFieldStrengthPerAxisENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa25fromMagneticFieldStrengthENS_7ref_ptrINS_4GridIfEEEENS0_INS_13MagneticFieldEEE0
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa8dumpGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd1
_ZN7crpropa8loadGridENS_7ref_ptrINS_4GridIfEEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd0
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEd11
_ZN7crpropa9scaleGridENS_7ref_ptrINS_4GridIfEEEEd0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/GridTools.cpp.gcov.html b/doc/coverageReport/src/GridTools.cpp.gcov.html deleted file mode 100644 index 20f0163b7..000000000 --- a/doc/coverageReport/src/GridTools.cpp.gcov.html +++ /dev/null @@ -1,491 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/GridTools.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - GridTools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6724527.3 %
Date:2024-04-08 14:58:22Functions:71936.8 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/GridTools.h"
-       2             : #include "crpropa/magneticField/MagneticField.h"
-       3             : 
-       4             : #include <fstream>
-       5             : #include <sstream>
-       6             : 
-       7             : namespace crpropa {
-       8             : 
-       9           0 : void scaleGrid(ref_ptr<Grid1f> grid, double a) {
-      10           0 :         for (int ix = 0; ix < grid->getNx(); ix++)
-      11           0 :                 for (int iy = 0; iy < grid->getNy(); iy++)
-      12           0 :                         for (int iz = 0; iz < grid->getNz(); iz++)
-      13           0 :                                 grid->get(ix, iy, iz) *= a;
-      14           0 : }
-      15             : 
-      16          11 : void scaleGrid(ref_ptr<Grid3f> grid, double a) {
-      17         654 :         for (int ix = 0; ix < grid->getNx(); ix++)
-      18       41612 :                 for (int iy = 0; iy < grid->getNy(); iy++)
-      19     2662436 :                         for (int iz = 0; iz < grid->getNz(); iz++)
-      20     2621467 :                                 grid->get(ix, iy, iz) *= a;
-      21          11 : }
-      22             : 
-      23           1 : Vector3f meanFieldVector(ref_ptr<Grid3f> grid) {
-      24             :         size_t Nx = grid->getNx();
-      25             :         size_t Ny = grid->getNy();
-      26             :         size_t Nz = grid->getNz();
-      27             :         Vector3f mean(0.);
-      28          65 :         for (int ix = 0; ix < Nx; ix++)
-      29        4160 :                 for (int iy = 0; iy < Ny; iy++)
-      30      266240 :                         for (int iz = 0; iz < Nz; iz++)
-      31             :                                 mean += grid->get(ix, iy, iz);
-      32           1 :         return mean / Nx / Ny / Nz;
-      33             : }
-      34             : 
-      35           0 : double meanFieldStrength(ref_ptr<Grid3f> grid) {
-      36             :         size_t Nx = grid->getNx();
-      37             :         size_t Ny = grid->getNy();
-      38             :         size_t Nz = grid->getNz();
-      39             :         double mean = 0;
-      40           0 :         for (int ix = 0; ix < Nx; ix++)
-      41           0 :                 for (int iy = 0; iy < Ny; iy++)
-      42           0 :                         for (int iz = 0; iz < Nz; iz++)
-      43           0 :                                 mean += grid->get(ix, iy, iz).getR();
-      44           0 :         return mean / Nx / Ny / Nz;
-      45             : }
-      46             : 
-      47           0 : double meanFieldStrength(ref_ptr<Grid1f> grid) {
-      48             :         size_t Nx = grid->getNx();
-      49             :         size_t Ny = grid->getNy();
-      50             :         size_t Nz = grid->getNz();
-      51             :         double mean = 0;
-      52           0 :         for (int ix = 0; ix < Nx; ix++)
-      53           0 :                 for (int iy = 0; iy < Ny; iy++)
-      54           0 :                         for (int iz = 0; iz < Nz; iz++)
-      55           0 :                                 mean += grid->get(ix, iy, iz);
-      56           0 :         return mean / Nx / Ny / Nz;
-      57             : }
-      58             : 
-      59          11 : double rmsFieldStrength(ref_ptr<Grid3f> grid) {
-      60             :         size_t Nx = grid->getNx();
-      61             :         size_t Ny = grid->getNy();
-      62             :         size_t Nz = grid->getNz();
-      63             :         double sumV2 = 0;
-      64         715 :         for (int ix = 0; ix < Nx; ix++)
-      65       45760 :                 for (int iy = 0; iy < Ny; iy++)
-      66     2928640 :                         for (int iz = 0; iz < Nz; iz++)
-      67     2883584 :                                 sumV2 += grid->get(ix, iy, iz).getR2();
-      68          11 :         return std::sqrt(sumV2 / Nx / Ny / Nz);
-      69             : }
-      70             : 
-      71           0 : double rmsFieldStrength(ref_ptr<Grid1f> grid) {
-      72             :         size_t Nx = grid->getNx();
-      73             :         size_t Ny = grid->getNy();
-      74             :         size_t Nz = grid->getNz();
-      75             :         double sumV2 = 0;
-      76           0 :         for (int ix = 0; ix < Nx; ix++)
-      77           0 :                 for (int iy = 0; iy < Ny; iy++)
-      78           0 :                         for (int iz = 0; iz < Nz; iz++)
-      79           0 :                                 sumV2 += pow(grid->get(ix, iy, iz), 2);
-      80           0 :         return std::sqrt(sumV2 / Nx / Ny / Nz);
-      81             : }
-      82             : 
-      83           0 : std::array<float, 3> rmsFieldStrengthPerAxis(ref_ptr<Grid3f> grid) {
-      84             :     size_t Nx = grid->getNx();
-      85             :     size_t Ny = grid->getNy();
-      86             :     size_t Nz = grid->getNz();
-      87             :     float sumV2_x = 0;
-      88             :     float sumV2_y = 0;
-      89             :     float sumV2_z = 0;
-      90           0 :     for (int ix = 0; ix < Nx; ix++)
-      91           0 :         for (int iy = 0; iy < Ny; iy++)
-      92           0 :             for (int iz = 0; iz < Nz; iz++) {
-      93           0 :                 sumV2_x += pow(grid->get(ix, iy, iz).x, 2);
-      94           0 :                 sumV2_y += pow(grid->get(ix, iy, iz).y, 2);
-      95           0 :                 sumV2_z += pow(grid->get(ix, iy, iz).z, 2);
-      96             :             }
-      97             :     return {
-      98           0 :         std::sqrt(sumV2_x / Nx / Ny / Nz),
-      99           0 :         std::sqrt(sumV2_y / Nx / Ny / Nz),
-     100           0 :         std::sqrt(sumV2_z / Nx / Ny / Nz)
-     101           0 :     };
-     102             : }
-     103             : 
-     104           0 : void fromMagneticField(ref_ptr<Grid3f> grid, ref_ptr<MagneticField> field) {
-     105             :         Vector3d origin = grid->getOrigin();
-     106             :         Vector3d spacing = grid->getSpacing();
-     107             :         size_t Nx = grid->getNx();
-     108             :         size_t Ny = grid->getNy();
-     109             :         size_t Nz = grid->getNz();
-     110           0 :         for (size_t ix = 0; ix < Nx; ix++)
-     111           0 :                 for (size_t iy = 0; iy < Ny; iy++)
-     112           0 :                         for (size_t iz = 0; iz < Nz; iz++) {
-     113           0 :                                 Vector3d pos = Vector3d(double(ix) + 0.5, double(iy) + 0.5, double(iz) + 0.5) * spacing + origin;
-     114           0 :                                 Vector3d B = field->getField(pos);
-     115             :                                 grid->get(ix, iy, iz) = B;
-     116             :         }
-     117           0 : }
-     118             : 
-     119           0 : void fromMagneticFieldStrength(ref_ptr<Grid1f> grid, ref_ptr<MagneticField> field) {
-     120             :         Vector3d origin = grid->getOrigin();
-     121             :         Vector3d spacing = grid->getSpacing();
-     122             :         size_t Nx = grid->getNx();
-     123             :         size_t Ny = grid->getNy();
-     124             :         size_t Nz = grid->getNz();
-     125           0 :         for (size_t ix = 0; ix < Nx; ix++)
-     126           0 :                 for (size_t iy = 0; iy < Ny; iy++)
-     127           0 :                         for (size_t iz = 0; iz < Nz; iz++) {
-     128           0 :                                 Vector3d pos = Vector3d(double(ix) + 0.5, double(iy) + 0.5, double(iz) + 0.5) * spacing + origin;
-     129           0 :                                 double s = field->getField(pos).getR();
-     130           0 :                                 grid->get(ix, iy, iz) = s;
-     131             :         }
-     132           0 : }
-     133             : 
-     134           1 : void loadGrid(ref_ptr<Grid3f> grid, std::string filename, double c) {
-     135           1 :         std::ifstream fin(filename.c_str(), std::ios::binary);
-     136           1 :         if (!fin) {
-     137           0 :                 std::stringstream ss;
-     138           0 :                 ss << "load Grid3f: " << filename << " not found";
-     139           0 :                 throw std::runtime_error(ss.str());
-     140           0 :         }
-     141             : 
-     142             :         // get length of file and compare to size of grid
-     143           1 :         fin.seekg(0, fin.end);
-     144           1 :         size_t length = fin.tellg() / sizeof(float);
-     145           1 :         fin.seekg (0, fin.beg);
-     146             : 
-     147             :         size_t nx = grid->getNx();
-     148             :         size_t ny = grid->getNy();
-     149             :         size_t nz = grid->getNz();
-     150             : 
-     151           1 :         if (length != (3 * nx * ny * nz))
-     152           0 :                 throw std::runtime_error("loadGrid: file and grid size do not match");
-     153             : 
-     154           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     155          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     156          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     157             :                                 Vector3f &b = grid->get(ix, iy, iz);
-     158          27 :                                 fin.read((char*) &(b.x), sizeof(float));
-     159          27 :                                 fin.read((char*) &(b.y), sizeof(float));
-     160          27 :                                 fin.read((char*) &(b.z), sizeof(float));
-     161          27 :                                 b *= c;
-     162             :                         }
-     163             :                 }
-     164             :         }
-     165           1 :         fin.close();
-     166           1 : }
-     167             : 
-     168           0 : void loadGrid(ref_ptr<Grid1f> grid, std::string filename, double c) {
-     169           0 :         std::ifstream fin(filename.c_str(), std::ios::binary);
-     170           0 :         if (!fin) {
-     171           0 :                 std::stringstream ss;
-     172           0 :                 ss << "load Grid1f: " << filename << " not found";
-     173           0 :                 throw std::runtime_error(ss.str());
-     174           0 :         }
-     175             : 
-     176             :         // get length of file and compare to size of grid
-     177           0 :         fin.seekg(0, fin.end);
-     178           0 :         size_t length = fin.tellg() / sizeof(float);
-     179           0 :         fin.seekg (0, fin.beg);
-     180             : 
-     181             :         size_t nx = grid->getNx();
-     182             :         size_t ny = grid->getNy();
-     183             :         size_t nz = grid->getNz();
-     184             : 
-     185           0 :         if (length != (nx * ny * nz))
-     186           0 :                 throw std::runtime_error("loadGrid: file and grid size do not match");
-     187             : 
-     188           0 :         for (int ix = 0; ix < nx; ix++) {
-     189           0 :                 for (int iy = 0; iy < ny; iy++) {
-     190           0 :                         for (int iz = 0; iz < nz; iz++) {
-     191             :                                 float &b = grid->get(ix, iy, iz);
-     192           0 :                                 fin.read((char*) &b, sizeof(float));
-     193           0 :                                 b *= c;
-     194             :                         }
-     195             :                 }
-     196             :         }
-     197           0 :         fin.close();
-     198           0 : }
-     199             : 
-     200           1 : void dumpGrid(ref_ptr<Grid3f> grid, std::string filename, double c) {
-     201           1 :         std::ofstream fout(filename.c_str(), std::ios::binary);
-     202           1 :         if (!fout) {
-     203           0 :                 std::stringstream ss;
-     204           0 :                 ss << "dump Grid3f: " << filename << " not found";
-     205           0 :                 throw std::runtime_error(ss.str());
-     206           0 :         }
-     207           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     208          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     209          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     210          27 :                                 Vector3f b = grid->get(ix, iy, iz) * c;
-     211          27 :                                 fout.write((char*) &(b.x), sizeof(float));
-     212          27 :                                 fout.write((char*) &(b.y), sizeof(float));
-     213          27 :                                 fout.write((char*) &(b.z), sizeof(float));
-     214             :                         }
-     215             :                 }
-     216             :         }
-     217           1 :         fout.close();
-     218           1 : }
-     219             : 
-     220           0 : void dumpGrid(ref_ptr<Grid1f> grid, std::string filename, double c) {
-     221           0 :         std::ofstream fout(filename.c_str(), std::ios::binary);
-     222           0 :         if (!fout) {
-     223           0 :                 std::stringstream ss;
-     224           0 :                 ss << "dump Grid1f: " << filename << " not found";
-     225           0 :                 throw std::runtime_error(ss.str());
-     226           0 :         }
-     227           0 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     228           0 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     229           0 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     230           0 :                                 float b = grid->get(ix, iy, iz) * c;
-     231           0 :                                 fout.write((char*) &b, sizeof(float));
-     232             :                         }
-     233             :                 }
-     234             :         }
-     235           0 :         fout.close();
-     236           0 : }
-     237             : 
-     238           1 : void loadGridFromTxt(ref_ptr<Grid3f> grid, std::string filename, double c) {
-     239           1 :         std::ifstream fin(filename.c_str());
-     240           1 :         if (!fin) {
-     241           0 :                 std::stringstream ss;
-     242           0 :                 ss << "load Grid3f: " << filename << " not found";
-     243           0 :                 throw std::runtime_error(ss.str());
-     244           0 :         }
-     245             :         // skip header lines
-     246           1 :         while (fin.peek() == '#')
-     247           0 :                 fin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-     248             : 
-     249           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     250          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     251          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     252             :                                 Vector3f &b = grid->get(ix, iy, iz);
-     253          27 :                                 fin >> b.x >> b.y >> b.z;
-     254          27 :                                 b *= c;
-     255          27 :                                 if (fin.eof())
-     256           0 :                                         throw std::runtime_error("load Grid3f: file too short");
-     257             :                         }
-     258             :                 }
-     259             :         }
-     260           1 :         fin.close();
-     261           1 : }
-     262             : 
-     263           0 : void loadGridFromTxt(ref_ptr<Grid1f> grid, std::string filename, double c) {
-     264           0 :         std::ifstream fin(filename.c_str());
-     265           0 :         if (!fin) {
-     266           0 :                 std::stringstream ss;
-     267           0 :                 ss << "load Grid1f: " << filename << " not found";
-     268           0 :                 throw std::runtime_error(ss.str());
-     269           0 :         }
-     270             :         // skip header lines
-     271           0 :         while (fin.peek() == '#')
-     272           0 :                 fin.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-     273             : 
-     274           0 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     275           0 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     276           0 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     277             :                                 float &b = grid->get(ix, iy, iz);
-     278             :                                 fin >> b;
-     279           0 :                                 b *= c;
-     280           0 :                                 if (fin.eof())
-     281           0 :                                         throw std::runtime_error("load Grid1f: file too short");
-     282             :                         }
-     283             :                 }
-     284             :         }
-     285           0 :         fin.close();
-     286           0 : }
-     287             : 
-     288           1 : void dumpGridToTxt(ref_ptr<Grid3f> grid, std::string filename, double c) {
-     289           1 :         std::ofstream fout(filename.c_str());
-     290           1 :         if (!fout) {
-     291           0 :                 std::stringstream ss;
-     292           0 :                 ss << "dump Grid3f: " << filename << " not found";
-     293           0 :                 throw std::runtime_error(ss.str());
-     294           0 :         }
-     295           4 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     296          12 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     297          36 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     298          27 :                                 Vector3f b = grid->get(ix, iy, iz) * c;
-     299          27 :                                 fout << b << "\n";
-     300             :                         }
-     301             :                 }
-     302             :         }
-     303           1 :         fout.close();
-     304           1 : }
-     305             : 
-     306           0 : void dumpGridToTxt(ref_ptr<Grid1f> grid, std::string filename, double c) {
-     307           0 :         std::ofstream fout(filename.c_str());
-     308           0 :         if (!fout) {
-     309           0 :                 std::stringstream ss;
-     310           0 :                 ss << "dump Grid1f: " << filename << " not found";
-     311           0 :                 throw std::runtime_error(ss.str());
-     312           0 :         }
-     313           0 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     314           0 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     315           0 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     316           0 :                                 float b = grid->get(ix, iy, iz) * c;
-     317           0 :                                 fout << b << "\n";
-     318             :                         }
-     319             :                 }
-     320             :         }
-     321           0 :         fout.close();
-     322           0 : }
-     323             : 
-     324             : #ifdef CRPROPA_HAVE_FFTW3F
-     325             : 
-     326           0 : std::vector<std::pair<int, float>> gridPowerSpectrum(ref_ptr<Grid3f> grid) {
-     327             : 
-     328           0 :   double rms = rmsFieldStrength(grid);
-     329             :   size_t n = grid->getNx(); // size of array
-     330             : 
-     331             :   // arrays to hold the complex vector components of the B(k)-field
-     332             :   fftwf_complex *Bkx, *Bky, *Bkz;
-     333           0 :   Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n);
-     334           0 :   Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n);
-     335           0 :   Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n);
-     336             : 
-     337             :   fftwf_complex *Bx = (fftwf_complex *)Bkx;
-     338             :   fftwf_complex *By = (fftwf_complex *)Bky;
-     339             :   fftwf_complex *Bz = (fftwf_complex *)Bkz;
-     340             : 
-     341             :   // save to temp
-     342             :   int i;
-     343           0 :   for (size_t ix = 0; ix < n; ix++) {
-     344           0 :     for (size_t iy = 0; iy < n; iy++) {
-     345           0 :       for (size_t iz = 0; iz < n; iz++) {
-     346           0 :         i = ix * n * n + iy * n + iz;
-     347             :         Vector3<float> &b = grid->get(ix, iy, iz);
-     348           0 :         Bx[i][0] = b.x / rms;
-     349           0 :         By[i][0] = b.y / rms;
-     350           0 :         Bz[i][0] = b.z / rms;
-     351             :       }
-     352             :     }
-     353             :   }
-     354             : 
-     355             :   // in-place, real to complex, inverse Fourier transformation on each component
-     356             :   // note that the last elements of B(x) are unused now
-     357             :   fftwf_plan plan_x =
-     358           0 :       fftwf_plan_dft_3d(n, n, n, Bx, Bkx, FFTW_FORWARD, FFTW_ESTIMATE);
-     359           0 :   fftwf_execute(plan_x);
-     360           0 :   fftwf_destroy_plan(plan_x);
-     361             : 
-     362             :   fftwf_plan plan_y =
-     363           0 :       fftwf_plan_dft_3d(n, n, n, By, Bky, FFTW_FORWARD, FFTW_ESTIMATE);
-     364           0 :   fftwf_execute(plan_y);
-     365           0 :   fftwf_destroy_plan(plan_y);
-     366             : 
-     367             :   fftwf_plan plan_z =
-     368           0 :       fftwf_plan_dft_3d(n, n, n, Bz, Bkz, FFTW_FORWARD, FFTW_ESTIMATE);
-     369           0 :   fftwf_execute(plan_z);
-     370           0 :   fftwf_destroy_plan(plan_z);
-     371             : 
-     372             :   float power;
-     373             :   std::map<size_t, std::pair<float, int>> spectrum;
-     374             :   int k;
-     375             : 
-     376           0 :   for (size_t ix = 0; ix < n; ix++) {
-     377           0 :     for (size_t iy = 0; iy < n; iy++) {
-     378           0 :       for (size_t iz = 0; iz < n; iz++) {
-     379           0 :         i = ix * n * n + iy * n + iz;
-     380           0 :         k = static_cast<int>(
-     381           0 :             std::floor(std::sqrt(ix * ix + iy * iy + iz * iz)));
-     382           0 :         if (k > n / 2. || k == 0)
-     383           0 :           continue;
-     384           0 :         power = ((Bkx[i][0] * Bkx[i][0] + Bkx[i][1] * Bkx[i][1]) +
-     385           0 :                  (Bky[i][0] * Bky[i][0] + Bky[i][1] * Bky[i][1]) +
-     386           0 :                  (Bkz[i][0] * Bkz[i][0] + Bkz[i][1] * Bkz[i][1]));
-     387           0 :         if (spectrum.find(k) == spectrum.end()) {
-     388           0 :           spectrum[k].first = power;
-     389           0 :           spectrum[k].second = 1;
-     390             :         } else {
-     391           0 :           spectrum[k].first += power;
-     392           0 :           spectrum[k].second += 1;
-     393             :         }
-     394             :       }
-     395             :     }
-     396             :   }
-     397             : 
-     398           0 :   fftwf_free(Bkx);
-     399           0 :   fftwf_free(Bky);
-     400           0 :   fftwf_free(Bkz);
-     401             : 
-     402             :   std::vector<std::pair<int, float>> points;
-     403           0 :   for (std::map<size_t, std::pair<float, int>>::iterator it = spectrum.begin();
-     404           0 :        it != spectrum.end(); ++it) {
-     405           0 :     points.push_back(
-     406           0 :         std::make_pair(it->first, (it->second).first / (it->second).second));
-     407             :   }
-     408             : 
-     409           0 :   return points;
-     410             : }
-     411             : 
-     412             : #endif // CRPROPA_HAVE_FFTW3F
-     413             : 
-     414             : 
-     415             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Module.cpp.func-sort-c.html b/doc/coverageReport/src/Module.cpp.func-sort-c.html deleted file mode 100644 index 16f3b25e6..000000000 --- a/doc/coverageReport/src/Module.cpp.func-sort-c.html +++ /dev/null @@ -1,120 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Module.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Module.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:374877.1 %
Date:2024-04-08 14:58:22Functions:91275.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17AbstractCondition13setAcceptFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_0
_ZN7crpropa17AbstractCondition23setMakeAcceptedInactiveEb0
_ZNK7crpropa6Module14getDescriptionB5cxx11Ev0
_ZN7crpropa17AbstractCondition13setRejectFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_1
_ZN7crpropa17AbstractCondition23setMakeRejectedInactiveEb1
_ZN7crpropa17AbstractCondition8onAcceptEPNS_6ModuleE1
_ZN7crpropa17AbstractCondition8onRejectEPNS_6ModuleE1
_ZNK7crpropa17AbstractCondition6acceptEPNS_9CandidateE2
_ZN7crpropa17AbstractConditionC2Ev33
_ZN7crpropa6ModuleC2Ev209
_ZN7crpropa6Module14setDescriptionERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE365
_ZNK7crpropa17AbstractCondition6rejectEPNS_9CandidateE1126
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Module.cpp.func.html b/doc/coverageReport/src/Module.cpp.func.html deleted file mode 100644 index b0c8fb43e..000000000 --- a/doc/coverageReport/src/Module.cpp.func.html +++ /dev/null @@ -1,120 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Module.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Module.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:374877.1 %
Date:2024-04-08 14:58:22Functions:91275.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17AbstractCondition13setAcceptFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_0
_ZN7crpropa17AbstractCondition13setRejectFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_1
_ZN7crpropa17AbstractCondition23setMakeAcceptedInactiveEb0
_ZN7crpropa17AbstractCondition23setMakeRejectedInactiveEb1
_ZN7crpropa17AbstractCondition8onAcceptEPNS_6ModuleE1
_ZN7crpropa17AbstractCondition8onRejectEPNS_6ModuleE1
_ZN7crpropa17AbstractConditionC2Ev33
_ZN7crpropa6Module14setDescriptionERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE365
_ZN7crpropa6ModuleC2Ev209
_ZNK7crpropa17AbstractCondition6acceptEPNS_9CandidateE2
_ZNK7crpropa17AbstractCondition6rejectEPNS_9CandidateE1126
_ZNK7crpropa6Module14getDescriptionB5cxx11Ev0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Module.cpp.gcov.html b/doc/coverageReport/src/Module.cpp.gcov.html deleted file mode 100644 index 3dc4592a3..000000000 --- a/doc/coverageReport/src/Module.cpp.gcov.html +++ /dev/null @@ -1,156 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Module.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Module.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:374877.1 %
Date:2024-04-08 14:58:22Functions:91275.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Module.h"
-       2             : 
-       3             : #include <typeinfo>
-       4             : 
-       5             : namespace crpropa {
-       6             : 
-       7         209 : Module::Module() {
-       8             :         const std::type_info &info = typeid(*this);
-       9         209 :         setDescription(info.name());
-      10         209 : }
-      11             : 
-      12           0 : std::string Module::getDescription() const {
-      13           0 :         return description;
-      14             : }
-      15             : 
-      16         365 : void Module::setDescription(const std::string &d) {
-      17         365 :         description = d;
-      18         365 : }
-      19             : 
-      20          33 : AbstractCondition::AbstractCondition() :
-      21          33 :                 makeRejectedInactive(true), makeAcceptedInactive(false), rejectFlagKey(
-      22          33 :                                 "Rejected") {
-      23             : 
-      24          33 : }
-      25             : 
-      26        1126 : void AbstractCondition::reject(Candidate *candidate) const {
-      27        1126 :         if (!candidate)
-      28             :                 return;
-      29             : 
-      30        1126 :         if (rejectAction.valid())
-      31           5 :                 rejectAction->process(candidate);
-      32             : 
-      33        1126 :         if (!rejectFlagKey.empty())
-      34        1126 :                 candidate->setProperty(rejectFlagKey, rejectFlagValue);
-      35             : 
-      36        1126 :         if (makeRejectedInactive)
-      37        1125 :                 candidate->setActive(false);
-      38             : }
-      39             : 
-      40           2 : void AbstractCondition::accept(Candidate *candidate) const {
-      41           2 :         if (!candidate)
-      42             :                 return;
-      43             : 
-      44           2 :         if (acceptAction.valid())
-      45           2 :                 acceptAction->process(candidate);
-      46             : 
-      47           2 :         if (!acceptFlagKey.empty())
-      48           0 :                 candidate->setProperty(acceptFlagKey, acceptFlagValue);
-      49             : 
-      50           2 :         if (makeAcceptedInactive)
-      51           0 :                 candidate->setActive(false);
-      52             : }
-      53             : 
-      54           1 : void AbstractCondition::setMakeRejectedInactive(bool deactivate) {
-      55           1 :         makeRejectedInactive = deactivate;
-      56           1 : }
-      57             : 
-      58           0 : void AbstractCondition::setMakeAcceptedInactive(bool deactivate) {
-      59           0 :         makeAcceptedInactive = deactivate;
-      60           0 : }
-      61             : 
-      62           1 : void AbstractCondition::onReject(Module *action) {
-      63           1 :         rejectAction = action;
-      64           1 : }
-      65             : 
-      66           1 : void AbstractCondition::onAccept(Module *action) {
-      67           1 :         acceptAction = action;
-      68           1 : }
-      69             : 
-      70           1 : void AbstractCondition::setRejectFlag(std::string key, std::string value) {
-      71           1 :         rejectFlagKey = key;
-      72           1 :         rejectFlagValue = value;
-      73           1 : }
-      74             : 
-      75           0 : void AbstractCondition::setAcceptFlag(std::string key, std::string value) {
-      76           0 :         acceptFlagKey = key;
-      77           0 :         acceptFlagValue = value;
-      78           0 : }
-      79             : 
-      80             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleID.cpp.func-sort-c.html b/doc/coverageReport/src/ParticleID.cpp.func-sort-c.html deleted file mode 100644 index 02a39f19f..000000000 --- a/doc/coverageReport/src/ParticleID.cpp.func-sort-c.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleID.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleID.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:163053.3 %
Date:2024-04-08 14:58:22Functions:4580.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15convertIdToNameB5cxx11Ei0
_ZN7crpropa9nucleusIdEii45149
_ZN7crpropa10massNumberEi202819
_ZN7crpropa12chargeNumberEi364529
_ZN7crpropa9isNucleusEi20370056
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleID.cpp.func.html b/doc/coverageReport/src/ParticleID.cpp.func.html deleted file mode 100644 index 70f77a588..000000000 --- a/doc/coverageReport/src/ParticleID.cpp.func.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleID.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleID.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:163053.3 %
Date:2024-04-08 14:58:22Functions:4580.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10massNumberEi202819
_ZN7crpropa12chargeNumberEi364529
_ZN7crpropa15convertIdToNameB5cxx11Ei0
_ZN7crpropa9isNucleusEi20370056
_ZN7crpropa9nucleusIdEii45149
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleID.cpp.gcov.html b/doc/coverageReport/src/ParticleID.cpp.gcov.html deleted file mode 100644 index 917e4a925..000000000 --- a/doc/coverageReport/src/ParticleID.cpp.gcov.html +++ /dev/null @@ -1,130 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleID.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleID.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:163053.3 %
Date:2024-04-08 14:58:22Functions:4580.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/ParticleID.h"
-       2             : 
-       3             : #include "HepPID/ParticleIDMethods.hh"
-       4             : #include "HepPID/ParticleName.hh"
-       5             : #include "kiss/convert.h"
-       6             : 
-       7             : #include <string>
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11       45149 : int nucleusId(int a, int z) {
-      12       45149 :         if (z < 0)
-      13           0 :                 throw std::runtime_error(
-      14           0 :                                 "crpropa::Nucleus: no nucleus with Z < 0, A=" + kiss::str(a) + " Z="
-      15           0 :                                                 + kiss::str(z));
-      16       45149 :         if (a < 1)
-      17           0 :                 throw std::runtime_error(
-      18           0 :                                 "crpropa::Nucleus: no nucleus with A < 1, A=" + kiss::str(a) + " Z="
-      19           0 :                                                 + kiss::str(z));
-      20       45149 :         if (a < z)
-      21           1 :                 throw std::runtime_error(
-      22           2 :                                 "crpropa::Nucleus: no nucleus with A < Z, A=" + kiss::str(a) + " Z="
-      23           4 :                                                 + kiss::str(z));
-      24       45148 :         return 1000000000 + z * 10000 + a * 10;
-      25             : }
-      26             : 
-      27      364529 : int chargeNumber(int id) {
-      28      364529 :         return HepPID::Z(id);
-      29             : }
-      30             : 
-      31      202819 : int massNumber(int id) {
-      32      202819 :         if (id == 2112)
-      33             :                 return 1;
-      34      202818 :         return HepPID::A(id);
-      35             : }
-      36             : 
-      37    20370056 : bool isNucleus(int id) {
-      38    20370056 :         if (id == 2112)
-      39             :                 return true; // consider neutron as nucleus
-      40    20370056 :         return HepPID::isNucleus(id);
-      41             : }
-      42             : 
-      43           0 : std::string convertIdToName(int id) {
-      44             :         // handle a few extra cases that HepPID doesn't like
-      45           0 :         if (id == 1000000010) // neutron
-      46           0 :                 id = 2112;
-      47           0 :         if (id == -1000000010) // anti-neutron
-      48           0 :                 id = -2112;
-      49           0 :         if (id == -1000010010) // anti-proton
-      50           0 :                 id = -2212;
-      51           0 :         return HepPID::particleName(id);
-      52             : }
-      53             : 
-      54             : }
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html b/doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html deleted file mode 100644 index 684f8b4f6..000000000 --- a/doc/coverageReport/src/ParticleMass.cpp.func-sort-c.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleMass.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleMass.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:303196.8 %
Date:2024-04-08 14:58:22Functions:44100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16NuclearMassTable4initEv12
_ZN7crpropa11nuclearMassEi161184
_ZN7crpropa16NuclearMassTable7getMassEm161208
_ZN7crpropa11nuclearMassEii161209
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleMass.cpp.func.html b/doc/coverageReport/src/ParticleMass.cpp.func.html deleted file mode 100644 index f0fe27c62..000000000 --- a/doc/coverageReport/src/ParticleMass.cpp.func.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleMass.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleMass.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:303196.8 %
Date:2024-04-08 14:58:22Functions:44100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11nuclearMassEi161184
_ZN7crpropa11nuclearMassEii161209
_ZN7crpropa16NuclearMassTable4initEv12
_ZN7crpropa16NuclearMassTable7getMassEm161208
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleMass.cpp.gcov.html b/doc/coverageReport/src/ParticleMass.cpp.gcov.html deleted file mode 100644 index 22315606f..000000000 --- a/doc/coverageReport/src/ParticleMass.cpp.gcov.html +++ /dev/null @@ -1,150 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleMass.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleMass.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:303196.8 %
Date:2024-04-08 14:58:22Functions:44100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/ParticleMass.h"
-       2             : #include "crpropa/ParticleID.h"
-       3             : #include "crpropa/Common.h"
-       4             : #include "crpropa/Units.h"
-       5             : 
-       6             : #include "kiss/convert.h"
-       7             : #include "kiss/logger.h"
-       8             : 
-       9             : #include <vector>
-      10             : #include <fstream>
-      11             : #include <stdexcept>
-      12             : #include <limits>
-      13             : 
-      14             : namespace crpropa {
-      15             : 
-      16             : struct NuclearMassTable {
-      17             :         bool initialized;
-      18             :         std::vector<double> table;
-      19             : 
-      20             :         NuclearMassTable() {
-      21             :                 initialized = false;
-      22             :         }
-      23             : 
-      24          12 :         void init() {
-      25          24 :                 std::string filename = getDataPath("nuclear_mass.txt");
-      26          12 :                 std::ifstream infile(filename.c_str());
-      27             : 
-      28          12 :                 if (!infile.good())
-      29           0 :                         throw std::runtime_error("crpropa: could not open file " + filename);
-      30             : 
-      31             :                 int Z, N;
-      32             :                 double mass;
-      33       10092 :                 while (infile.good()) {
-      34       10080 :                         if (infile.peek() != '#') {
-      35       10056 :                                 infile >> Z >> N >> mass;
-      36       10056 :                                 table.push_back(mass);
-      37             :                         }
-      38       10080 :                         infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-      39             :                 }
-      40             : 
-      41          12 :                 infile.close();
-      42          12 :                 initialized = true;
-      43          24 :         }
-      44             : 
-      45      161208 :         double getMass(std::size_t idx) {
-      46      161208 :                 if (!initialized) {
-      47          12 : #pragma omp critical(init)
-      48          12 :                         init();
-      49             :                 }
-      50      161208 :                 return table[idx];
-      51             :         }
-      52             : };
-      53             : 
-      54             : static NuclearMassTable nuclearMassTable;
-      55             : 
-      56      161184 : double nuclearMass(int id) {
-      57      161184 :         int A = massNumber(id);
-      58      161184 :         int Z = chargeNumber(id);
-      59      161184 :         return nuclearMass(A, Z);
-      60             : }
-      61             : 
-      62      161209 : double nuclearMass(int A, int Z) {
-      63      161209 :         if ((A < 1) or (A > 56) or (Z < 0) or (Z > 26) or (Z > A)) {
-      64           2 :                 KISS_LOG_WARNING <<
-      65           1 :                 "nuclearMass: nuclear mass not found in the mass table for " <<
-      66           1 :                 "A = " << A << ", Z = " << Z << ". " <<
-      67           1 :                 "Approximated value used A * amu - Z * m_e instead.";
-      68           1 :                 return A * amu - Z * mass_electron;
-      69             :         }
-      70      161208 :         int N = A - Z;
-      71      161208 :         return nuclearMassTable.getMass(Z * 31 + N);
-      72             : }
-      73             : 
-      74             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleState.cpp.func-sort-c.html b/doc/coverageReport/src/ParticleState.cpp.func-sort-c.html deleted file mode 100644 index c6897830a..000000000 --- a/doc/coverageReport/src/ParticleState.cpp.func-sort-c.html +++ /dev/null @@ -1,140 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleState.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleState.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:485685.7 %
Date:2024-04-08 14:58:22Functions:161794.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13ParticleState14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ParticleState11getRigidityEv1
_ZNK7crpropa13ParticleState11getVelocityEv1
_ZNK7crpropa13ParticleState11getMomentumEv2
_ZNK7crpropa13ParticleState7getMassEv4
_ZN7crpropa13ParticleState16setLorentzFactorEd15420
_ZNK7crpropa13ParticleState16getLorentzFactorEv33182
_ZNK7crpropa13ParticleState5getIdEv290682
_ZNK7crpropa13ParticleState12getDirectionEv500446
_ZNK7crpropa13ParticleState9getEnergyEv603581
_ZNK7crpropa13ParticleState9getChargeEv960335
_ZNK7crpropa13ParticleState11getPositionEv12488919
_ZN7crpropa13ParticleStateC2EidNS_7Vector3IdEES2_16844401
_ZN7crpropa13ParticleState12setDirectionERKNS_7Vector3IdEE17329639
_ZN7crpropa13ParticleState5setIdEi20314515
_ZN7crpropa13ParticleState9setEnergyEd20322799
_ZN7crpropa13ParticleState11setPositionERKNS_7Vector3IdEE24114998
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleState.cpp.func.html b/doc/coverageReport/src/ParticleState.cpp.func.html deleted file mode 100644 index 2ad881fd0..000000000 --- a/doc/coverageReport/src/ParticleState.cpp.func.html +++ /dev/null @@ -1,140 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleState.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleState.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:485685.7 %
Date:2024-04-08 14:58:22Functions:161794.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13ParticleState11setPositionERKNS_7Vector3IdEE24114998
_ZN7crpropa13ParticleState12setDirectionERKNS_7Vector3IdEE17329639
_ZN7crpropa13ParticleState16setLorentzFactorEd15420
_ZN7crpropa13ParticleState5setIdEi20314515
_ZN7crpropa13ParticleState9setEnergyEd20322799
_ZN7crpropa13ParticleStateC2EidNS_7Vector3IdEES2_16844401
_ZNK7crpropa13ParticleState11getMomentumEv2
_ZNK7crpropa13ParticleState11getPositionEv12488919
_ZNK7crpropa13ParticleState11getRigidityEv1
_ZNK7crpropa13ParticleState11getVelocityEv1
_ZNK7crpropa13ParticleState12getDirectionEv500446
_ZNK7crpropa13ParticleState14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ParticleState16getLorentzFactorEv33182
_ZNK7crpropa13ParticleState5getIdEv290682
_ZNK7crpropa13ParticleState7getMassEv4
_ZNK7crpropa13ParticleState9getChargeEv960335
_ZNK7crpropa13ParticleState9getEnergyEv603581
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ParticleState.cpp.gcov.html b/doc/coverageReport/src/ParticleState.cpp.gcov.html deleted file mode 100644 index 34ba83680..000000000 --- a/doc/coverageReport/src/ParticleState.cpp.gcov.html +++ /dev/null @@ -1,178 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ParticleState.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ParticleState.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:485685.7 %
Date:2024-04-08 14:58:22Functions:161794.1 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/ParticleState.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Common.h"
-       4             : #include "crpropa/ParticleID.h"
-       5             : #include "crpropa/ParticleMass.h"
-       6             : 
-       7             : #include "HepPID/ParticleIDMethods.hh"
-       8             : 
-       9             : #include <cstdlib>
-      10             : #include <sstream>
-      11             : 
-      12             : namespace crpropa {
-      13             : 
-      14    16844401 : ParticleState::ParticleState(int id, double E, Vector3d pos, Vector3d dir): id(0), energy(0.), position(0.), direction(0.), pmass(0.), charge(0.)
-      15             : {
-      16    16844401 :         setId(id);
-      17    16844401 :         setEnergy(E);
-      18    16844401 :         setPosition(pos);
-      19    16844401 :         setDirection(dir);
-      20    16844401 : }
-      21             : 
-      22    24114998 : void ParticleState::setPosition(const Vector3d &pos) {
-      23             :         position = pos;
-      24    24114998 : }
-      25             : 
-      26    12488919 : const Vector3d &ParticleState::getPosition() const {
-      27    12488919 :         return position;
-      28             : }
-      29             : 
-      30    17329639 : void ParticleState::setDirection(const Vector3d &dir) {
-      31             :         direction = dir / dir.getR();
-      32    17329639 : }
-      33             : 
-      34      500446 : const Vector3d &ParticleState::getDirection() const {
-      35      500446 :         return direction;
-      36             : }
-      37             : 
-      38    20322799 : void ParticleState::setEnergy(double newEnergy) {
-      39    20322799 :         energy = std::max(0., newEnergy); // prevent negative energies
-      40    20322799 : }
-      41             : 
-      42      603581 : double ParticleState::getEnergy() const {
-      43      603581 :         return energy;
-      44             : }
-      45             : 
-      46           1 : double ParticleState::getRigidity() const {
-      47           1 :         return fabs(energy / charge);
-      48             : }
-      49             : 
-      50    20314515 : void ParticleState::setId(int newId) {
-      51    20314515 :         id = newId;
-      52    20314515 :         if (isNucleus(id)) {
-      53      146261 :                 pmass = nuclearMass(id);
-      54      146261 :                 charge = chargeNumber(id) * eplus;
-      55      146261 :                 if (id < 0)
-      56           4 :                         charge *= -1; // anti-nucleus
-      57             :         } else {
-      58    20168254 :                 if (abs(id) == 11)
-      59       15064 :                         pmass = mass_electron;
-      60    20168254 :                 charge = HepPID::charge(id) * eplus;
-      61             :         }
-      62    20314515 : }
-      63             : 
-      64      290682 : int ParticleState::getId() const {
-      65      290682 :         return id;
-      66             : }
-      67             : 
-      68           4 : double ParticleState::getMass() const {
-      69           4 :         return pmass;
-      70             : }
-      71             : 
-      72      960335 : double ParticleState::getCharge() const {
-      73      960335 :         return charge;
-      74             : }
-      75             : 
-      76       33182 : double ParticleState::getLorentzFactor() const {
-      77       33182 :         return energy / (pmass * c_squared);
-      78             : }
-      79             : 
-      80       15420 : void ParticleState::setLorentzFactor(double lf) {
-      81       15420 :         lf = std::max(0., lf); // prevent negative Lorentz factors
-      82       15420 :         energy = lf * pmass * c_squared;
-      83       15420 : }
-      84             : 
-      85           1 : Vector3d ParticleState::getVelocity() const {
-      86           1 :         return direction * c_light;
-      87             : }
-      88             : 
-      89           2 : Vector3d ParticleState::getMomentum() const {
-      90           2 :         return direction * (energy / c_light);
-      91             : }
-      92             : 
-      93           0 : std::string ParticleState::getDescription() const {
-      94           0 :         std::stringstream ss;
-      95           0 :         ss << "Particle " << id << ", ";
-      96           0 :         ss << "E = " << energy / EeV << " EeV, ";
-      97           0 :         ss << "x = " << position / Mpc << " Mpc, ";
-      98           0 :         ss << "p = " << direction;
-      99           0 :         return ss.str();
-     100           0 : }
-     101             : 
-     102             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html b/doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html deleted file mode 100644 index eca58f129..000000000 --- a/doc/coverageReport/src/PhotonBackground.cpp.func-sort-c.html +++ /dev/null @@ -1,132 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/PhotonBackground.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - PhotonBackground.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8812073.3 %
Date:2024-04-08 14:58:22Functions:121580.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20BlackbodyPhotonField11setQuantileEd0
_ZNK7crpropa18TabularPhotonField22getMaximumPhotonEnergyEd0
_ZNK7crpropa18TabularPhotonField22getMinimumPhotonEnergyEd0
_ZNK7crpropa20BlackbodyPhotonField22getMaximumPhotonEnergyEd29
_ZNK7crpropa20BlackbodyPhotonField22getMinimumPhotonEnergyEd29
_ZN7crpropa20BlackbodyPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd40
_ZN7crpropa18TabularPhotonField12readRedshiftENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE73
_ZN7crpropa18TabularPhotonField19initRedshiftScalingEv73
_ZN7crpropa18TabularPhotonField16readPhotonEnergyENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonField17readPhotonDensityENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEb94
_ZNK7crpropa18TabularPhotonField14checkInputDataEv94
_ZNK7crpropa20BlackbodyPhotonField16getPhotonDensityEdd10689
_ZNK7crpropa18TabularPhotonField18getRedshiftScalingEd16757
_ZNK7crpropa18TabularPhotonField16getPhotonDensityEdd9536930
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/PhotonBackground.cpp.func.html b/doc/coverageReport/src/PhotonBackground.cpp.func.html deleted file mode 100644 index c0525218b..000000000 --- a/doc/coverageReport/src/PhotonBackground.cpp.func.html +++ /dev/null @@ -1,132 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/PhotonBackground.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - PhotonBackground.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8812073.3 %
Date:2024-04-08 14:58:22Functions:121580.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18TabularPhotonField12readRedshiftENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE73
_ZN7crpropa18TabularPhotonField16readPhotonEnergyENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonField17readPhotonDensityENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE94
_ZN7crpropa18TabularPhotonField19initRedshiftScalingEv73
_ZN7crpropa18TabularPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEb94
_ZN7crpropa20BlackbodyPhotonField11setQuantileEd0
_ZN7crpropa20BlackbodyPhotonFieldC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEd40
_ZNK7crpropa18TabularPhotonField14checkInputDataEv94
_ZNK7crpropa18TabularPhotonField16getPhotonDensityEdd9536930
_ZNK7crpropa18TabularPhotonField18getRedshiftScalingEd16757
_ZNK7crpropa18TabularPhotonField22getMaximumPhotonEnergyEd0
_ZNK7crpropa18TabularPhotonField22getMinimumPhotonEnergyEd0
_ZNK7crpropa20BlackbodyPhotonField16getPhotonDensityEdd10689
_ZNK7crpropa20BlackbodyPhotonField22getMaximumPhotonEnergyEd29
_ZNK7crpropa20BlackbodyPhotonField22getMinimumPhotonEnergyEd29
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/PhotonBackground.cpp.gcov.html b/doc/coverageReport/src/PhotonBackground.cpp.gcov.html deleted file mode 100644 index 7d90ae0f2..000000000 --- a/doc/coverageReport/src/PhotonBackground.cpp.gcov.html +++ /dev/null @@ -1,291 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/PhotonBackground.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - PhotonBackground.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8812073.3 %
Date:2024-04-08 14:58:22Functions:121580.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/PhotonBackground.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #include "kiss/logger.h"
-       6             : 
-       7             : #include <fstream>
-       8             : #include <stdexcept>
-       9             : #include <limits>
-      10             : #include <cmath>
-      11             : 
-      12             : namespace crpropa {
-      13             : 
-      14          94 : TabularPhotonField::TabularPhotonField(std::string fieldName, bool isRedshiftDependent) {
-      15          94 :         this->fieldName = fieldName;
-      16          94 :         this->isRedshiftDependent = isRedshiftDependent;
-      17             : 
-      18         188 :         readPhotonEnergy(getDataPath("") + "Scaling/" + this->fieldName + "_photonEnergy.txt");
-      19         188 :         readPhotonDensity(getDataPath("") + "Scaling/" + this->fieldName + "_photonDensity.txt");
-      20          94 :         if (this->isRedshiftDependent)
-      21         146 :                 readRedshift(getDataPath("") + "Scaling/" + this->fieldName + "_redshift.txt");
-      22             : 
-      23          94 :         checkInputData();
-      24             : 
-      25          94 :         if (this->isRedshiftDependent)
-      26          73 :                 initRedshiftScaling();
-      27          94 : }
-      28             : 
-      29             : 
-      30     9536930 : double TabularPhotonField::getPhotonDensity(double Ephoton, double z) const {   
-      31     9536930 :         if ((this->isRedshiftDependent)) {
-      32             :                 // fix behaviour for future redshift. See issue #414
-      33             :                 // with redshift < 0 the photon density is set to 0 in interpolate2d. 
-      34             :                 // Therefore it is assumed that the photon density does not change from values at z = 0. This is only valid for small changes in redshift.
-      35     9536930 :                 double zMin = this->redshifts[0];
-      36     9536930 :                 if(z < zMin){
-      37           0 :                         if(z < -1) {
-      38           0 :                                 KISS_LOG_WARNING << "Photon Field " << fieldName << " uses FutureRedshift with z < -1. The photon density is set to n(Ephoton, z=0). \n";
-      39             :                         }
-      40           0 :                         return getPhotonDensity(Ephoton, zMin);
-      41             :                 } else {
-      42     9536930 :                         return interpolate2d(Ephoton, z, this->photonEnergies, this->redshifts, this->photonDensity);
-      43             :                 }
-      44             :         } else {
-      45           0 :                 return interpolate(Ephoton, this->photonEnergies, this->photonDensity);
-      46             :         }
-      47             : }
-      48             : 
-      49             : 
-      50       16757 : double TabularPhotonField::getRedshiftScaling(double z) const {
-      51       16757 :         if (!this->isRedshiftDependent)
-      52             :                 return 1.;
-      53             :  
-      54       16573 :         if (z < this->redshifts.front())
-      55             :                 return 1.;
-      56             :  
-      57       16573 :         if (z > this->redshifts.back())
-      58             :                 return 0.;
-      59             :  
-      60       16573 :         return interpolate(z, this->redshifts, this->redshiftScalings);
-      61             : }
-      62             : 
-      63           0 : double TabularPhotonField::getMinimumPhotonEnergy(double z) const{
-      64           0 :         return photonEnergies[0];
-      65             : }
-      66             : 
-      67           0 : double TabularPhotonField::getMaximumPhotonEnergy(double z) const{
-      68           0 :         return photonEnergies[photonEnergies.size() -1];
-      69             : }
-      70             : 
-      71          94 : void TabularPhotonField::readPhotonEnergy(std::string filePath) {
-      72          94 :         std::ifstream infile(filePath.c_str());
-      73          94 :         if (!infile.good())
-      74           0 :                 throw std::runtime_error("TabularPhotonField::readPhotonEnergy: could not open " + filePath);
-      75             : 
-      76             :         std::string line;
-      77       15320 :         while (std::getline(infile, line)) {
-      78       15226 :                 if ((line.size() > 0) & (line[0] != '#') )
-      79       14944 :                         this->photonEnergies.push_back(std::stod(line));
-      80             :         }
-      81          94 :         infile.close();
-      82          94 : }
-      83             : 
-      84          94 : void TabularPhotonField::readPhotonDensity(std::string filePath) {
-      85          94 :         std::ifstream infile(filePath.c_str());
-      86          94 :         if (!infile.good())
-      87           0 :                 throw std::runtime_error("TabularPhotonField::readPhotonDensity: could not open " + filePath);
-      88             : 
-      89             :         std::string line;
-      90     4772519 :         while (std::getline(infile, line)) {
-      91     4772425 :                 if ((line.size() > 0) & (line[0] != '#') )
-      92     4772143 :                         this->photonDensity.push_back(std::stod(line));
-      93             :         }
-      94          94 :         infile.close();
-      95          94 : }
-      96             : 
-      97          73 : void TabularPhotonField::readRedshift(std::string filePath) {
-      98          73 :         std::ifstream infile(filePath.c_str());
-      99          73 :         if (!infile.good())
-     100           0 :                 throw std::runtime_error("TabularPhotonField::initRedshift: could not open " + filePath);
-     101             : 
-     102             :         std::string line;
-     103       14599 :         while (std::getline(infile, line)) {
-     104       14526 :                 if ((line.size() > 0) & (line[0] != '#') )
-     105       14307 :                         this->redshifts.push_back(std::stod(line));
-     106             :         }
-     107          73 :         infile.close();
-     108          73 : }
-     109             : 
-     110          73 : void TabularPhotonField::initRedshiftScaling() {
-     111             :         double n0 = 0.;
-     112       14380 :         for (int i = 0; i < this->redshifts.size(); ++i) {
-     113       14307 :                 double z = this->redshifts[i];
-     114             :                 double n = 0.;
-     115     4770022 :                 for (int j = 0; j < this->photonEnergies.size()-1; ++j) {
-     116     4755715 :                         double e_j = this->photonEnergies[j];
-     117     4755715 :                         double e_j1 = this->photonEnergies[j+1];
-     118     4755715 :                         double deltaLogE = std::log10(e_j1) - std::log10(e_j);
-     119     4755715 :                         if (z == 0.)
-     120       12750 :                                 n0 += (getPhotonDensity(e_j, 0) + getPhotonDensity(e_j1, 0)) / 2. * deltaLogE;
-     121     4755715 :                         n += (getPhotonDensity(e_j, z) + getPhotonDensity(e_j1, z)) / 2. * deltaLogE;
-     122             :                 }
-     123       14307 :                 this->redshiftScalings.push_back(n / n0);
-     124             :         }
-     125          73 : }
-     126             : 
-     127          94 : void TabularPhotonField::checkInputData() const {
-     128          94 :         if (this->isRedshiftDependent) {
-     129          73 :                 if (this->photonDensity.size() != this->photonEnergies.size() * this-> redshifts.size())
-     130           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: length of photon density input is unequal to length of photon energy input times length of redshift input");
-     131             :         } else {
-     132          21 :                 if (this->photonEnergies.size() != this->photonDensity.size())
-     133           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: length of photon energy input is unequal to length of photon density input");
-     134             :         }
-     135             : 
-     136       15038 :         for (int i = 0; i < this->photonEnergies.size(); ++i) {
-     137             :                 double ePrevious = 0.;
-     138       14944 :                 double e = this->photonEnergies[i];
-     139       14944 :                 if (e <= 0.)
-     140           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: a value in the photon energy input is not positive");
-     141             :                 if (e <= ePrevious)
-     142             :                         throw std::runtime_error("TabularPhotonField::checkInputData: photon energy values are not strictly increasing");
-     143             :                 ePrevious = e;
-     144             :         }
-     145             : 
-     146     4772237 :         for (int i = 0; i < this->photonDensity.size(); ++i) {
-     147     4772143 :                 if (this->photonDensity[i] < 0.)
-     148           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: a value in the photon density input is negative");
-     149             :         }
-     150             : 
-     151          94 :         if (this->isRedshiftDependent) {
-     152          73 :                 if (this->redshifts[0] != 0.)
-     153           0 :                         throw std::runtime_error("TabularPhotonField::checkInputData: redshift input must start with zero");
-     154             : 
-     155       14380 :                 for (int i = 0; i < this->redshifts.size(); ++i) {
-     156             :                         double zPrevious = -1.;
-     157       14307 :                         double z = this->redshifts[i];
-     158       14307 :                         if (z < 0.)
-     159           0 :                                 throw std::runtime_error("TabularPhotonField::checkInputData: a value in the redshift input is negative");
-     160       14307 :                         if (z <= zPrevious)
-     161           0 :                                 throw std::runtime_error("TabularPhotonField::checkInputData: redshift values are not strictly increasing");
-     162             :                         zPrevious = z;
-     163             :                 }
-     164             : 
-     165          73 :                 for (int i = 0; i < this->redshiftScalings.size(); ++i) {
-     166           0 :                         double scalingFactor = this->redshiftScalings[i];
-     167           0 :                         if (scalingFactor <= 0.)
-     168           0 :                                 throw std::runtime_error("TabularPhotonField::checkInputData: initRedshiftScaling has created a non-positive scaling factor");
-     169             :                 }
-     170             :         }
-     171          94 : }
-     172             : 
-     173          40 : BlackbodyPhotonField::BlackbodyPhotonField(std::string fieldName, double blackbodyTemperature) {
-     174          40 :         this->fieldName = fieldName;
-     175          40 :         this->blackbodyTemperature = blackbodyTemperature;
-     176          40 :         this->quantile = 0.0001; // tested to be sufficient, only used for extreme values of primary energy or temperature
-     177          40 : }
-     178             : 
-     179       10689 : double BlackbodyPhotonField::getPhotonDensity(double Ephoton, double z) const {
-     180       10689 :         return 8 * M_PI * pow_integer<3>(Ephoton / (h_planck * c_light)) / std::expm1(Ephoton / (k_boltzmann * this->blackbodyTemperature));
-     181             : }
-     182             : 
-     183          29 : double BlackbodyPhotonField::getMinimumPhotonEnergy(double z) const {
-     184             :         double A;
-     185          29 :         int quantile_int = 10000 * quantile;
-     186          29 :         switch (quantile_int)
-     187             :         {
-     188             :         case 1: // 0.01 % percentil
-     189             :                 A = 1.093586e-5 * eV / kelvin;
-     190             :                 break;
-     191           0 :         case 10:                // 0.1 % percentil
-     192             :                 A = 2.402189e-5 * eV / kelvin;
-     193           0 :                 break;
-     194           0 :         case 100:               // 1 % percentil
-     195             :                 A = 5.417942e-5 * eV / kelvin;
-     196           0 :                 break;
-     197           0 :         default:
-     198           0 :                 throw std::runtime_error("Quantile not understood. Please use 0.01 (1%), 0.001 (0.1%) or 0.0001 (0.01%) \n");
-     199             :                 break;
-     200             :         }
-     201          29 :         return A * this -> blackbodyTemperature;
-     202             : }
-     203             : 
-     204          29 : double BlackbodyPhotonField::getMaximumPhotonEnergy(double z) const {
-     205          29 :         double factor = std::max(1., blackbodyTemperature / 2.73);
-     206          29 :         return 0.1 * factor * eV; // T dependent scaling, starting at 0.1 eV as suitable for CMB
-     207             : }
-     208             : 
-     209           0 : void BlackbodyPhotonField::setQuantile(double q) {
-     210           0 :         if(not ((q == 0.0001) or (q == 0.001) or (q == 0.01)))
-     211           0 :                 throw std::runtime_error("Quantile not understood. Please use 0.01 (1%), 0.001 (0.1%) or 0.0001 (0.01%) \n");
-     212           0 :         this -> quantile = q;
-     213           0 : }
-     214             : 
-     215             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html b/doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html deleted file mode 100644 index 5818e83f3..000000000 --- a/doc/coverageReport/src/ProgressBar.cpp.func-sort-c.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ProgressBar.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ProgressBar.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:395078.0 %
Date:2024-04-08 14:58:22Functions:4580.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11ProgressBar8setErrorEv0
_ZN7crpropa11ProgressBar5startERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa11ProgressBarC2Emm5
_ZN7crpropa11ProgressBar11setPositionEm100
_ZN7crpropa11ProgressBar6updateEv100
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ProgressBar.cpp.func.html b/doc/coverageReport/src/ProgressBar.cpp.func.html deleted file mode 100644 index eabab3799..000000000 --- a/doc/coverageReport/src/ProgressBar.cpp.func.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ProgressBar.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ProgressBar.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:395078.0 %
Date:2024-04-08 14:58:22Functions:4580.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11ProgressBar11setPositionEm100
_ZN7crpropa11ProgressBar5startERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa11ProgressBar6updateEv100
_ZN7crpropa11ProgressBar8setErrorEv0
_ZN7crpropa11ProgressBarC2Emm5
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/ProgressBar.cpp.gcov.html b/doc/coverageReport/src/ProgressBar.cpp.gcov.html deleted file mode 100644 index 4bcb4bfab..000000000 --- a/doc/coverageReport/src/ProgressBar.cpp.gcov.html +++ /dev/null @@ -1,153 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/ProgressBar.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - ProgressBar.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:395078.0 %
Date:2024-04-08 14:58:22Functions:4580.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/ProgressBar.h"
-       2             : 
-       3             : #include <cstdio>
-       4             : #include <iostream>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8             : /// Initialize a ProgressBar with [steps] number of steps, updated at [updateSteps] intervalls
-       9           5 : ProgressBar::ProgressBar(unsigned long steps, unsigned long updateSteps) :
-      10           5 :                 _steps(steps), _currentCount(0), _maxbarLength(10), _updateSteps(
-      11           5 :                                 updateSteps), _nextStep(1), _startTime(0) {
-      12           5 :         if (_updateSteps > _steps)
-      13           3 :                 _updateSteps = _steps;
-      14           5 :         arrow.append(">");
-      15           5 : }
-      16             : 
-      17           1 : void ProgressBar::start(const std::string &title) {
-      18           1 :         _startTime = time(NULL);
-      19           1 :         std::string s = ctime(&_startTime);
-      20           1 :         s.erase(s.end() - 1, s.end());
-      21           1 :         stringTmpl = "  Started ";
-      22             :         stringTmpl.append(s);
-      23           1 :         stringTmpl.append(" : [%-10s] %3i%%    %s: %02i:%02i:%02i %s\r");
-      24             :         std::cout << title << std::endl;
-      25             : 
-      26           1 : }
-      27             : /// update the progressbar
-      28             : /// should be called steps times in a loop
-      29         100 : void ProgressBar::update() {
-      30         100 :         _currentCount++;
-      31         100 :         if (_currentCount == _nextStep || _currentCount == _steps
-      32           0 :                         || _currentCount == 1000) {
-      33         100 :                                 _nextStep += long(_steps / float(_updateSteps));
-      34         100 :                         setPosition(_currentCount);
-      35             :                         }
-      36         100 : }
-      37             : 
-      38         100 : void ProgressBar::setPosition(unsigned long position) {
-      39         100 :         int percentage = int(100 * (position / float(_steps)));
-      40         100 :         time_t currentTime = time(NULL);
-      41         100 :         if (position < _steps) {
-      42          99 :                 if (arrow.size() <= (_maxbarLength) * (position) / (_steps))
-      43           9 :                         arrow.insert(0, "=");
-      44          99 :                 float tElapsed = currentTime - _startTime;
-      45          99 :                 float tToGo = (_steps - position) * tElapsed / position;
-      46          99 :                 std::printf(stringTmpl.c_str(), arrow.c_str(), percentage, "Finish in",
-      47          99 :                                 int(tToGo / 3600), (int(tToGo) % 3600) / 60,
-      48          99 :                                 int(tToGo) % 60, "");
-      49          99 :                 fflush(stdout);
-      50             :         } else {
-      51           1 :                 float tElapsed = currentTime - _startTime;
-      52           1 :                 std::string s = " - Finished at ";
-      53           1 :                 s.append(ctime(&currentTime));
-      54             :                 char fs[255];
-      55             :                 std::sprintf(fs, "%c[%d;%dm Finished %c[%dm", 27, 1, 32, 27, 0);
-      56           1 :                 std::printf(stringTmpl.c_str(), fs, 100, "Needed",
-      57           1 :                                 int(tElapsed / 3600), (int(tElapsed) % 3600) / 60,
-      58           1 :                                 int(tElapsed) % 60, s.c_str());
-      59             :         }
-      60         100 : }
-      61             : 
-      62             : 
-      63             : /// Mark the progressbar with an error
-      64           0 : void ProgressBar::setError() {
-      65           0 :         time_t currentTime = time(NULL);
-      66           0 :         _currentCount++;
-      67           0 :         float tElapsed = currentTime - _startTime;
-      68           0 :         std::string s = " - Finished at ";
-      69           0 :         s.append(ctime(&currentTime));
-      70             :         char fs[255];
-      71             :         std::sprintf(fs, "%c[%d;%dm  ERROR   %c[%dm", 27, 1, 31, 27, 0);
-      72           0 :         std::printf(stringTmpl.c_str(), fs, _currentCount, "Needed",
-      73           0 :                         int(tElapsed / 3600), (int(tElapsed) % 3600) / 60,
-      74           0 :                         int(tElapsed) % 60, s.c_str());
-      75           0 : }
-      76             : 
-      77             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Random.cpp.func-sort-c.html b/doc/coverageReport/src/Random.cpp.func-sort-c.html deleted file mode 100644 index e9ea9e87a..000000000 --- a/doc/coverageReport/src/Random.cpp.func-sort-c.html +++ /dev/null @@ -1,256 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Random.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Random.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13924157.7 %
Date:2024-04-08 14:58:22Functions:264656.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Random10randDblExcERKd0
_ZN7crpropa6Random11seedThreadsEj0
_ZN7crpropa6Random12randRayleighEd0
_ZN7crpropa6Random14getSeedThreadsEv0
_ZN7crpropa6Random15randExponentialEv0
_ZN7crpropa6Random18randBrokenPowerLawEddddd0
_ZN7crpropa6Random18randVectorLambertsERKNS_7Vector3IdEE0
_ZN7crpropa6Random18randVectorLambertsEv0
_ZN7crpropa6Random4hashEll0
_ZN7crpropa6Random4loadEPj0
_ZN7crpropa6Random4randERKd0
_ZN7crpropa6Random6rand53Ev0
_ZN7crpropa6Random7randExcERKd0
_ZN7crpropa6Random7randIntERKj0
_ZN7crpropa6RandomC2EPjj0
_ZN7crpropa6RandomC2ERKj0
_ZN7crpropalsERSoRKNS_6RandomE0
_ZN7crproparsERSiRNS_6RandomE0
_ZNK7crpropa6Random14getSeed_base64B5cxx11Ev0
_ZNK7crpropa6Random4saveEPj0
_ZN7crpropa6Random4seedERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa6Random7getSeedEv2
_ZN7crpropa6Random4seedEj13
_ZN7crpropa6Random9randInt64ERKm421
_ZN7crpropa6Random9randInt64Ev864
_ZN7crpropa6Random10randFisherEd1000
_ZN7crpropa6Random16randFisherVectorERKNS_7Vector3IdEEd1000
_ZN7crpropa6Random12randPowerLawEddd1104
_ZN7crpropa6Random4seedEv4881
_ZN7crpropa6RandomC2Ev4881
_ZN7crpropa6Random4seedEPjj4884
_ZN7crpropa6Random10initializeEj4897
_ZN7crpropa6Random7randBinERKSt6vectorIfSaIfEE10102
_ZN7crpropa6Random6reloadEv46321
_ZN7crpropa6Random14randConeVectorERKNS_7Vector3IdEEd480001
_ZN7crpropa6Random20randVectorAroundMeanERKNS_7Vector3IdEEd481001
_ZN7crpropa6Random10randVectorEv962203
_ZN7crpropa6Random10randDblExcEv1715954
_ZN7crpropa6Random7randExcEv1715954
_ZN7crpropa6Random8randNormERKdS2_1715954
_ZN7crpropa6Random11randUniformEdd2404687
_ZN7crpropa6Random8instanceEv2658589
_ZN7crpropa6Random26randomInterpolatedPositionERKNS_7Vector3IdEES4_3628723
_ZN7crpropa6Random7randBinERKSt6vectorIdSaIdEE3739276
_ZN7crpropa6Random4randEv22414108
_ZN7crpropa6Random7randIntEv25852694
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Random.cpp.func.html b/doc/coverageReport/src/Random.cpp.func.html deleted file mode 100644 index c6e8901c8..000000000 --- a/doc/coverageReport/src/Random.cpp.func.html +++ /dev/null @@ -1,256 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Random.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Random.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13924157.7 %
Date:2024-04-08 14:58:22Functions:264656.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Random10initializeEj4897
_ZN7crpropa6Random10randDblExcERKd0
_ZN7crpropa6Random10randDblExcEv1715954
_ZN7crpropa6Random10randFisherEd1000
_ZN7crpropa6Random10randVectorEv962203
_ZN7crpropa6Random11randUniformEdd2404687
_ZN7crpropa6Random11seedThreadsEj0
_ZN7crpropa6Random12randPowerLawEddd1104
_ZN7crpropa6Random12randRayleighEd0
_ZN7crpropa6Random14getSeedThreadsEv0
_ZN7crpropa6Random14randConeVectorERKNS_7Vector3IdEEd480001
_ZN7crpropa6Random15randExponentialEv0
_ZN7crpropa6Random16randFisherVectorERKNS_7Vector3IdEEd1000
_ZN7crpropa6Random18randBrokenPowerLawEddddd0
_ZN7crpropa6Random18randVectorLambertsERKNS_7Vector3IdEE0
_ZN7crpropa6Random18randVectorLambertsEv0
_ZN7crpropa6Random20randVectorAroundMeanERKNS_7Vector3IdEEd481001
_ZN7crpropa6Random26randomInterpolatedPositionERKNS_7Vector3IdEES4_3628723
_ZN7crpropa6Random4hashEll0
_ZN7crpropa6Random4loadEPj0
_ZN7crpropa6Random4randERKd0
_ZN7crpropa6Random4randEv22414108
_ZN7crpropa6Random4seedEPjj4884
_ZN7crpropa6Random4seedERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa6Random4seedEj13
_ZN7crpropa6Random4seedEv4881
_ZN7crpropa6Random6rand53Ev0
_ZN7crpropa6Random6reloadEv46321
_ZN7crpropa6Random7randBinERKSt6vectorIdSaIdEE3739276
_ZN7crpropa6Random7randBinERKSt6vectorIfSaIfEE10102
_ZN7crpropa6Random7randExcERKd0
_ZN7crpropa6Random7randExcEv1715954
_ZN7crpropa6Random7randIntERKj0
_ZN7crpropa6Random7randIntEv25852694
_ZN7crpropa6Random8instanceEv2658589
_ZN7crpropa6Random8randNormERKdS2_1715954
_ZN7crpropa6Random9randInt64ERKm421
_ZN7crpropa6Random9randInt64Ev864
_ZN7crpropa6RandomC2EPjj0
_ZN7crpropa6RandomC2ERKj0
_ZN7crpropa6RandomC2Ev4881
_ZN7crpropalsERSoRKNS_6RandomE0
_ZN7crproparsERSiRNS_6RandomE0
_ZNK7crpropa6Random14getSeed_base64B5cxx11Ev0
_ZNK7crpropa6Random4saveEPj0
_ZNK7crpropa6Random7getSeedEv2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Random.cpp.gcov.html b/doc/coverageReport/src/Random.cpp.gcov.html deleted file mode 100644 index 4aaef80c6..000000000 --- a/doc/coverageReport/src/Random.cpp.gcov.html +++ /dev/null @@ -1,605 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Random.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Random.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13924157.7 %
Date:2024-04-08 14:58:22Functions:264656.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : // Random.cpp is based on Random.h
-       2             : // Mersenne Twister random number generator -- a C++ class Random
-       3             : // Based on code by Makoto Matsumoto, Takuji Nishimura, and Shawn Cokus
-       4             : // Richard J. Wagner  v1.0  15 May 2003  rjwagner@writeme.com
-       5             : 
-       6             : // The Mersenne Twister is an algorithm for generating random numbers.  It
-       7             : // was designed with consideration of the flaws in various other generators.
-       8             : // The period, 2^19937-1, and the order of equidistribution, 623 dimensions,
-       9             : // are far greater.  The generator is also fast; it avoids multiplication and
-      10             : // division, and it benefits from caches and pipelines.  For more information
-      11             : // see the inventors' web page at http://www.math.keio.ac.jp/~matumoto/emt.html
-      12             : 
-      13             : // Reference
-      14             : // M. Matsumoto and T. Nishimura, "Mersenne Twister: A 623-Dimensionally
-      15             : // Equidistributed Uniform Pseudo-Random Number Generator", ACM Transactions on
-      16             : // Modeling and Computer Simulation, Vol. 8, No. 1, January 1998, pp 3-30.
-      17             : 
-      18             : // Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura,
-      19             : // Copyright (C) 2000 - 2003, Richard J. Wagner
-      20             : // All rights reserved.                          
-      21             : //
-      22             : // Redistribution and use in source and binary forms, with or without
-      23             : // modification, are permitted provided that the following conditions
-      24             : // are met:
-      25             : //
-      26             : //   1. Redistributions of source code must retain the above copyright
-      27             : //      notice, this list of conditions and the following disclaimer.
-      28             : //
-      29             : //   2. Redistributions in binary form must reproduce the above copyright
-      30             : //      notice, this list of conditions and the following disclaimer in the
-      31             : //      documentation and/or other materials provided with the distribution.
-      32             : //
-      33             : //   3. The names of its contributors may not be used to endorse or promote 
-      34             : //      products derived from this software without specific prior written 
-      35             : //      permission.
-      36             : //
-      37             : // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-      38             : // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-      39             : // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-      40             : // A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE COPYRIGHT OWNER OR
-      41             : // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
-      42             : // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
-      43             : // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
-      44             : // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
-      45             : // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
-      46             : // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
-      47             : // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
-      48             : 
-      49             : // The original code included the following notice:
-      50             : //
-      51             : //     When you use this, send an email to: matumoto@math.keio.ac.jp
-      52             : //     with an appropriate reference to your work.
-      53             : //
-      54             : // It would be nice to CC: rjwagner@writeme.com and Cokus@math.washington.edu
-      55             : // when you write.
-      56             : 
-      57             : // Parts of this file are modified beginning in 29.10.09 for adaption in PXL.
-      58             : // Parts of this file are modified beginning in 10.02.12 for adaption in CRPropa.
-      59             : 
-      60             : #include "crpropa/Random.h"
-      61             : 
-      62             : #include "crpropa/base64.h"
-      63             : 
-      64             : #include <cstdio>
-      65             : 
-      66             : namespace crpropa {
-      67             : 
-      68           0 : Random::Random(const uint32_t& oneSeed) {
-      69           0 :         seed(oneSeed);
-      70           0 : }
-      71             : 
-      72           0 : Random::Random(uint32_t * const bigSeed, const uint32_t seedLength) {
-      73           0 :         seed(bigSeed, seedLength);
-      74           0 : }
-      75             : 
-      76        4881 : Random::Random() {
-      77        4881 :         seed();
-      78        4881 : }
-      79             : 
-      80    22414108 : double Random::rand() {
-      81    22414108 :         return double(randInt()) * (1.0 / 4294967295.0);
-      82             : }
-      83             : 
-      84           0 : double Random::rand(const double& n) {
-      85           0 :         return rand() * n;
-      86             : }
-      87             : 
-      88     1715954 : double Random::randExc() {
-      89     1715954 :         return double(randInt()) * (1.0 / 4294967296.0);
-      90             : }
-      91             : 
-      92           0 : double Random::randExc(const double& n) {
-      93           0 :         return randExc() * n;
-      94             : }
-      95             : 
-      96     1715954 : double Random::randDblExc() {
-      97     1715954 :         return (double(randInt()) + 0.5) * (1.0 / 4294967296.0);
-      98             : }
-      99             : 
-     100           0 : double Random::randDblExc(const double& n) {
-     101           0 :         return randDblExc() * n;
-     102             : }
-     103             : 
-     104           0 : double Random::rand53() {
-     105           0 :         uint32_t a = randInt() >> 5, b = randInt() >> 6;
-     106           0 :         return (a * 67108864.0 + b) * (1.0 / 9007199254740992.0); // by Isaku Wada
-     107             : }
-     108             : 
-     109             : // Return a real number from a normal (Gaussian) distribution with given
-     110             : // mean and variance by Box-Muller method
-     111     1715954 : double Random::randNorm(const double& mean, const double& variance) {
-     112     1715954 :         double r = sqrt(-2.0 * log(1.0 - randDblExc())) * variance;
-     113     1715954 :         double phi = 2.0 * 3.14159265358979323846264338328 * randExc();
-     114     1715954 :         return mean + r * cos(phi);
-     115             : }
-     116             : 
-     117     2404687 : double Random::randUniform(double min, double max) {
-     118     2404687 :         return min + (max - min) * rand();
-     119             : }
-     120             : 
-     121           0 : double Random::randRayleigh(double sigma) {
-     122           0 :         return sigma * sqrt(-2.0 * log(1 - rand()));
-     123             : }
-     124             : 
-     125        1000 : double Random::randFisher(double kappa) {
-     126        1000 :         return acos(1. + 1. / kappa * log(1 - rand() * (1 - exp(-2 * kappa))));
-     127             : }
-     128             : 
-     129       10102 : size_t Random::randBin(const std::vector<float> &cdf) {
-     130             :         std::vector<float>::const_iterator it = std::lower_bound(cdf.begin(),
-     131       10102 :                         cdf.end(), rand() * cdf.back());
-     132       10102 :         return it - cdf.begin();
-     133             : }
-     134             : 
-     135     3739276 : size_t Random::randBin(const std::vector<double> &cdf) {
-     136             :         std::vector<double>::const_iterator it = std::lower_bound(cdf.begin(),
-     137     3739276 :                         cdf.end(), rand() * cdf.back());
-     138     3739276 :         return it - cdf.begin();
-     139             : }
-     140             : 
-     141      962203 : Vector3d Random::randVector() {
-     142      962203 :         double z = randUniform(-1.0, 1.0);
-     143      962203 :         double t = randUniform(-1.0 * M_PI, M_PI);
-     144      962203 :         double r = sqrt(1 - z * z);
-     145      962203 :         return Vector3d(r * cos(t), r * sin(t), z);
-     146             : }
-     147             : 
-     148      481001 : Vector3d Random::randVectorAroundMean(const Vector3d &meanDirection,
-     149             :                 double angle) {
-     150      481001 :         Vector3d axis = meanDirection.cross(randVector());
-     151             :         Vector3d v = meanDirection;
-     152      481001 :         return v.getRotated(axis, angle);
-     153             : }
-     154             : 
-     155        1000 : Vector3d Random::randFisherVector(const Vector3d &meanDirection, double kappa) {
-     156        1000 :         return randVectorAroundMean(meanDirection, randFisher(kappa));
-     157             : }
-     158             : 
-     159      480001 : Vector3d Random::randConeVector(const Vector3d &meanDirection, double angularRadius) {
-     160      480001 :         const double theta = acos(randUniform(1, cos(angularRadius)));
-     161      480001 :         return randVectorAroundMean(meanDirection, theta);
-     162             : }
-     163             : 
-     164           0 : Vector3d Random::randVectorLamberts() {
-     165             :         // random vector following Lamberts cosine law (https://en.wikipedia.org/wiki/Lambert%27s_cosine_law)
-     166             :         // for a surface element with normal vector pointing in positive z-axis (0, 0, 1)
-     167           0 :         double phi = randUniform(-1.0 * M_PI, M_PI);
-     168           0 :         double theta = M_PI / 2.0 - acos(sqrt(randUniform(0, 1)));
-     169           0 :         return Vector3d(cos(phi) * cos(theta), sin(phi) * cos(theta), sin(theta));
-     170             : }
-     171             : 
-     172           0 : Vector3d Random::randVectorLamberts(const Vector3d &normalVector) {
-     173             :         // random vector following Lamberts cosine law for a surface element described by normalVector
-     174           0 :         Vector3d vLambertz = randVectorLamberts();
-     175             :         // find rotation axis that rotates the z-axis to the normalVector of the surface element
-     176             :         Vector3d axis = normalVector.cross(Vector3d(0, 0, 1));
-     177           0 :         if (axis.getR() < std::numeric_limits<double>::epsilon()) {
-     178             :                 axis = Vector3d(0, 0, 1);
-     179             :         }
-     180           0 :         double angle = normalVector.getAngleTo(Vector3d(0, 0, 1));
-     181             :         // rotate the random Lamberts vector from z-axis to respective surface element
-     182           0 :         return vLambertz.getRotated(axis / axis.getR(), -angle);
-     183             : }
-     184             : 
-     185     3628723 : Vector3d Random::randomInterpolatedPosition(const Vector3d &a, const Vector3d &b) {
-     186     3628723 :         return a + rand() * (b - a);
-     187             : }
-     188             : 
-     189        1104 : double Random::randPowerLaw(double index, double min, double max) {
-     190        1104 :         if ((min < 0) || (max < min)) {
-     191           0 :                 throw std::runtime_error(
-     192           0 :                                 "Power law distribution only possible for 0 <= min <= max");
-     193             :         }
-     194             :         //check for index -1!
-     195        1104 :         if ((std::abs(index + 1.0)) < std::numeric_limits<double>::epsilon()) {
-     196           2 :                 double part1 = log(max);
-     197           2 :                 double part2 = log(min);
-     198           2 :                 return exp((part1 - part2) * rand() + part2);
-     199             :         } else {
-     200        1102 :                 double part1 = pow(max, index + 1);
-     201        1102 :                 double part2 = pow(min, index + 1);
-     202        1102 :                 double ex = 1 / (index + 1);
-     203        1102 :                 return pow((part1 - part2) * rand() + part2, ex);
-     204             :         }
-     205             : }
-     206             : 
-     207           0 : double Random::randBrokenPowerLaw(double index1, double index2,
-     208             :                 double breakpoint, double min, double max) {
-     209           0 :         if ((min <= 0) || (max < min)) {
-     210           0 :                 throw std::runtime_error(
-     211           0 :                                 "Power law distribution only possible for 0 < min <= max");
-     212             :         }
-     213           0 :         if (min >= breakpoint) {
-     214           0 :                 return this->randPowerLaw(index2, min, max);
-     215           0 :         } else if (max <= breakpoint) {
-     216           0 :                 return this->randPowerLaw(index2, min, max);
-     217             :         } else {
-     218             :                 double intPL1;
-     219             :                 // check if index1 = -1
-     220           0 :                 if ((std::abs(index1 + 1.0)) < std::numeric_limits<double>::epsilon()) {
-     221           0 :                         intPL1 = log(breakpoint / min);
-     222             :                 } else {
-     223           0 :                         intPL1 = (pow(breakpoint, index1 + 1) - pow(min, index1 + 1))
-     224             :                                         / (index1 + 1);
-     225             :                 }
-     226             :                 double intPL2;
-     227             :                 // check if index2 = -1
-     228           0 :                 if ((std::abs(index2 + 1.0)) < std::numeric_limits<double>::epsilon()) {
-     229           0 :                         intPL2 = log(max / breakpoint) * pow(breakpoint, index1 - index2);
-     230             :                 } else {
-     231           0 :                         intPL2 = (pow(max, index2 + 1) - pow(breakpoint, index2 + 1))
-     232           0 :                                         * pow(breakpoint, index1 - index2) / (index2 + 1);
-     233             :                 }
-     234           0 :                 if (rand() > intPL1 / (intPL1 + intPL2))
-     235           0 :                         return randPowerLaw(index2, breakpoint, max);
-     236             :                 else
-     237           0 :                         return randPowerLaw(index1, min, breakpoint);
-     238             :         }
-     239             : }
-     240             : 
-     241           0 : double Random::randExponential() {
-     242             :         double dum;
-     243             :         do {
-     244           0 :                 dum = rand();
-     245           0 :         } while (dum < std::numeric_limits<double>::epsilon());
-     246           0 :         return -1.0 * log(dum);
-     247             : }
-     248             : 
-     249    25852694 : uint32_t Random::randInt() {
-     250    25852694 :         if (left == 0)
-     251       41424 :                 reload();
-     252    25852694 :         --left;
-     253             : 
-     254             :         uint32_t s1;
-     255    25852694 :         s1 = *pNext++;
-     256    25852694 :         s1 ^= (s1 >> 11);
-     257    25852694 :         s1 ^= (s1 << 7) & 0x9d2c5680UL;
-     258    25852694 :         s1 ^= (s1 << 15) & 0xefc60000UL;
-     259    25852694 :         return (s1 ^ (s1 >> 18));
-     260             : }
-     261             : 
-     262           0 : uint32_t Random::randInt(const uint32_t& n) {
-     263             : // Find which bits are used in n
-     264             : // Optimized by Magnus Jonsson (magnus@smartelectronix.com)
-     265           0 :         uint32_t used = n;
-     266           0 :         used |= used >> 1;
-     267           0 :         used |= used >> 2;
-     268           0 :         used |= used >> 4;
-     269           0 :         used |= used >> 8;
-     270           0 :         used |= used >> 16;
-     271             : 
-     272             : // Draw numbers until one is found in [0,n]
-     273             :         uint32_t i;
-     274             :         do
-     275           0 :                 i = randInt() & used; // toss unused bits to shorten search
-     276           0 :         while (i > n);
-     277           0 :         return i;
-     278             : }
-     279             : 
-     280             : 
-     281         864 : uint64_t Random::randInt64()
-     282             : {
-     283         864 :         int64_t a = randInt();
-     284         864 :         int64_t b = randInt();
-     285         864 :         return (b + a << 32);
-     286             : }
-     287             : 
-     288             : 
-     289         421 : uint64_t Random::randInt64(const uint64_t &n)
-     290             : {
-     291         421 :         uint64_t used = n;
-     292         421 :         used |= used >> 1;
-     293         421 :         used |= used >> 2;
-     294         421 :         used |= used >> 4;
-     295         421 :         used |= used >> 8;
-     296         421 :         used |= used >> 16;
-     297         421 :         used |= used >> 32;
-     298             : 
-     299             :         // Draw numbers until one is found in [0,n]
-     300             :         uint64_t i;
-     301             :         do
-     302         864 :                 i = randInt64() & used; // toss unused bits to shorten search
-     303         864 :         while (i > n);
-     304         421 :         return i;
-     305             : }
-     306             : 
-     307             : 
-     308             : 
-     309          13 : void Random::seed(const uint32_t oneSeed) {
-     310          13 :         initial_seed.resize(1);
-     311          13 :         initial_seed[0] = oneSeed;
-     312          13 :         initialize(oneSeed);
-     313          13 :         reload();
-     314          13 : }
-     315             : 
-     316        4884 : void Random::seed(uint32_t * const bigSeed, const uint32_t seedLength) {
-     317             : 
-     318        4884 :         initial_seed.resize(seedLength);
-     319     3051260 :         for (size_t i =0; i< seedLength; i++)
-     320             :         {
-     321     3046376 :                 initial_seed[i] = bigSeed[i];
-     322             :         }
-     323             : 
-     324        4884 :         initialize(19650218UL);
-     325             :         int i = 1;
-     326             :         uint32_t j = 0;
-     327        4884 :         int k = (N > seedLength ? N : seedLength);
-     328     3052500 :         for (; k; --k) {
-     329     3047616 :                 state[i] = state[i]
-     330     3047616 :                                 ^ ((state[i - 1] ^ (state[i - 1] >> 30)) * 1664525UL);
-     331     3047616 :                 state[i] += (bigSeed[j] & 0xffffffffUL) + j;
-     332             :                 state[i] &= 0xffffffffUL;
-     333     3047616 :                 ++i;
-     334     3047616 :                 ++j;
-     335     3047616 :                 if (i >= N) {
-     336        4884 :                         state[0] = state[N - 1];
-     337             :                         i = 1;
-     338             :                 }
-     339     3047616 :                 if (j >= seedLength)
-     340             :                         j = 0;
-     341             :         }
-     342     3047616 :         for (k = N - 1; k; --k) {
-     343     3042732 :                 state[i] = state[i]
-     344     3042732 :                                 ^ ((state[i - 1] ^ (state[i - 1] >> 30)) * 1566083941UL);
-     345     3042732 :                 state[i] -= i;
-     346             :                 state[i] &= 0xffffffffUL;
-     347     3042732 :                 ++i;
-     348     3042732 :                 if (i >= N) {
-     349        4884 :                         state[0] = state[N - 1];
-     350             :                         i = 1;
-     351             :                 }
-     352             :         }
-     353        4884 :         state[0] = 0x80000000UL; // MSB is 1, assuring non-zero initial array
-     354        4884 :         reload();
-     355        4884 : }
-     356             : 
-     357        4881 : void Random::seed() {
-     358             : // First try getting an array from /dev/urandom
-     359        4881 :         FILE* urandom = std::fopen("/dev/urandom", "rb");
-     360        4881 :         if (urandom) {
-     361             :                 uint32_t bigSeed[N];
-     362             :                 uint32_t *s = bigSeed;
-     363             :                 int i = N;
-     364             :                 bool success = true;
-     365     3050625 :                 while (success && i--)
-     366     6091488 :                         success = std::fread(s++, sizeof(uint32_t), 1, urandom) != 0;
-     367        4881 :                 std::fclose(urandom);
-     368        4881 :                 if (success) {
-     369        4881 :                         seed(bigSeed, N);
-     370        4881 :                         return;
-     371             :                 }
-     372             :         }
-     373             : 
-     374             : // Was not successful, so use time() and clock() instead
-     375           0 :         seed(hash(time(NULL), clock()));
-     376             : }
-     377             : 
-     378             : 
-     379        4897 : void Random::initialize(const uint32_t seed) {
-     380        4897 :         uint32_t *s = state;
-     381             :         uint32_t *r = state;
-     382             :         int i = 1;
-     383        4897 :         *s++ = seed & 0xffffffffUL;
-     384     3055728 :         for (; i < N; ++i) {
-     385     3050831 :                 *s++ = (1812433253UL * (*r ^ (*r >> 30)) + i) & 0xffffffffUL;
-     386     3050831 :                 r++;
-     387             :         }
-     388        4897 : }
-     389             : 
-     390       46321 : void Random::reload() {
-     391       46321 :         uint32_t *p = state;
-     392             :         int i;
-     393    10561188 :         for (i = N - M; i--; ++p)
-     394    10514867 :                 *p = twist(p[M], p[0], p[1]);
-     395    18389437 :         for (i = M; --i; ++p)
-     396    18343116 :                 *p = twist(p[M - N], p[0], p[1]);
-     397       46321 :         *p = twist(p[M - N], p[0], state[0]);
-     398             : 
-     399       46321 :         left = N, pNext = state;
-     400       46321 : }
-     401             : 
-     402           0 : uint32_t Random::hash(time_t t, clock_t c) {
-     403             :         static uint32_t differ = 0; // guarantee time-based seeds will change
-     404             : 
-     405             :         uint32_t h1 = 0;
-     406             :         unsigned char *p = (unsigned char *) &t;
-     407           0 :         for (size_t i = 0; i < sizeof(t); ++i) {
-     408           0 :                 h1 *= std::numeric_limits<unsigned char>::max() + 2U;
-     409           0 :                 h1 += p[i];
-     410             :         }
-     411             :         uint32_t h2 = 0;
-     412             :         p = (unsigned char *) &c;
-     413           0 :         for (size_t j = 0; j < sizeof(c); ++j) {
-     414           0 :                 h2 *= std::numeric_limits<unsigned char>::max() + 2U;
-     415           0 :                 h2 += p[j];
-     416             :         }
-     417           0 :         return (h1 + differ++) ^ h2;
-     418             : }
-     419             : 
-     420           0 : void Random::save(uint32_t* saveArray) const {
-     421             :         uint32_t *sa = saveArray;
-     422           0 :         const uint32_t *s = state;
-     423             :         int i = N;
-     424           0 :         for (; i--; *sa++ = *s++) {
-     425             :         }
-     426           0 :         *sa = left;
-     427           0 : }
-     428             : 
-     429           2 : const std::vector<uint32_t> &Random::getSeed() const
-     430             : {
-     431           2 :         return initial_seed;
-     432             : }
-     433             : 
-     434           0 : void Random::load(uint32_t * const loadArray) {
-     435           0 :         uint32_t *s = state;
-     436             :         uint32_t *la = loadArray;
-     437             :         int i = N;
-     438           0 :         for (; i--; *s++ = *la++) {
-     439             :         }
-     440           0 :         left = *la;
-     441           0 :         pNext = &state[N - left];
-     442           0 : }
-     443             : 
-     444           0 : std::ostream& operator<<(std::ostream& os, const Random& mtrand) {
-     445           0 :         const uint32_t *s = mtrand.state;
-     446             :         int i = mtrand.N;
-     447           0 :         for (; i--; os << *s++ << "\t") {
-     448             :         }
-     449           0 :         return os << mtrand.left;
-     450             : }
-     451             : 
-     452           0 : std::istream& operator>>(std::istream& is, Random& mtrand) {
-     453           0 :         uint32_t *s = mtrand.state;
-     454             :         int i = mtrand.N;
-     455           0 :         for (; i--; is >> *s++) {
-     456             :         }
-     457           0 :         is >> mtrand.left;
-     458           0 :         mtrand.pNext = &mtrand.state[mtrand.N - mtrand.left];
-     459           0 :         return is;
-     460             : }
-     461             : 
-     462             : #ifdef _OPENMP
-     463             : #include <omp.h>
-     464             : #include <stdexcept>
-     465             : 
-     466             : // see http://stackoverflow.com/questions/8051108/using-the-openmp-threadprivate-directive-on-static-instances-of-c-stl-types
-     467             : const static int MAX_THREAD = 256;
-     468             : 
-     469             : struct RANDOM_TLS_ITEM {
-     470             :         Random r;
-     471             :         char padding[(sizeof(Random) / 64 + 1) * 64 - sizeof(Random)];
-     472             : };
-     473             : 
-     474             : #ifdef _MSC_VER
-     475             : __declspec(align(64)) static RANDOM_TLS_ITEM _tls[MAX_THREAD];
-     476             : #else
-     477             : __attribute__ ((aligned(64))) static RANDOM_TLS_ITEM _tls[MAX_THREAD];
-     478             : #endif
-     479             : 
-     480     2658589 : Random &Random::instance() {
-     481     2658589 :         int i = omp_get_thread_num();
-     482     2658589 :         if (i >= MAX_THREAD)
-     483           0 :         throw std::runtime_error("crpropa::Random: more than MAX_THREAD threads!");
-     484     2658589 :         return _tls[i].r;
-     485             : }
-     486             : 
-     487           0 : void Random::seedThreads(const uint32_t oneSeed) {
-     488           0 :         for(size_t i = 0; i < MAX_THREAD; ++i)
-     489           0 :         _tls[i].r.seed(oneSeed + i);
-     490           0 : }
-     491             : 
-     492           0 : std::vector< std::vector<uint32_t> > Random::getSeedThreads()
-     493             : {
-     494             :         std::vector< std::vector<uint32_t> > seeds;
-     495           0 :         for(size_t i = 0; i < omp_get_num_threads(); ++i)
-     496           0 :                 seeds.push_back(_tls[i].r.getSeed() ); 
-     497           0 :         return seeds;
-     498           0 : }
-     499             : 
-     500             : #else
-     501             : static Random _random;
-     502             : Random &Random::instance() {
-     503             :         return _random;
-     504             : }
-     505             : void Random::seedThreads(const uint32_t oneSeed) {
-     506             :         _random.seed(oneSeed);
-     507             : }
-     508             : std::vector< std::vector<uint32_t> > Random::getSeedThreads()
-     509             : {
-     510             :         std::vector< std::vector<uint32_t> > seeds;
-     511             :                 seeds.push_back(_random.getSeed() ); 
-     512             :         return seeds;
-     513             : }
-     514             : #endif
-     515             : 
-     516           0 : const std::string Random::getSeed_base64() const
-     517             : {
-     518           0 :         return Base64::encode((unsigned char*) &initial_seed[0], sizeof(initial_seed[0]) * initial_seed.size() / sizeof(unsigned char));
-     519             : }
-     520             : 
-     521           1 : void Random::seed(const std::string &b64Seed)
-     522             : {
-     523           1 :         std::string decoded_data = Base64::decode(b64Seed);
-     524           1 :         size_t seedSize = decoded_data.size() * sizeof(decoded_data[0]) / sizeof(uint32_t);
-     525           1 :         seed((uint32_t*)decoded_data.c_str(), seedSize );
-     526           1 : }
-     527             : 
-     528             : } // namespace crpropa
-     529             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Source.cpp.func-sort-c.html b/doc/coverageReport/src/Source.cpp.func-sort-c.html deleted file mode 100644 index 34e0bcd2a..000000000 --- a/doc/coverageReport/src/Source.cpp.func-sort-c.html +++ /dev/null @@ -1,656 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Source.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Source.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:45978458.5 %
Date:2024-04-08 14:58:22Functions:8114655.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14SourcePositionC2Ed0
_ZN7crpropa15SourceDirection14setDescriptionEv0
_ZN7crpropa15SourceDirectionC2ENS_7Vector3IdEE0
_ZN7crpropa17SourceEmissionMap14setDescriptionEv0
_ZN7crpropa17SourceEmissionMap14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17SourceEmissionMapC2EPNS_11EmissionMapE0
_ZN7crpropa18SourceUniformShell14setDescriptionEv0
_ZN7crpropa18SourceUniformShellC2ENS_7Vector3IdEEd0
_ZN7crpropa21SourceSNRDistribution14setDescriptionEv0
_ZN7crpropa21SourceSNRDistribution7setBetaEd0
_ZN7crpropa21SourceSNRDistributionC2Ev0
_ZN7crpropa21SourceUniformCylinder14setDescriptionEv0
_ZN7crpropa21SourceUniformRedshift14setDescriptionEv0
_ZN7crpropa21SourceUniformRedshiftC2Edd0
_ZN7crpropa22SourceMassDistribution14getDescriptionB5cxx11Ev0
_ZN7crpropa22SourceMassDistribution15setMaximalTriesEi0
_ZN7crpropa22SourceMassDistribution17setMaximalDensityEd0
_ZN7crpropa22SourceMassDistribution9setXrangeEdd0
_ZN7crpropa22SourceMassDistribution9setYrangeEdd0
_ZN7crpropa22SourceMassDistribution9setZrangeEdd0
_ZN7crpropa22SourceMassDistributionC2ENS_7ref_ptrINS_7DensityEEEdddd0
_ZN7crpropa24SourceGenericComposition3addEiid0
_ZN7crpropa24SourcePulsarDistribution12getThetaBlurEv0
_ZN7crpropa24SourcePulsarDistribution12setThetaBlurEd0
_ZN7crpropa24SourcePulsarDistribution14setDescriptionEv0
_ZN7crpropa24SourcePulsarDistribution7getRMaxEv0
_ZN7crpropa24SourcePulsarDistribution7getZMaxEv0
_ZN7crpropa24SourcePulsarDistribution7setRMaxEd0
_ZN7crpropa24SourcePulsarDistribution7setZMaxEd0
_ZN7crpropa24SourcePulsarDistribution8getFrMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getFzMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getRBlurEv0
_ZN7crpropa24SourcePulsarDistribution8setFrMaxEdd0
_ZN7crpropa24SourcePulsarDistribution8setFzMaxEd0
_ZN7crpropa24SourcePulsarDistribution8setRBlurEd0
_ZN7crpropa24SourcePulsarDistributionC2Eddddd0
_ZN7crpropa24SourcePulsarDistributionC2Ev0
_ZN7crpropa27SourceMultipleParticleTypes14setDescriptionEv0
_ZN7crpropa27SourceMultipleParticleTypes3addEid0
_ZN7crpropa27SourceMultipleParticleTypesC2Ev0
_ZN7crpropa33SourceLambertDistributionOnSphere14setDescriptionEv0
_ZN7crpropa33SourceLambertDistributionOnSphereC2ERKNS_7Vector3IdEEdb0
_ZNK7crpropa10SourceList14getDescriptionB5cxx11Ev0
_ZNK7crpropa13SourceFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa15SourceDirection15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa17SourceEmissionMap16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa18SourceUniformShell15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa21SourceSNRDistribution7getBetaEv0
_ZNK7crpropa21SourceSNRDistribution7getRMaxEv0
_ZNK7crpropa21SourceSNRDistribution7getZMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getAlphaEv0
_ZNK7crpropa21SourceSNRDistribution8getFrMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getFzMaxEv0
_ZNK7crpropa21SourceUniformRedshift16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa22SourceMassDistribution14samplePositionEv0
_ZNK7crpropa22SourceMassDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa24SourcePulsarDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa24SourcePulsarDistribution2frEd0
_ZNK7crpropa24SourcePulsarDistribution2fzEd0
_ZNK7crpropa24SourcePulsarDistribution5blurREd0
_ZNK7crpropa24SourcePulsarDistribution6fthetaEid0
_ZNK7crpropa24SourcePulsarDistribution9blurThetaEdd0
_ZNK7crpropa27SourceMultipleParticleTypes15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa33SourceLambertDistributionOnSphere15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa6Source14getDescriptionB5cxx11Ev0
_ZN7crpropa14SourceRedshift14setDescriptionEv1
_ZN7crpropa14SourceRedshiftC2Ed1
_ZN7crpropa15SourceUniform1D14setDescriptionEv1
_ZN7crpropa15SourceUniform1DC2Eddb1
_ZN7crpropa16SourceRedshift1D14setDescriptionEv1
_ZN7crpropa16SourceRedshift1DC2Ev1
_ZN7crpropa16SourceUniformBox14setDescriptionEv1
_ZN7crpropa16SourceUniformBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa18SourceEmissionCone12setDirectionENS_7Vector3IdEE1
_ZN7crpropa18SourceEmissionCone14setDescriptionEv1
_ZN7crpropa18SourceEmissionConeC2ENS_7Vector3IdEEd1
_ZN7crpropa19SourceUniformSphere14setDescriptionEv1
_ZN7crpropa19SourceUniformSphereC2ENS_7Vector3IdEEd1
_ZN7crpropa21SourceSNRDistribution7setZMaxEd1
_ZN7crpropa21SourceSNRDistribution8setAlphaEd1
_ZN7crpropa21SourceSNRDistribution8setFzMaxEd1
_ZN7crpropa21SourceSNRDistributionC2Edddd1
_ZN7crpropa21SourceUniformCylinderC2ENS_7Vector3IdEEdd1
_ZN7crpropa22SourceDirectedEmission14setDescriptionEv1
_ZN7crpropa22SourceDirectedEmissionC2ENS_7Vector3IdEEd1
_ZN7crpropa23SourceMultiplePositions14setDescriptionEv1
_ZN7crpropa23SourceMultiplePositionsC2Ev1
_ZN7crpropa24SourceGenericComposition14setDescriptionEv1
_ZN7crpropa24SourceGenericCompositionC2EddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEm1
_ZN7crpropa25SourceUniformHollowSphere14setDescriptionEv1
_ZN7crpropa25SourceUniformHollowSphereC2ENS_7Vector3IdEEdd1
_ZN7crpropa9SourceTag14setDescriptionEv1
_ZN7crpropa9SourceTag6setTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa9SourceTagC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa14SourceRedshift16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa15SourceUniform1D15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa16SourceRedshift1D16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa16SourceUniformBox15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa18SourceEmissionCone15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa19SourceUniformSphere15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa21SourceUniformCylinder15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa9SourceTag16prepareCandidateERNS_9CandidateE1
_ZN7crpropa12SourceEnergy14setDescriptionEv2
_ZN7crpropa12SourceEnergyC2Ed2
_ZN7crpropa17SourceDensityGrid14setDescriptionEv2
_ZN7crpropa17SourceDensityGridC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa19SourceDensityGrid1D14setDescriptionEv2
_ZN7crpropa19SourceDensityGrid1DC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa21SourceSNRDistribution7setRMaxEd2
_ZN7crpropa21SourceSNRDistribution8setFrMaxEv2
_ZN7crpropa23SourceMultiplePositions3addENS_7Vector3IdEEd2
_ZN7crpropa23SourceRedshiftEvolutionC2Eddd2
_ZN7crpropa24SourceGenericComposition3addEid2
_ZN7crpropa10SourceList3addEPNS_6SourceEd3
_ZN7crpropa17SourceCompositionC2Eddd3
_ZN7crpropa18SourceParticleType14setDescriptionEv3
_ZN7crpropa18SourceParticleTypeC2Ei3
_ZN7crpropa23SourceIsotropicEmission14setDescriptionEv3
_ZN7crpropa23SourceIsotropicEmissionC2Ev3
_ZNK7crpropa17SourceComposition15prepareParticleERNS_13ParticleStateE3
_ZN7crpropa17SourceComposition3addEiid4
_ZN7crpropa22SourcePowerLawSpectrum14setDescriptionEv4
_ZN7crpropa22SourcePowerLawSpectrumC2Eddd4
_ZN7crpropa14SourcePosition14setDescriptionEv5
_ZN7crpropa14SourcePositionC2ENS_7Vector3IdEE5
_ZN7crpropa17SourceComposition3addEid5
_ZN7crpropa17SourceComposition14setDescriptionEv8
_ZN7crpropa6Source3addEPNS_13SourceFeatureE19
_ZNK7crpropa25SourceUniformHollowSphere15prepareParticleERNS_13ParticleStateE100
_ZNK7crpropa19SourceDensityGrid1D15prepareParticleERNS_13ParticleStateE101
_ZNK7crpropa23SourceRedshiftEvolution16prepareCandidateERNS_9CandidateE200
_ZNK7crpropa12SourceEnergy15prepareParticleERNS_13ParticleStateE1000
_ZNK7crpropa22SourceDirectedEmission16prepareCandidateERNS_9CandidateE1000
_ZNK7crpropa10SourceList12getCandidateEv1002
_ZNK7crpropa18SourceParticleType15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa23SourceIsotropicEmission15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa22SourcePowerLawSpectrum15prepareParticleERNS_13ParticleStateE1102
_ZNK7crpropa14SourcePosition15prepareParticleERNS_13ParticleStateE1103
_ZNK7crpropa6Source12getCandidateEv2103
_ZNK7crpropa13SourceFeature16prepareCandidateERNS_9CandidateE5407
_ZNK7crpropa23SourceMultiplePositions15prepareParticleERNS_13ParticleStateE10000
_ZNK7crpropa17SourceDensityGrid15prepareParticleERNS_13ParticleStateE10001
_ZNK7crpropa24SourceGenericComposition15prepareParticleERNS_13ParticleStateE100000
_ZNK7crpropa21SourceSNRDistribution15prepareParticleERNS_13ParticleStateE100001
_ZNK7crpropa21SourceSNRDistribution2frEd193272
_ZNK7crpropa21SourceSNRDistribution2fzEd1663640
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Source.cpp.func.html b/doc/coverageReport/src/Source.cpp.func.html deleted file mode 100644 index cbdfefa59..000000000 --- a/doc/coverageReport/src/Source.cpp.func.html +++ /dev/null @@ -1,656 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Source.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Source.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:45978458.5 %
Date:2024-04-08 14:58:22Functions:8114655.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10SourceList3addEPNS_6SourceEd3
_ZN7crpropa12SourceEnergy14setDescriptionEv2
_ZN7crpropa12SourceEnergyC2Ed2
_ZN7crpropa14SourcePosition14setDescriptionEv5
_ZN7crpropa14SourcePositionC2ENS_7Vector3IdEE5
_ZN7crpropa14SourcePositionC2Ed0
_ZN7crpropa14SourceRedshift14setDescriptionEv1
_ZN7crpropa14SourceRedshiftC2Ed1
_ZN7crpropa15SourceDirection14setDescriptionEv0
_ZN7crpropa15SourceDirectionC2ENS_7Vector3IdEE0
_ZN7crpropa15SourceUniform1D14setDescriptionEv1
_ZN7crpropa15SourceUniform1DC2Eddb1
_ZN7crpropa16SourceRedshift1D14setDescriptionEv1
_ZN7crpropa16SourceRedshift1DC2Ev1
_ZN7crpropa16SourceUniformBox14setDescriptionEv1
_ZN7crpropa16SourceUniformBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa17SourceComposition14setDescriptionEv8
_ZN7crpropa17SourceComposition3addEid5
_ZN7crpropa17SourceComposition3addEiid4
_ZN7crpropa17SourceCompositionC2Eddd3
_ZN7crpropa17SourceDensityGrid14setDescriptionEv2
_ZN7crpropa17SourceDensityGridC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa17SourceEmissionMap14setDescriptionEv0
_ZN7crpropa17SourceEmissionMap14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17SourceEmissionMapC2EPNS_11EmissionMapE0
_ZN7crpropa18SourceEmissionCone12setDirectionENS_7Vector3IdEE1
_ZN7crpropa18SourceEmissionCone14setDescriptionEv1
_ZN7crpropa18SourceEmissionConeC2ENS_7Vector3IdEEd1
_ZN7crpropa18SourceParticleType14setDescriptionEv3
_ZN7crpropa18SourceParticleTypeC2Ei3
_ZN7crpropa18SourceUniformShell14setDescriptionEv0
_ZN7crpropa18SourceUniformShellC2ENS_7Vector3IdEEd0
_ZN7crpropa19SourceDensityGrid1D14setDescriptionEv2
_ZN7crpropa19SourceDensityGrid1DC2ENS_7ref_ptrINS_4GridIfEEEE2
_ZN7crpropa19SourceUniformSphere14setDescriptionEv1
_ZN7crpropa19SourceUniformSphereC2ENS_7Vector3IdEEd1
_ZN7crpropa21SourceSNRDistribution14setDescriptionEv0
_ZN7crpropa21SourceSNRDistribution7setBetaEd0
_ZN7crpropa21SourceSNRDistribution7setRMaxEd2
_ZN7crpropa21SourceSNRDistribution7setZMaxEd1
_ZN7crpropa21SourceSNRDistribution8setAlphaEd1
_ZN7crpropa21SourceSNRDistribution8setFrMaxEv2
_ZN7crpropa21SourceSNRDistribution8setFzMaxEd1
_ZN7crpropa21SourceSNRDistributionC2Edddd1
_ZN7crpropa21SourceSNRDistributionC2Ev0
_ZN7crpropa21SourceUniformCylinder14setDescriptionEv0
_ZN7crpropa21SourceUniformCylinderC2ENS_7Vector3IdEEdd1
_ZN7crpropa21SourceUniformRedshift14setDescriptionEv0
_ZN7crpropa21SourceUniformRedshiftC2Edd0
_ZN7crpropa22SourceDirectedEmission14setDescriptionEv1
_ZN7crpropa22SourceDirectedEmissionC2ENS_7Vector3IdEEd1
_ZN7crpropa22SourceMassDistribution14getDescriptionB5cxx11Ev0
_ZN7crpropa22SourceMassDistribution15setMaximalTriesEi0
_ZN7crpropa22SourceMassDistribution17setMaximalDensityEd0
_ZN7crpropa22SourceMassDistribution9setXrangeEdd0
_ZN7crpropa22SourceMassDistribution9setYrangeEdd0
_ZN7crpropa22SourceMassDistribution9setZrangeEdd0
_ZN7crpropa22SourceMassDistributionC2ENS_7ref_ptrINS_7DensityEEEdddd0
_ZN7crpropa22SourcePowerLawSpectrum14setDescriptionEv4
_ZN7crpropa22SourcePowerLawSpectrumC2Eddd4
_ZN7crpropa23SourceIsotropicEmission14setDescriptionEv3
_ZN7crpropa23SourceIsotropicEmissionC2Ev3
_ZN7crpropa23SourceMultiplePositions14setDescriptionEv1
_ZN7crpropa23SourceMultiplePositions3addENS_7Vector3IdEEd2
_ZN7crpropa23SourceMultiplePositionsC2Ev1
_ZN7crpropa23SourceRedshiftEvolutionC2Eddd2
_ZN7crpropa24SourceGenericComposition14setDescriptionEv1
_ZN7crpropa24SourceGenericComposition3addEid2
_ZN7crpropa24SourceGenericComposition3addEiid0
_ZN7crpropa24SourceGenericCompositionC2EddNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEm1
_ZN7crpropa24SourcePulsarDistribution12getThetaBlurEv0
_ZN7crpropa24SourcePulsarDistribution12setThetaBlurEd0
_ZN7crpropa24SourcePulsarDistribution14setDescriptionEv0
_ZN7crpropa24SourcePulsarDistribution7getRMaxEv0
_ZN7crpropa24SourcePulsarDistribution7getZMaxEv0
_ZN7crpropa24SourcePulsarDistribution7setRMaxEd0
_ZN7crpropa24SourcePulsarDistribution7setZMaxEd0
_ZN7crpropa24SourcePulsarDistribution8getFrMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getFzMaxEv0
_ZN7crpropa24SourcePulsarDistribution8getRBlurEv0
_ZN7crpropa24SourcePulsarDistribution8setFrMaxEdd0
_ZN7crpropa24SourcePulsarDistribution8setFzMaxEd0
_ZN7crpropa24SourcePulsarDistribution8setRBlurEd0
_ZN7crpropa24SourcePulsarDistributionC2Eddddd0
_ZN7crpropa24SourcePulsarDistributionC2Ev0
_ZN7crpropa25SourceUniformHollowSphere14setDescriptionEv1
_ZN7crpropa25SourceUniformHollowSphereC2ENS_7Vector3IdEEdd1
_ZN7crpropa27SourceMultipleParticleTypes14setDescriptionEv0
_ZN7crpropa27SourceMultipleParticleTypes3addEid0
_ZN7crpropa27SourceMultipleParticleTypesC2Ev0
_ZN7crpropa33SourceLambertDistributionOnSphere14setDescriptionEv0
_ZN7crpropa33SourceLambertDistributionOnSphereC2ERKNS_7Vector3IdEEdb0
_ZN7crpropa6Source3addEPNS_13SourceFeatureE19
_ZN7crpropa9SourceTag14setDescriptionEv1
_ZN7crpropa9SourceTag6setTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa9SourceTagC2ENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa10SourceList12getCandidateEv1002
_ZNK7crpropa10SourceList14getDescriptionB5cxx11Ev0
_ZNK7crpropa12SourceEnergy15prepareParticleERNS_13ParticleStateE1000
_ZNK7crpropa13SourceFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa13SourceFeature16prepareCandidateERNS_9CandidateE5407
_ZNK7crpropa14SourcePosition15prepareParticleERNS_13ParticleStateE1103
_ZNK7crpropa14SourceRedshift16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa15SourceDirection15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa15SourceUniform1D15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa16SourceRedshift1D16prepareCandidateERNS_9CandidateE1
_ZNK7crpropa16SourceUniformBox15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa17SourceComposition15prepareParticleERNS_13ParticleStateE3
_ZNK7crpropa17SourceDensityGrid15prepareParticleERNS_13ParticleStateE10001
_ZNK7crpropa17SourceEmissionMap16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa18SourceEmissionCone15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa18SourceParticleType15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa18SourceUniformShell15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa19SourceDensityGrid1D15prepareParticleERNS_13ParticleStateE101
_ZNK7crpropa19SourceUniformSphere15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa21SourceSNRDistribution15prepareParticleERNS_13ParticleStateE100001
_ZNK7crpropa21SourceSNRDistribution2frEd193272
_ZNK7crpropa21SourceSNRDistribution2fzEd1663640
_ZNK7crpropa21SourceSNRDistribution7getBetaEv0
_ZNK7crpropa21SourceSNRDistribution7getRMaxEv0
_ZNK7crpropa21SourceSNRDistribution7getZMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getAlphaEv0
_ZNK7crpropa21SourceSNRDistribution8getFrMaxEv0
_ZNK7crpropa21SourceSNRDistribution8getFzMaxEv0
_ZNK7crpropa21SourceUniformCylinder15prepareParticleERNS_13ParticleStateE1
_ZNK7crpropa21SourceUniformRedshift16prepareCandidateERNS_9CandidateE0
_ZNK7crpropa22SourceDirectedEmission16prepareCandidateERNS_9CandidateE1000
_ZNK7crpropa22SourceMassDistribution14samplePositionEv0
_ZNK7crpropa22SourceMassDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa22SourcePowerLawSpectrum15prepareParticleERNS_13ParticleStateE1102
_ZNK7crpropa23SourceIsotropicEmission15prepareParticleERNS_13ParticleStateE1101
_ZNK7crpropa23SourceMultiplePositions15prepareParticleERNS_13ParticleStateE10000
_ZNK7crpropa23SourceRedshiftEvolution16prepareCandidateERNS_9CandidateE200
_ZNK7crpropa24SourceGenericComposition15prepareParticleERNS_13ParticleStateE100000
_ZNK7crpropa24SourcePulsarDistribution15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa24SourcePulsarDistribution2frEd0
_ZNK7crpropa24SourcePulsarDistribution2fzEd0
_ZNK7crpropa24SourcePulsarDistribution5blurREd0
_ZNK7crpropa24SourcePulsarDistribution6fthetaEid0
_ZNK7crpropa24SourcePulsarDistribution9blurThetaEdd0
_ZNK7crpropa25SourceUniformHollowSphere15prepareParticleERNS_13ParticleStateE100
_ZNK7crpropa27SourceMultipleParticleTypes15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa33SourceLambertDistributionOnSphere15prepareParticleERNS_13ParticleStateE0
_ZNK7crpropa6Source12getCandidateEv2103
_ZNK7crpropa6Source14getDescriptionB5cxx11Ev0
_ZNK7crpropa9SourceTag16prepareCandidateERNS_9CandidateE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Source.cpp.gcov.html b/doc/coverageReport/src/Source.cpp.gcov.html deleted file mode 100644 index 6cc5e6642..000000000 --- a/doc/coverageReport/src/Source.cpp.gcov.html +++ /dev/null @@ -1,1218 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Source.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Source.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:45978458.5 %
Date:2024-04-08 14:58:22Functions:8114655.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Source.h"
-       2             : #include "crpropa/Random.h"
-       3             : #include "crpropa/Cosmology.h"
-       4             : #include "crpropa/Common.h"
-       5             : #include "crpropa/Units.h"
-       6             : #include "crpropa/ParticleID.h"
-       7             : 
-       8             : #ifdef CRPROPA_HAVE_MUPARSER
-       9             : #include "muParser.h"
-      10             : #endif
-      11             : 
-      12             : #include <sstream>
-      13             : #include <stdexcept>
-      14             : 
-      15             : namespace crpropa {
-      16             : 
-      17             : // Source ---------------------------------------------------------------------
-      18          19 : void Source::add(SourceFeature* property) {
-      19          19 :         features.push_back(property);
-      20          19 : }
-      21             : 
-      22        2103 : ref_ptr<Candidate> Source::getCandidate() const {
-      23        4206 :         ref_ptr<Candidate> candidate = new Candidate();
-      24        7512 :         for (int i = 0; i < features.size(); i++)
-      25        5409 :                 (*features[i]).prepareCandidate(*candidate);
-      26        2103 :         return candidate;
-      27             : }
-      28             : 
-      29           0 : std::string Source::getDescription() const {
-      30           0 :         std::stringstream ss;
-      31           0 :         ss << "Cosmic ray source\n";
-      32           0 :         for (int i = 0; i < features.size(); i++)
-      33           0 :                 ss << "    " << features[i]->getDescription();
-      34           0 :         return ss.str();
-      35           0 : }
-      36             : 
-      37             : // SourceList------------------------------------------------------------------
-      38           3 : void SourceList::add(Source* source, double weight) {
-      39           6 :         sources.push_back(source);
-      40           3 :         if (cdf.size() > 0)
-      41           1 :                 weight += cdf.back();
-      42           3 :         cdf.push_back(weight);
-      43           3 : }
-      44             : 
-      45        1002 : ref_ptr<Candidate> SourceList::getCandidate() const {
-      46        1002 :         if (sources.size() == 0)
-      47           1 :                 throw std::runtime_error("SourceList: no sources set");
-      48        1001 :         size_t i = Random::instance().randBin(cdf);
-      49        1001 :         return (sources[i])->getCandidate();
-      50             : }
-      51             : 
-      52           0 : std::string SourceList::getDescription() const {
-      53           0 :         std::stringstream ss;
-      54           0 :         ss << "List of cosmic ray sources\n";
-      55           0 :         for (int i = 0; i < sources.size(); i++)
-      56           0 :                 ss << "  " << sources[i]->getDescription();
-      57           0 :         return ss.str();
-      58           0 : }
-      59             : 
-      60             : // SourceFeature---------------------------------------------------------------
-      61        5407 : void SourceFeature::prepareCandidate(Candidate& candidate) const {
-      62        5407 :         ParticleState &source = candidate.source;
-      63        5407 :         prepareParticle(source);
-      64             :         candidate.created = source;
-      65             :         candidate.current = source;
-      66             :         candidate.previous = source;
-      67        5407 : }
-      68             : 
-      69           0 : std::string SourceFeature::getDescription() const {
-      70           0 :         return description;
-      71             : }
-      72             : 
-      73             : // ----------------------------------------------------------------------------
-      74           3 : SourceParticleType::SourceParticleType(int id) :
-      75           3 :                 id(id) {
-      76           3 :         setDescription();
-      77           3 : }
-      78             : 
-      79        1101 : void SourceParticleType::prepareParticle(ParticleState& particle) const {
-      80        1101 :         particle.setId(id);
-      81        1101 : }
-      82             : 
-      83           3 : void SourceParticleType::setDescription() {
-      84           3 :         std::stringstream ss;
-      85           3 :         ss << "SourceParticleType: " << id << "\n";
-      86           3 :         description = ss.str();
-      87           3 : }
-      88             : 
-      89             : // ----------------------------------------------------------------------------
-      90           0 : SourceMultipleParticleTypes::SourceMultipleParticleTypes() {
-      91           0 :         setDescription();
-      92           0 : }
-      93             : 
-      94           0 : void SourceMultipleParticleTypes::add(int id, double a) {
-      95           0 :         particleTypes.push_back(id);
-      96           0 :         if (cdf.size() > 0)
-      97           0 :                 a += cdf.back();
-      98           0 :         cdf.push_back(a);
-      99           0 :         setDescription();
-     100           0 : }
-     101             : 
-     102           0 : void SourceMultipleParticleTypes::prepareParticle(ParticleState& particle) const {
-     103           0 :         if (particleTypes.size() == 0)
-     104           0 :                 throw std::runtime_error("SourceMultipleParticleTypes: no nuclei set");
-     105           0 :         size_t i = Random::instance().randBin(cdf);
-     106           0 :         particle.setId(particleTypes[i]);
-     107           0 : }
-     108             : 
-     109           0 : void SourceMultipleParticleTypes::setDescription() {
-     110           0 :         std::stringstream ss;
-     111           0 :         ss << "SourceMultipleParticleTypes: Random particle type\n";
-     112           0 :         for (int i = 0; i < particleTypes.size(); i++)
-     113           0 :                 ss << "      ID = " << particleTypes[i] << "\n";
-     114           0 :         description = ss.str();
-     115           0 : }
-     116             : 
-     117             : // ----------------------------------------------------------------------------
-     118           2 : SourceEnergy::SourceEnergy(double energy) :
-     119           2 :                 E(energy) {
-     120           2 :         setDescription();
-     121           2 : }
-     122             : 
-     123        1000 : void SourceEnergy::prepareParticle(ParticleState& p) const {
-     124        1000 :         p.setEnergy(E);
-     125        1000 : }
-     126             : 
-     127           2 : void SourceEnergy::setDescription() {
-     128           2 :         std::stringstream ss;
-     129           2 :         ss << "SourceEnergy: " << E / EeV << " EeV\n";
-     130           2 :         description = ss.str();
-     131           2 : }
-     132             : 
-     133             : // ----------------------------------------------------------------------------
-     134           4 : SourcePowerLawSpectrum::SourcePowerLawSpectrum(double Emin, double Emax,
-     135           4 :                 double index) :
-     136           4 :                 Emin(Emin), Emax(Emax), index(index) {
-     137           4 :         setDescription();
-     138           4 : }
-     139             : 
-     140        1102 : void SourcePowerLawSpectrum::prepareParticle(ParticleState& particle) const {
-     141        1102 :         Random &random = Random::instance();
-     142        1102 :         double E = random.randPowerLaw(index, Emin, Emax);
-     143        1102 :         particle.setEnergy(E);
-     144        1102 : }
-     145             : 
-     146           4 : void SourcePowerLawSpectrum::setDescription() {
-     147           4 :         std::stringstream ss;
-     148           4 :         ss << "SourcePowerLawSpectrum: Random energy ";
-     149           8 :         ss << "E = " << Emin / EeV << " - " << Emax / EeV << " EeV, ";
-     150           4 :         ss << "dN/dE ~ E^" << index  << "\n";
-     151           4 :         description = ss.str();
-     152           4 : }
-     153             : 
-     154             : // ----------------------------------------------------------------------------
-     155           3 : SourceComposition::SourceComposition(double Emin, double Rmax, double index) :
-     156           3 :                 Emin(Emin), Rmax(Rmax), index(index) {
-     157           3 :         setDescription();
-     158           3 : }
-     159             : 
-     160           5 : void SourceComposition::add(int id, double weight) {
-     161           5 :         nuclei.push_back(id);
-     162           5 :         int A = massNumber(id);
-     163           5 :         int Z = chargeNumber(id);
-     164             : 
-     165           5 :         double a = 1 + index;
-     166           5 :         if (std::abs(a) < std::numeric_limits<double>::min())
-     167           5 :                 weight *= log(Z * Rmax / Emin);
-     168             :         else
-     169           0 :                 weight *= (pow(Z * Rmax, a) - pow(Emin, a)) / a;
-     170             : 
-     171           5 :         weight *= pow(A, -a);
-     172             : 
-     173           5 :         if (cdf.size() > 0)
-     174           3 :                 weight += cdf.back();
-     175           5 :         cdf.push_back(weight);
-     176           5 :         setDescription();
-     177           5 : }
-     178             : 
-     179           4 : void SourceComposition::add(int A, int Z, double a) {
-     180           4 :         add(nucleusId(A, Z), a);
-     181           4 : }
-     182             : 
-     183           3 : void SourceComposition::prepareParticle(ParticleState& particle) const {
-     184           3 :         if (nuclei.size() == 0)
-     185           1 :                 throw std::runtime_error("SourceComposition: No source isotope set");
-     186             : 
-     187           2 :         Random &random = Random::instance();
-     188             : 
-     189             :         // draw random particle type
-     190           2 :         size_t i = random.randBin(cdf);
-     191           2 :         int id = nuclei[i];
-     192           2 :         particle.setId(id);
-     193             : 
-     194             :         // random energy from power law
-     195           2 :         int Z = chargeNumber(id);
-     196           2 :         particle.setEnergy(random.randPowerLaw(index, Emin, Z * Rmax));
-     197           2 : }
-     198             : 
-     199           8 : void SourceComposition::setDescription() {
-     200           8 :         std::stringstream ss;
-     201           8 :         ss << "SourceComposition: Random element and energy ";
-     202          16 :         ss << "E = " << Emin / EeV << " - Z*" << Rmax / EeV << " EeV, ";
-     203           8 :         ss << "dN/dE ~ E^" << index << "\n";
-     204          19 :         for (int i = 0; i < nuclei.size(); i++)
-     205          11 :                 ss << "      ID = " << nuclei[i] << "\n";
-     206           8 :         description = ss.str();
-     207           8 : }
-     208             : 
-     209             : // ----------------------------------------------------------------------------
-     210           5 : SourcePosition::SourcePosition(Vector3d position) :
-     211           5 :                 position(position) {
-     212           5 :         setDescription();
-     213           5 : }
-     214             : 
-     215           0 : SourcePosition::SourcePosition(double d) :
-     216           0 :                 position(Vector3d(d, 0, 0)) {
-     217           0 :         setDescription();
-     218           0 : }
-     219             : 
-     220        1103 : void SourcePosition::prepareParticle(ParticleState& particle) const {
-     221        1103 :         particle.setPosition(position);
-     222        1103 : }
-     223             : 
-     224           5 : void SourcePosition::setDescription() {
-     225           5 :         std::stringstream ss;
-     226           5 :         ss << "SourcePosition: " << position / Mpc << " Mpc\n";
-     227           5 :         description = ss.str();
-     228           5 : }
-     229             : 
-     230             : // ----------------------------------------------------------------------------
-     231           1 : SourceMultiplePositions::SourceMultiplePositions() {
-     232           1 :         setDescription();
-     233           1 : }
-     234             : 
-     235           2 : void SourceMultiplePositions::add(Vector3d pos, double weight) {
-     236           2 :         positions.push_back(pos);
-     237           2 :         if (cdf.size() > 0)
-     238           1 :                 weight += cdf.back();
-     239           2 :         cdf.push_back(weight);
-     240           2 : }
-     241             : 
-     242       10000 : void SourceMultiplePositions::prepareParticle(ParticleState& particle) const {
-     243       10000 :         if (positions.size() == 0)
-     244           0 :                 throw std::runtime_error("SourceMultiplePositions: no position set");
-     245       10000 :         size_t i = Random::instance().randBin(cdf);
-     246       10000 :         particle.setPosition(positions[i]);
-     247       10000 : }
-     248             : 
-     249           1 : void SourceMultiplePositions::setDescription() {
-     250           1 :         std::stringstream ss;
-     251           1 :         ss << "SourceMultiplePositions: Random position from list\n";
-     252           1 :         for (int i = 0; i < positions.size(); i++)
-     253           0 :                 ss << "  " << positions[i] / Mpc << " Mpc\n";
-     254           1 :         description = ss.str();
-     255           1 : }
-     256             : 
-     257             : // ----------------------------------------------------------------------------
-     258           1 : SourceUniformSphere::SourceUniformSphere(Vector3d center, double radius) :
-     259           1 :                 center(center), radius(radius) {
-     260           1 :         setDescription();
-     261           1 : }
-     262             : 
-     263           1 : void SourceUniformSphere::prepareParticle(ParticleState& particle) const {
-     264           1 :         Random &random = Random::instance();
-     265           1 :         double r = pow(random.rand(), 1. / 3.) * radius;
-     266           1 :         particle.setPosition(center + random.randVector() * r);
-     267           1 : }
-     268             : 
-     269           1 : void SourceUniformSphere::setDescription() {
-     270           1 :         std::stringstream ss;
-     271           1 :         ss << "SourceUniformSphere: Random position within a sphere at ";
-     272           1 :         ss << center / Mpc << " Mpc with";
-     273           1 :         ss  << radius / Mpc << " Mpc radius\n";
-     274           1 :         description = ss.str();
-     275           1 : }
-     276             : 
-     277             : // ----------------------------------------------------------------------------
-     278           1 : SourceUniformHollowSphere::SourceUniformHollowSphere(
-     279             :                 Vector3d center,
-     280             :                 double radius_inner,
-     281           1 :                 double radius_outer) :
-     282           1 :                 center(center), radius_inner(radius_inner),
-     283           1 :                 radius_outer(radius_outer) {
-     284           1 :         setDescription();
-     285           1 : }
-     286             : 
-     287         100 : void SourceUniformHollowSphere::prepareParticle(ParticleState& particle) const {
-     288         100 :         Random &random = Random::instance();
-     289         100 :         double r = radius_inner + pow(random.rand(), 1. / 3.) * (radius_outer - radius_inner);
-     290         100 :         particle.setPosition(center + random.randVector() * r);
-     291         100 : }
-     292             : 
-     293           1 : void SourceUniformHollowSphere::setDescription() {
-     294           1 :         std::stringstream ss;
-     295           1 :         ss << "SourceUniformHollowSphere: Random position within a sphere at ";
-     296           1 :         ss << center / Mpc << " Mpc with";
-     297           1 :         ss << radius_inner / Mpc << " Mpc inner radius\n";
-     298           1 :         ss << radius_outer / Mpc << " Mpc outer radius\n";
-     299           1 :         description = ss.str();
-     300           1 : }
-     301             : 
-     302             : // ----------------------------------------------------------------------------
-     303           0 : SourceUniformShell::SourceUniformShell(Vector3d center, double radius) :
-     304           0 :                 center(center), radius(radius) {
-     305           0 :         setDescription();
-     306           0 : }
-     307             : 
-     308           0 : void SourceUniformShell::prepareParticle(ParticleState& particle) const {
-     309           0 :         Random &random = Random::instance();
-     310           0 :         particle.setPosition(center + random.randVector() * radius);
-     311           0 : }
-     312             : 
-     313           0 : void SourceUniformShell::setDescription() {
-     314           0 :         std::stringstream ss;
-     315           0 :         ss << "SourceUniformShell: Random position on a spherical shell at ";
-     316           0 :         ss << center / Mpc << " Mpc with ";
-     317           0 :         ss << radius / Mpc << " Mpc radius\n";
-     318           0 :         description = ss.str();
-     319           0 : }
-     320             : 
-     321             : // ----------------------------------------------------------------------------
-     322           1 : SourceUniformBox::SourceUniformBox(Vector3d origin, Vector3d size) :
-     323           1 :                 origin(origin), size(size) {
-     324           1 :         setDescription();
-     325           1 : }
-     326             : 
-     327           1 : void SourceUniformBox::prepareParticle(ParticleState& particle) const {
-     328           1 :         Random &random = Random::instance();
-     329           1 :         Vector3d pos(random.rand(), random.rand(), random.rand());
-     330           1 :         particle.setPosition(pos * size + origin);
-     331           1 : }
-     332             : 
-     333           1 : void SourceUniformBox::setDescription() {
-     334           1 :         std::stringstream ss;
-     335           1 :         ss << "SourceUniformBox: Random uniform position in box with ";
-     336           1 :         ss << "origin = " << origin / Mpc << " Mpc and ";
-     337           1 :         ss << "size = " << size / Mpc << " Mpc\n";
-     338           1 :         description = ss.str();
-     339           1 : }
-     340             : 
-     341             : // ---------------------------------------------------------------------------
-     342           1 : SourceUniformCylinder::SourceUniformCylinder(Vector3d origin, double height, double radius) :
-     343           1 :     origin(origin), height(height), radius(radius) {
-     344           1 : }
-     345             : 
-     346           1 : void SourceUniformCylinder::prepareParticle(ParticleState& particle) const {
-     347           1 :   Random &random = Random::instance();
-     348           1 :   double phi = 2*M_PI*random.rand();
-     349           1 :   double RandRadius = radius*pow(random.rand(), 1. / 2.);
-     350           1 :   Vector3d pos(cos(phi)*RandRadius, sin(phi)*RandRadius, (-0.5+random.rand())*height);
-     351           1 :   particle.setPosition(pos + origin);
-     352           1 :   }
-     353             : 
-     354           0 : void SourceUniformCylinder::setDescription() {
-     355           0 :         std::stringstream ss;
-     356           0 :         ss << "SourceUniformCylinder: Random uniform position in cylinder with ";
-     357           0 :         ss << "origin = " << origin / Mpc << " Mpc and ";
-     358           0 :         ss << "radius = " << radius / Mpc << " Mpc and";
-     359           0 :         ss << "height = " << height / Mpc << " Mpc\n";
-     360           0 :         description = ss.str();
-     361           0 : }
-     362             : 
-     363             : // ---------------------------------------------------------------------------
-     364           0 : SourceSNRDistribution::SourceSNRDistribution() :
-     365           0 :     rEarth(8.5 * kpc), beta(3.53), zg(0.3 * kpc) {
-     366           0 :         setAlpha(2.);
-     367           0 :         setFrMax();
-     368           0 :         setFzMax(0.3 * kpc);
-     369           0 :         setRMax(20 * kpc);
-     370           0 :         setZMax(5 * kpc);
-     371           0 : }
-     372             : 
-     373           1 : SourceSNRDistribution::SourceSNRDistribution(double rEarth, double alpha, double beta, double zg) :
-     374           1 :     rEarth(rEarth), beta(beta), zg(zg) {
-     375           1 :         setAlpha(alpha);
-     376           1 :         setFrMax();
-     377           1 :         setFzMax(zg);
-     378           1 :         setRMax(20 * kpc);
-     379           1 :         setZMax(5 * kpc);
-     380           1 : }
-     381             : 
-     382      100001 : void SourceSNRDistribution::prepareParticle(ParticleState& particle) const {
-     383      100001 :         Random &random = Random::instance();
-     384             :         double RPos;
-     385             :         while (true) {
-     386      193272 :                 RPos = random.rand() * rMax;
-     387      193272 :                 double fTest = random.rand() * frMax;
-     388      193272 :                 double fR = fr(RPos);
-     389      193272 :                 if (fTest <= fR) {
-     390             :                         break;
-     391             :                 }
-     392             :         }
-     393             :         double ZPos;
-     394             :         while (true) {
-     395     1663640 :                 ZPos = (random.rand() - 0.5) * 2 * zMax;
-     396     1663640 :                 double fTest = random.rand() * fzMax;
-     397     1663640 :                 double fZ=fz(ZPos);
-     398     1663640 :                 if (fTest<=fZ) {
-     399             :                         break;
-     400             :                 }
-     401             :         }
-     402      100001 :         double phi = random.rand() * 2 * M_PI;
-     403      100001 :         Vector3d pos(cos(phi) * RPos, sin(phi) * RPos, ZPos);
-     404      100001 :         particle.setPosition(pos);
-     405      100001 : }
-     406             : 
-     407      193272 : double SourceSNRDistribution::fr(double r) const {
-     408      193272 :         return pow(r / rEarth, alpha) * exp(- beta * (r - rEarth) / rEarth);
-     409             : }
-     410             : 
-     411     1663640 : double SourceSNRDistribution::fz(double z) const{
-     412             :         double Az = 1.;
-     413     1663640 :         double f = 1. / zg * exp(- fabs(z) / zg);
-     414             :         double fz = Az * f;
-     415     1663640 :         return fz;
-     416             : }
-     417             : 
-     418           0 : double SourceSNRDistribution::getAlpha() const {
-     419           0 :         return alpha - 1;  // -1 to account for the R-term in the volume element dV = R * dR * dphi * dz
-     420             : }
-     421             : 
-     422           0 : double SourceSNRDistribution::getBeta() const {
-     423           0 :         return beta;
-     424             : }
-     425             : 
-     426           2 : void SourceSNRDistribution::setFrMax() {
-     427           2 :         frMax = pow(alpha / beta, alpha) * exp(beta - alpha);
-     428           2 :         return;
-     429             : }
-     430             : 
-     431           1 : void SourceSNRDistribution::setFzMax(double zg) {
-     432           1 :         fzMax = 1. / zg;
-     433           1 :         return;
-     434             : }
-     435             : 
-     436           2 : void SourceSNRDistribution::setRMax(double r) {
-     437           2 :         rMax = r;
-     438           2 :         return;
-     439             : }
-     440             : 
-     441           1 : void SourceSNRDistribution::setZMax(double z) {
-     442           1 :         zMax = z;
-     443           1 :         return;
-     444             : }
-     445             : 
-     446           0 : double SourceSNRDistribution::getFrMax() const {
-     447           0 :         return frMax;
-     448             : }
-     449             : 
-     450           0 : double SourceSNRDistribution::getFzMax() const {
-     451           0 :         return fzMax;
-     452             : }
-     453             : 
-     454           0 : double SourceSNRDistribution::getRMax() const {
-     455           0 :         return rMax;
-     456             : }
-     457             : 
-     458           0 : double SourceSNRDistribution::getZMax() const {
-     459           0 :         return zMax;
-     460             : }
-     461             : 
-     462           1 : void SourceSNRDistribution::setAlpha(double a) {
-     463           1 :         alpha = a + 1.; // add 1 for dV = r * dR * dphi * dz
-     464           1 :         setRMax(rMax);
-     465           1 :         setFrMax();
-     466           1 : }
-     467             : 
-     468           0 : void SourceSNRDistribution::setBeta(double b) {
-     469           0 :         beta = b;
-     470           0 :         setRMax(rMax);
-     471           0 :         setFrMax();
-     472           0 : }
-     473             : 
-     474           0 : void SourceSNRDistribution::setDescription() {
-     475           0 :         std::stringstream ss;
-     476           0 :         ss << "SourceSNRDistribution: Random position according to SNR distribution";
-     477           0 :         ss << "rEarth = " << rEarth / kpc << " kpc and ";
-     478           0 :         ss << "zg = " << zg / kpc << " kpc and";
-     479           0 :         ss << "beta = " << beta << " \n";
-     480           0 :         description = ss.str();
-     481           0 : }
-     482             : 
-     483             : // ---------------------------------------------------------------------------
-     484           0 : SourcePulsarDistribution::SourcePulsarDistribution() :
-     485           0 :     rEarth(8.5*kpc), beta(3.53), zg(0.3*kpc) {
-     486           0 :         setFrMax(8.5*kpc, 3.53);
-     487           0 :         setFzMax(0.3*kpc);
-     488           0 :         setRMax(22*kpc);
-     489           0 :         setZMax(5*kpc);
-     490           0 :         setRBlur(0.07);
-     491           0 :         setThetaBlur(0.35/kpc);
-     492           0 : }
-     493             : 
-     494           0 : SourcePulsarDistribution::SourcePulsarDistribution(double rEarth, double beta, double zg, double rB, double tB) :
-     495           0 :     rEarth(rEarth), beta(beta), zg(zg) {
-     496           0 :         setFrMax(rEarth, beta);
-     497           0 :         setFzMax(zg);
-     498           0 :         setRBlur(rB);
-     499           0 :         setThetaBlur(tB);
-     500           0 :         setRMax(22 * kpc);
-     501           0 :         setZMax(5 * kpc);
-     502           0 : }
-     503             : 
-     504           0 : void SourcePulsarDistribution::prepareParticle(ParticleState& particle) const {
-     505           0 :         Random &random = Random::instance();
-     506             :         double Rtilde;
-     507             :         while (true) {
-     508           0 :                 Rtilde = random.rand() * rMax;
-     509           0 :                 double fTest = random.rand() * frMax * 1.1;
-     510           0 :                 double fR = fr(Rtilde);
-     511           0 :                 if (fTest <= fR) {
-     512             :                         break;
-     513             :                 }
-     514             :         }
-     515             :         double ZPos;
-     516             :         while (true) {
-     517           0 :                 ZPos = (random.rand() - 0.5) * 2 * zMax;
-     518           0 :                 double fTest = random.rand() * fzMax;
-     519           0 :                 double fZ = fz(ZPos);
-     520           0 :                 if (fTest <= fZ) {
-     521             :                         break;
-     522             :                 }
-     523             :         }
-     524             : 
-     525           0 :         int i = random.randInt(3);
-     526           0 :         double thetaTilde = ftheta(i, Rtilde);
-     527           0 :         double RPos = blurR(Rtilde);
-     528           0 :         double phi = blurTheta(thetaTilde, Rtilde);
-     529           0 :         Vector3d pos(cos(phi) * RPos, sin(phi) * RPos, ZPos);
-     530             : 
-     531           0 :         particle.setPosition(pos);
-     532           0 :   }
-     533             : 
-     534           0 : double SourcePulsarDistribution::fr(double r) const {
-     535           0 :         double f = r * pow(r / rEarth, 2.) * exp(-beta * (r - rEarth) / rEarth);
-     536           0 :         return f;
-     537             : }
-     538             : 
-     539           0 : double SourcePulsarDistribution::fz(double z) const{
-     540             :         double Az = 1.;
-     541           0 :         double f = 1. / zg * exp(- fabs(z) / zg);
-     542             :         double fz = Az * f;
-     543           0 :         return fz;
-     544             : }
-     545             : 
-     546           0 : double SourcePulsarDistribution::ftheta(int i, double r) const {
-     547           0 :         const double k_0[] = {4.25, 4.25, 4.89, 4.89};
-     548           0 :         const double r_0[] = {3.48 * kpc, 3.48 * kpc, 4.9 * kpc, 4.9 * kpc};
-     549           0 :         const double theta_0[] = {0., 3.14, 2.52, -0.62};
-     550           0 :         double K = k_0[i];
-     551           0 :         double R = r_0[i];
-     552           0 :         double Theta = theta_0[i];
-     553             : 
-     554           0 :         double theta = K * log(r / R) + Theta;
-     555             : 
-     556           0 :         return theta;
-     557             : }
-     558             : 
-     559           0 : double SourcePulsarDistribution::blurR(double rTilde) const {
-     560           0 :         Random &random = Random::instance();
-     561           0 :         return random.randNorm(rTilde, rBlur * rTilde);
-     562             : }
-     563             : 
-     564           0 : double SourcePulsarDistribution::blurTheta(double thetaTilde, double rTilde) const {
-     565           0 :         Random &random = Random::instance();
-     566           0 :         double thetaCorr = (random.rand() - 0.5) * 2 * M_PI;
-     567           0 :         double tau = thetaCorr * exp(- thetaBlur * rTilde);
-     568           0 :         return thetaTilde + tau;
-     569             : }
-     570             : 
-     571           0 : void SourcePulsarDistribution::setFrMax(double R, double b) {
-     572           0 :         double r = 3 * R / b;
-     573           0 :         frMax = fr(r);
-     574           0 : }
-     575             : 
-     576           0 : void SourcePulsarDistribution::setFzMax(double zg) {
-     577           0 :         fzMax = 1. / zg;
-     578           0 :         return;
-     579             : }
-     580             : 
-     581           0 : void SourcePulsarDistribution::setRMax(double r) {
-     582           0 :         rMax = r;
-     583           0 :         return;
-     584             : }
-     585             : 
-     586           0 : void SourcePulsarDistribution::setZMax(double z) {
-     587           0 :         zMax = z;
-     588           0 :         return;
-     589             : }
-     590             : 
-     591           0 : void SourcePulsarDistribution::setRBlur(double r) {
-     592           0 :         rBlur = r;
-     593           0 :         return;
-     594             : }
-     595             : 
-     596           0 : void SourcePulsarDistribution::setThetaBlur(double theta) {
-     597           0 :         thetaBlur = theta;
-     598           0 :         return;
-     599             : }
-     600             : 
-     601           0 : double SourcePulsarDistribution::getFrMax() {
-     602           0 :         return frMax;
-     603             : }
-     604             : 
-     605           0 : double SourcePulsarDistribution::getFzMax() {
-     606           0 :         return fzMax;
-     607             : }
-     608             : 
-     609           0 : double SourcePulsarDistribution::getRMax() {
-     610           0 :         return rMax;
-     611             : }
-     612             : 
-     613           0 : double SourcePulsarDistribution::getZMax() {
-     614           0 :         return zMax;
-     615             : }
-     616             : 
-     617           0 : double SourcePulsarDistribution::getRBlur() {
-     618           0 :         return rBlur;
-     619             : }
-     620             : 
-     621           0 : double SourcePulsarDistribution::getThetaBlur() {
-     622           0 :         return thetaBlur;
-     623             : }
-     624             : 
-     625             : 
-     626           0 : void SourcePulsarDistribution::setDescription() {
-     627           0 :         std::stringstream ss;
-     628           0 :         ss << "SourcePulsarDistribution: Random position according to pulsar distribution";
-     629           0 :         ss << "rEarth = " << rEarth / kpc << " kpc and ";
-     630           0 :         ss << "zg = " << zg / kpc << " kpc and ";
-     631           0 :         ss << "beta = " << beta << " and ";
-     632           0 :         ss << "r_blur = " << rBlur << " and ";
-     633           0 :         ss << "theta blur = " << thetaBlur << "\n";
-     634           0 :         description = ss.str();
-     635           0 : }
-     636             : 
-     637             : // ----------------------------------------------------------------------------
-     638           1 : SourceUniform1D::SourceUniform1D(double minD, double maxD, bool withCosmology) {
-     639           1 :         this->withCosmology = withCosmology;
-     640           1 :         if (withCosmology) {
-     641           1 :                 this->minD = comoving2LightTravelDistance(minD);
-     642           1 :                 this->maxD = comoving2LightTravelDistance(maxD);
-     643             :         } else {
-     644           0 :                 this->minD = minD;
-     645           0 :                 this->maxD = maxD;
-     646             :         }
-     647           1 :         setDescription();
-     648           1 : }
-     649             : 
-     650           1 : void SourceUniform1D::prepareParticle(ParticleState& particle) const {
-     651           1 :         Random& random = Random::instance();
-     652           1 :         double d = random.rand() * (maxD - minD) + minD;
-     653           1 :         if (withCosmology)
-     654           1 :                 d = lightTravel2ComovingDistance(d);
-     655           1 :         particle.setPosition(Vector3d(d, 0, 0));
-     656           1 : }
-     657             : 
-     658           1 : void SourceUniform1D::setDescription() {
-     659           1 :         std::stringstream ss;
-     660           1 :         ss << "SourceUniform1D: Random uniform position in D = ";
-     661           2 :         ss << minD / Mpc << " - " << maxD / Mpc << " Mpc";
-     662           1 :         if (withCosmology)
-     663           1 :                 ss << " (including cosmology)";
-     664           1 :         ss << "\n";
-     665           1 :         description = ss.str();
-     666           1 : }
-     667             : 
-     668             : // ----------------------------------------------------------------------------
-     669           2 : SourceDensityGrid::SourceDensityGrid(ref_ptr<Grid1f> grid) :
-     670           2 :                 grid(grid) {
-     671             :         float sum = 0;
-     672          14 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     673         116 :                 for (int iy = 0; iy < grid->getNy(); iy++) {
-     674        1112 :                         for (int iz = 0; iz < grid->getNz(); iz++) {
-     675        1008 :                                 sum += grid->get(ix, iy, iz);
-     676        1008 :                                 grid->get(ix, iy, iz) = sum;
-     677             :                         }
-     678             :                 }
-     679             :         }
-     680           2 :         setDescription();
-     681           2 : }
-     682             : 
-     683       10001 : void SourceDensityGrid::prepareParticle(ParticleState& particle) const {
-     684       10001 :         Random &random = Random::instance();
-     685             : 
-     686             :         // draw random bin
-     687       10001 :         size_t i = random.randBin(grid->getGrid());
-     688       10001 :         Vector3d pos = grid->positionFromIndex(i);
-     689             : 
-     690             :         // draw uniform position within bin
-     691       10001 :         double dx = random.rand() - 0.5;
-     692       10001 :         double dy = random.rand() - 0.5;
-     693       10001 :         double dz = random.rand() - 0.5;
-     694             :         pos += Vector3d(dx, dy, dz) * grid->getSpacing();
-     695             : 
-     696       10001 :         particle.setPosition(pos);
-     697       10001 : }
-     698             : 
-     699           2 : void SourceDensityGrid::setDescription() {
-     700           2 :         description = "SourceDensityGrid: 3D source distribution according to density grid\n";
-     701           2 : }
-     702             : 
-     703             : // ----------------------------------------------------------------------------
-     704           2 : SourceDensityGrid1D::SourceDensityGrid1D(ref_ptr<Grid1f> grid) :
-     705           2 :                 grid(grid) {
-     706           2 :         if (grid->getNy() != 1)
-     707           0 :                 throw std::runtime_error("SourceDensityGrid1D: Ny != 1");
-     708           2 :         if (grid->getNz() != 1)
-     709           0 :                 throw std::runtime_error("SourceDensityGrid1D: Nz != 1");
-     710             : 
-     711             :         float sum = 0;
-     712          22 :         for (int ix = 0; ix < grid->getNx(); ix++) {
-     713          20 :                 sum += grid->get(ix, 0, 0);
-     714          20 :                 grid->get(ix, 0, 0) = sum;
-     715             :         }
-     716           2 :         setDescription();
-     717           2 : }
-     718             : 
-     719         101 : void SourceDensityGrid1D::prepareParticle(ParticleState& particle) const {
-     720         101 :         Random &random = Random::instance();
-     721             : 
-     722             :         // draw random bin
-     723         101 :         size_t i = random.randBin(grid->getGrid());
-     724         101 :         Vector3d pos = grid->positionFromIndex(i);
-     725             : 
-     726             :         // draw uniform position within bin
-     727         101 :         double dx = random.rand() - 0.5;
-     728         101 :         pos.x += dx * grid->getSpacing().x;
-     729             : 
-     730         101 :         particle.setPosition(pos);
-     731         101 : }
-     732             : 
-     733           2 : void SourceDensityGrid1D::setDescription() {
-     734           2 :         description = "SourceDensityGrid1D: 1D source distribution according to density grid\n";
-     735           2 : }
-     736             : 
-     737             : // ----------------------------------------------------------------------------
-     738           3 : SourceIsotropicEmission::SourceIsotropicEmission() {
-     739           3 :         setDescription();
-     740           3 : }
-     741             : 
-     742        1101 : void SourceIsotropicEmission::prepareParticle(ParticleState& particle) const {
-     743        1101 :         Random &random = Random::instance();
-     744        1101 :         particle.setDirection(random.randVector());
-     745        1101 : }
-     746             : 
-     747           3 : void SourceIsotropicEmission::setDescription() {
-     748           3 :         description = "SourceIsotropicEmission: Random isotropic direction\n";
-     749           3 : }
-     750             : 
-     751             : // ----------------------------------------------------------------------------
-     752           1 : SourceDirectedEmission::SourceDirectedEmission(Vector3d mu, double kappa): mu(mu), kappa(kappa) {
-     753           1 :         if (kappa <= 0)
-     754           0 :                 throw std::runtime_error("The concentration parameter kappa should be larger than 0.");
-     755           1 :         setDescription();
-     756           1 : }
-     757             : 
-     758        1000 : void SourceDirectedEmission::prepareCandidate(Candidate &candidate) const {
-     759        1000 :         Random &random = Random::instance();
-     760             : 
-     761             :         Vector3d muvec = mu / mu.getR();
-     762        1000 :         Vector3d v = random.randFisherVector(muvec, kappa);
-     763             : 
-     764        1000 :         v = v.getUnitVector();
-     765        1000 :         candidate.source.setDirection(v);
-     766        1000 :         candidate.created.setDirection(v);
-     767        1000 :         candidate.previous.setDirection(v);
-     768        1000 :         candidate.current.setDirection(v);
-     769             : 
-     770             :         //set the weight of the particle, see eq. 3.1 of PoS(ICRC2019)447
-     771        1000 :         double pdfVonMises = kappa / (2. * M_PI * (1. - exp(-2. * kappa))) * exp(-kappa * (1. - v.dot(mu)));
-     772        1000 :         double weight = 1. / (4. * M_PI * pdfVonMises);
-     773        1000 :         candidate.setWeight(weight);
-     774        1000 : }
-     775             : 
-     776           1 : void SourceDirectedEmission::setDescription() {
-     777           1 :         std::stringstream ss;
-     778           1 :         ss << "SourceDirectedEmission: Random directed emission following the von-Mises-Fisher distribution with mean direction ";
-     779           1 :         ss << mu << " and concentration parameter kappa = ";
-     780           1 :         ss << kappa << "\n";
-     781           1 :         description = ss.str();
-     782           1 : }
-     783             : 
-     784             : // ----------------------------------------------------------------------------
-     785           0 : SourceLambertDistributionOnSphere::SourceLambertDistributionOnSphere(const Vector3d &center, double radius, bool inward) :
-     786           0 :                 center(center), radius(radius) {
-     787           0 :         this->inward = inward;
-     788           0 :         setDescription();
-     789           0 : }
-     790             : 
-     791           0 : void SourceLambertDistributionOnSphere::prepareParticle(ParticleState& particle) const {
-     792           0 :         Random &random = Random::instance();
-     793           0 :         Vector3d normalVector = random.randVector();
-     794           0 :         particle.setPosition(center + normalVector * radius);
-     795           0 :         double sign = inward ? -1 : 1; // negative (positive) Lamberts vector for inward (outward) directed emission
-     796           0 :         particle.setDirection(Vector3d(0, 0, 0) + sign * random.randVectorLamberts(normalVector));
-     797           0 : }
-     798             : 
-     799           0 : void SourceLambertDistributionOnSphere::setDescription() {
-     800           0 :         std::stringstream ss;
-     801           0 :         ss << "SourceLambertDistributionOnSphere: Random position and direction on a Sphere with center ";
-     802           0 :         ss << center / kpc << " kpc and ";
-     803           0 :         ss << radius / kpc << " kpc radius\n";
-     804           0 :         description = ss.str();
-     805           0 : }
-     806             : 
-     807             : // ----------------------------------------------------------------------------
-     808           0 : SourceDirection::SourceDirection(Vector3d direction) :
-     809           0 :                 direction(direction) {
-     810           0 :         setDescription();
-     811           0 : }
-     812             : 
-     813           0 : void SourceDirection::prepareParticle(ParticleState& particle) const {
-     814           0 :         particle.setDirection(direction);
-     815           0 : }
-     816             : 
-     817           0 : void SourceDirection::setDescription() {
-     818           0 :         std::stringstream ss;
-     819           0 :         ss <<  "SourceDirection: Emission direction = " << direction << "\n";
-     820           0 :         description = ss.str();
-     821           0 : }
-     822             : 
-     823             : // ----------------------------------------------------------------------------
-     824           0 : SourceEmissionMap::SourceEmissionMap(EmissionMap *emissionMap) : emissionMap(emissionMap) {
-     825           0 :         setDescription();
-     826           0 : }
-     827             : 
-     828           0 : void SourceEmissionMap::prepareCandidate(Candidate &candidate) const {
-     829           0 :         if (emissionMap) {
-     830           0 :                 bool accept = emissionMap->checkDirection(candidate.source);
-     831           0 :                 candidate.setActive(accept);
-     832             :         }
-     833           0 : }
-     834             : 
-     835           0 : void SourceEmissionMap::setDescription() {
-     836           0 :         description = "SourceEmissionMap: accept only directions from emission map\n";
-     837           0 : }
-     838             : 
-     839           0 : void SourceEmissionMap::setEmissionMap(EmissionMap *emissionMap) {
-     840           0 :         this->emissionMap = emissionMap;
-     841           0 : }
-     842             : 
-     843             : // ----------------------------------------------------------------------------
-     844           1 : SourceEmissionCone::SourceEmissionCone(Vector3d direction, double aperture) :
-     845           1 :         aperture(aperture) {
-     846           1 :         setDirection(direction);
-     847           1 :         setDescription();
-     848             :         
-     849           1 : }
-     850             : 
-     851           1 : void SourceEmissionCone::prepareParticle(ParticleState& particle) const {
-     852           1 :         Random &random = Random::instance();
-     853           1 :         particle.setDirection(random.randConeVector(direction, aperture));
-     854           1 : }
-     855             : 
-     856           1 : void SourceEmissionCone::setDirection(Vector3d dir) {
-     857           1 :         if (dir.getR() == 0) {
-     858           0 :                 throw std::runtime_error("SourceEmissionCone: The direction vector was a null vector.");
-     859             :         } else {
-     860           1 :                 direction = dir.getUnitVector();
-     861             :         }
-     862           1 : }
-     863             : 
-     864           1 : void SourceEmissionCone::setDescription() {
-     865           1 :         std::stringstream ss;
-     866           1 :         ss << "SourceEmissionCone: Jetted emission in ";
-     867           1 :         ss << "direction = " << direction << " with ";
-     868           1 :         ss << "half-opening angle = " << aperture << " rad\n";
-     869           1 :         description = ss.str();
-     870           1 : }
-     871             : 
-     872             : // ----------------------------------------------------------------------------
-     873           1 : SourceRedshift::SourceRedshift(double z) :
-     874           1 :                 z(z) {
-     875           1 :         setDescription();
-     876           1 : }
-     877             : 
-     878           1 : void SourceRedshift::prepareCandidate(Candidate& candidate) const {
-     879           1 :         candidate.setRedshift(z);
-     880           1 : }
-     881             : 
-     882           1 : void SourceRedshift::setDescription() {
-     883           1 :         std::stringstream ss;
-     884           1 :         ss << "SourceRedshift: Redshift z = " << z << "\n";
-     885           1 :         description = ss.str();
-     886           1 : }
-     887             : 
-     888             : // ----------------------------------------------------------------------------
-     889           0 : SourceUniformRedshift::SourceUniformRedshift(double zmin, double zmax) :
-     890           0 :                 zmin(zmin), zmax(zmax) {
-     891           0 :         setDescription();
-     892           0 : }
-     893             : 
-     894           0 : void SourceUniformRedshift::prepareCandidate(Candidate& candidate) const {
-     895           0 :         double z = Random::instance().randUniform(zmin, zmax);
-     896           0 :         candidate.setRedshift(z);
-     897           0 : }
-     898             : 
-     899           0 : void SourceUniformRedshift::setDescription() {
-     900           0 :         std::stringstream ss;
-     901           0 :         ss << "SourceUniformRedshift: Uniform redshift in z = ";
-     902           0 :         ss << zmin << " - " << zmax << "\n";
-     903           0 :         description = ss.str();
-     904           0 : }
-     905             : 
-     906             : // ----------------------------------------------------------------------------
-     907           2 : SourceRedshiftEvolution::SourceRedshiftEvolution(double m, double zmin, double zmax) : m(m), zmin(zmin), zmax(zmax) {
-     908           2 :         std::stringstream ss;
-     909             :         ss << "SourceRedshiftEvolution: (1+z)^m, m = " << m;
-     910           2 :         ss << ", z = " << zmin << " - " << zmax << "\n";
-     911           2 :         description = ss.str();
-     912           2 : }
-     913             : 
-     914         200 : void SourceRedshiftEvolution::prepareCandidate(Candidate& candidate) const {
-     915         200 :         double x = Random::instance().randUniform(0, 1);
-     916             :         double norm, z;
-     917             : 
-     918             :         // special case: m=-1
-     919         200 :         if ((std::abs(m+1)) < std::numeric_limits<double>::epsilon()) {
-     920         100 :                 norm = log1p(zmax) - log1p(zmin);
-     921         100 :                 z = exp(norm*x) * (1+zmin) - 1;
-     922             :         } else {
-     923         100 :                 norm = ( pow(1+zmax, m+1) - pow(1+zmin, m+1) ) / (m+1);
-     924         100 :                 z = pow( norm*(m+1)*x + pow(1+zmin, m+1), 1./(m+1)) - 1;
-     925             :         }
-     926         200 :         candidate.setRedshift(z);
-     927         200 : }
-     928             : 
-     929             : // ----------------------------------------------------------------------------
-     930           1 : SourceRedshift1D::SourceRedshift1D() {
-     931           1 :         setDescription();
-     932           1 : }
-     933             : 
-     934           1 : void SourceRedshift1D::prepareCandidate(Candidate& candidate) const {
-     935           1 :         double d = candidate.source.getPosition().getR();
-     936           1 :         double z = comovingDistance2Redshift(d);
-     937           1 :         candidate.setRedshift(z);
-     938           1 : }
-     939             : 
-     940           1 : void SourceRedshift1D::setDescription() {
-     941           1 :         description = "SourceRedshift1D: Redshift according to source distance\n";
-     942           1 : }
-     943             : 
-     944             : // ----------------------------------------------------------------------------
-     945             : #ifdef CRPROPA_HAVE_MUPARSER
-     946           1 : SourceGenericComposition::SourceGenericComposition(double Emin, double Emax, std::string expression, size_t bins) :
-     947           2 :         Emin(Emin), Emax(Emax), expression(expression), bins(bins) {
-     948             : 
-     949             :         // precalculate energy bins
-     950           1 :         double logEmin = ::log10(Emin);
-     951           1 :         double logEmax = ::log10(Emax);
-     952           1 :         double logStep = (logEmax - logEmin) / bins;
-     953           1 :         energy.resize(bins + 1);
-     954        1026 :         for (size_t i = 0; i <= bins; i++) {
-     955        1025 :                 energy[i] = ::pow(10, logEmin + i * logStep);
-     956             :         }
-     957           1 :         setDescription();
-     958           1 : }
-     959             : 
-     960           2 : void SourceGenericComposition::add(int id, double weight) {
-     961           2 :         int A = massNumber(id);
-     962           2 :         int Z = chargeNumber(id);
-     963             : 
-     964             :         Nucleus n;
-     965           2 :         n.id = id;
-     966             : 
-     967             :         // calculate nuclei cdf
-     968           2 :         mu::Parser p;
-     969             :         double E;
-     970           2 :         p.DefineVar("E", &E);
-     971           2 :         p.DefineConst("Emin", Emin);
-     972           2 :         p.DefineConst("Emax", Emax);
-     973           2 :         p.DefineConst("bins", bins);
-     974           2 :         p.DefineConst("A", (double)A);
-     975           2 :         p.DefineConst("Z", (double)Z);
-     976             : 
-     977           2 :         p.DefineConst("MeV", MeV);
-     978           2 :         p.DefineConst("GeV", GeV);
-     979           2 :         p.DefineConst("TeV", TeV);
-     980           2 :         p.DefineConst("PeV", PeV);
-     981           2 :         p.DefineConst("EeV", EeV);
-     982             : 
-     983           2 :         p.SetExpr(expression);
-     984             : 
-     985             :         // calculate pdf
-     986           2 :         n.cdf.resize(bins + 1);
-     987             : 
-     988        2052 :         for (std::size_t i=0; i<=bins; ++i) {
-     989        2050 :                 E = energy[i];
-     990        2050 :                 n.cdf[i] = p.Eval();
-     991             :         }
-     992             : 
-     993             :         // integrate
-     994        2050 :         for (std::size_t i=bins; i>0; --i) {
-     995        2048 :                 n.cdf[i] = (n.cdf[i-1] + n.cdf[i]) * (energy[i] - energy[i-1]) / 2;
-     996             :         }
-     997           2 :         n.cdf[0] = 0;
-     998             : 
-     999             :         // cumulate
-    1000        2050 :         for (std::size_t i=1; i<=bins; ++i) {
-    1001        2048 :                 n.cdf[i] += n.cdf[i-1];
-    1002             :         }
-    1003             : 
-    1004           2 :         nuclei.push_back(n);
-    1005             : 
-    1006             :         // update composition cdf
-    1007           2 :         if (cdf.size() == 0)
-    1008           1 :                 cdf.push_back(weight * n.cdf.back());
-    1009             :         else
-    1010           1 :                 cdf.push_back(cdf.back() + weight * n.cdf.back());
-    1011           2 : }
-    1012             : 
-    1013           0 : void SourceGenericComposition::add(int A, int Z, double a) {
-    1014           0 :         add(nucleusId(A, Z), a);
-    1015           0 : }
-    1016             : 
-    1017      100000 : void SourceGenericComposition::prepareParticle(ParticleState& particle) const {
-    1018      100000 :         if (nuclei.size() == 0)
-    1019           0 :                 throw std::runtime_error("SourceComposition: No source isotope set");
-    1020             : 
-    1021      100000 :         Random &random = Random::instance();
-    1022             : 
-    1023             : 
-    1024             :         // draw random particle type
-    1025      100000 :         size_t iN = random.randBin(cdf);
-    1026             :         const Nucleus &n = nuclei.at(iN);
-    1027      100000 :         particle.setId(n.id);
-    1028             : 
-    1029             :         // random energy
-    1030      100000 :         double E = interpolate(random.rand() * n.cdf.back(), n.cdf, energy);
-    1031      100000 :         particle.setEnergy(E);
-    1032      100000 : }
-    1033             : 
-    1034           1 : void SourceGenericComposition::setDescription() {
-    1035           1 :         description = "Generice source composition" + expression;
-    1036           1 : }
-    1037             : 
-    1038             : #endif
-    1039             : 
-    1040             : // ----------------------------------------------------------------------------
-    1041             : 
-    1042           1 : SourceTag::SourceTag(std::string tag) {
-    1043           1 :         setTag(tag);
-    1044           1 : }
-    1045             : 
-    1046           1 : void SourceTag::prepareCandidate(Candidate &cand) const {
-    1047           1 :         cand.setTagOrigin(sourceTag);
-    1048           1 : }
-    1049             : 
-    1050           1 : void SourceTag::setDescription() {
-    1051           1 :         description = "SourceTag: " + sourceTag;
-    1052           1 : }
-    1053             : 
-    1054           1 : void SourceTag::setTag(std::string tag) {
-    1055           1 :         sourceTag = tag;
-    1056           1 :         setDescription();
-    1057           1 : }
-    1058             : 
-    1059             : // ----------------------------------------------------------------------------
-    1060             : 
-    1061           0 : SourceMassDistribution::SourceMassDistribution(ref_ptr<Density> density, double max, double x, double y, double z) : 
-    1062           0 :         density(density), maxDensity(max), xMin(-x), xMax(x), yMin(-y), yMax(y), zMin(-z), zMax(z) {}
-    1063             : 
-    1064           0 : void SourceMassDistribution::setMaximalDensity(double maxDensity) {
-    1065           0 :         if (maxDensity <= 0) {
-    1066           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: maximal density must be larger than 0. Nothing changed.\n";
-    1067           0 :                 return;
-    1068             :         }
-    1069           0 :         this->maxDensity = maxDensity;
-    1070             : }
-    1071             : 
-    1072           0 : void SourceMassDistribution::setXrange(double xMin, double xMax) {
-    1073           0 :         if (xMin > xMax) {
-    1074           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: minimal x-value must not exceed the maximal one\n";
-    1075           0 :                 return;
-    1076             :         }
-    1077           0 :         this -> xMin = xMin;
-    1078           0 :         this -> xMax = xMax;
-    1079             : }
-    1080             : 
-    1081           0 : void SourceMassDistribution::setYrange(double yMin, double yMax) {
-    1082           0 :         if (yMin > yMax) {
-    1083           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: minimal y-value must not exceed the maximal one\n";
-    1084           0 :                 return;
-    1085             :         }
-    1086           0 :         this -> yMin = yMin;
-    1087           0 :         this -> yMax = yMax;
-    1088             : }
-    1089             : 
-    1090           0 : void SourceMassDistribution::setZrange(double zMin, double zMax) {
-    1091           0 :         if (zMin > zMax) {
-    1092           0 :                 KISS_LOG_WARNING << "SourceMassDistribution: minimal z-value must not exceed the maximal one\n";
-    1093           0 :                 return;
-    1094             :         }
-    1095           0 :         this -> zMin = zMin;
-    1096           0 :         this -> zMax = zMax;
-    1097             : }
-    1098             : 
-    1099           0 : Vector3d SourceMassDistribution::samplePosition() const {
-    1100             :         Vector3d pos; 
-    1101           0 :         Random &rand = Random::instance();
-    1102             : 
-    1103           0 :         for (int i = 0; i < maxTries; i++) {
-    1104           0 :                 pos.x = rand.randUniform(xMin, xMax);
-    1105           0 :                 pos.y = rand.randUniform(yMin, yMax);
-    1106           0 :                 pos.z = rand.randUniform(zMin, zMax);
-    1107             : 
-    1108           0 :                 double n_density = density->getDensity(pos) / maxDensity;
-    1109           0 :                 double n_test = rand.rand();
-    1110           0 :                 if (n_test < n_density) {
-    1111             :                         return pos;
-    1112             :                 }
-    1113             :         }
-    1114           0 :         KISS_LOG_WARNING << "SourceMassDistribution: sampling a position was not possible within " 
-    1115           0 :                 << maxTries << " tries. Please check the maximum density or increse the number of maximal tries. \n";
-    1116             :         return Vector3d(0.);
-    1117             : }       
-    1118             : 
-    1119           0 : void SourceMassDistribution::prepareParticle(ParticleState &state) const {
-    1120           0 :         Vector3d pos = samplePosition();
-    1121           0 :         state.setPosition(pos);
-    1122           0 : }
-    1123             : 
-    1124           0 : void SourceMassDistribution::setMaximalTries(int tries) {
-    1125           0 :         this -> maxTries = tries;
-    1126           0 : }
-    1127             : 
-    1128           0 : std::string SourceMassDistribution::getDescription() {
-    1129           0 :         std::stringstream ss;
-    1130           0 :         ss << "SourceMassDistribuion: following the density distribution :\n";
-    1131           0 :         ss << "\t" << density -> getDescription();
-    1132           0 :         ss << "with a maximal density of " << maxDensity << " / m^3 \n";
-    1133           0 :         ss << "using the sampling range: \n";
-    1134           0 :         ss << "\t x in [" << xMin / kpc << " ; " << xMax / kpc << "] kpc \n";
-    1135           0 :         ss << "\t y in [" << yMin / kpc << " ; " << yMax / kpc << "] kpc \n";
-    1136           0 :         ss << "\t z in [" << zMin / kpc << " ; " << zMax / kpc << "] kpc \n";
-    1137           0 :         ss << "with maximal number of tries for sampling of " << maxTries << "\n";
-    1138             : 
-    1139           0 :         return ss.str();
-    1140           0 : }
-    1141             : 
-    1142             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Variant.cpp.func-sort-c.html b/doc/coverageReport/src/Variant.cpp.func-sort-c.html deleted file mode 100644 index 3bcf5eae5..000000000 --- a/doc/coverageReport/src/Variant.cpp.func-sort-c.html +++ /dev/null @@ -1,264 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Variant.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Variant.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7151913.7 %
Date:2024-04-08 14:58:22Functions:184837.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Variant11getTypeNameENS0_4TypeE0
_ZN7crpropa7Variant6resizeEm0
_ZN7crpropa7Variant6toTypeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa7VariantC2ENS0_4TypeE0
_ZN7crpropa7VariantcvRSt6vectorIS0_SaIS0_EEEv0
_ZN7crpropa7VariantixEm0
_ZN7crpropalsERSoRKNS_7VariantE0
_ZNK7crpropa7Variant10toVector3cEv0
_ZNK7crpropa7Variant10toVector3dEv0
_ZNK7crpropa7Variant10toVector3fEv0
_ZNK7crpropa7Variant11getTypeNameEv0
_ZNK7crpropa7Variant12toLongDoubleEv0
_ZNK7crpropa7Variant14toComplexFloatEv0
_ZNK7crpropa7Variant15toComplexDoubleEv0
_ZNK7crpropa7Variant4sizeEv0
_ZNK7crpropa7Variant6toCharEv0
_ZNK7crpropa7Variant7getSizeEv0
_ZNK7crpropa7Variant7toFloatEv0
_ZNK7crpropa7Variant7toInt16Ev0
_ZNK7crpropa7Variant7toInt32Ev0
_ZNK7crpropa7Variant7toUCharEv0
_ZNK7crpropa7Variant8toUInt16Ev0
_ZNK7crpropa7Variant8toUInt32Ev0
_ZNK7crpropa7Variant8toUInt64Ev0
_ZNK7crpropa7Variant8toVectorEv0
_ZNK7crpropa7Variant9getSizeOfEv0
_ZNK7crpropa7VariantcvRKSt6vectorIS0_SaIS0_EEEv0
_ZNK7crpropa7VariantixEm0
_ZNK7crpropa7VariantneEPKc0
_ZNK7crpropa7VariantneERKS0_0
_ZN7crpropa7Variant12copyToBufferEPv1
_ZN7crpropa7Variant10fromStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS0_4TypeE2
_ZNK7crpropa7Variant5checkENS0_4TypeE2
_ZNK7crpropa7Variant6toBoolEv2
_ZNK7crpropa7Variant7toInt64Ev2
_ZN7crpropa7VariantC2EPKc3
_ZNK7crpropa7VarianteqERKS0_4
_ZNK7crpropa7Variant8toDoubleEv6
_ZNK7crpropa7Variant8toStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE6
_ZNK7crpropa7Variant7isValidEv8
_ZNK7crpropa7Variant11getTypeInfoEv60
_ZN7crpropa7VariantC2Ev1147
_ZN7crpropa7VariantaSERKS0_1153
_ZN7crpropa7VariantC2ERKS0_2306
_ZN7crpropa7Variant4copyERKS0_3459
_ZN7crpropa7VariantD2Ev4610
_ZN7crpropa7Variant5clearENS0_4TypeE5785
_ZN7crpropa7Variant5checkENS0_4TypeE5793
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Variant.cpp.func.html b/doc/coverageReport/src/Variant.cpp.func.html deleted file mode 100644 index 878d842c0..000000000 --- a/doc/coverageReport/src/Variant.cpp.func.html +++ /dev/null @@ -1,264 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Variant.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Variant.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7151913.7 %
Date:2024-04-08 14:58:22Functions:184837.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa7Variant10fromStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS0_4TypeE2
_ZN7crpropa7Variant11getTypeNameENS0_4TypeE0
_ZN7crpropa7Variant12copyToBufferEPv1
_ZN7crpropa7Variant4copyERKS0_3459
_ZN7crpropa7Variant5checkENS0_4TypeE5793
_ZN7crpropa7Variant5clearENS0_4TypeE5785
_ZN7crpropa7Variant6resizeEm0
_ZN7crpropa7Variant6toTypeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa7VariantC2ENS0_4TypeE0
_ZN7crpropa7VariantC2EPKc3
_ZN7crpropa7VariantC2ERKS0_2306
_ZN7crpropa7VariantC2Ev1147
_ZN7crpropa7VariantD2Ev4610
_ZN7crpropa7VariantaSERKS0_1153
_ZN7crpropa7VariantcvRSt6vectorIS0_SaIS0_EEEv0
_ZN7crpropa7VariantixEm0
_ZN7crpropalsERSoRKNS_7VariantE0
_ZNK7crpropa7Variant10toVector3cEv0
_ZNK7crpropa7Variant10toVector3dEv0
_ZNK7crpropa7Variant10toVector3fEv0
_ZNK7crpropa7Variant11getTypeInfoEv60
_ZNK7crpropa7Variant11getTypeNameEv0
_ZNK7crpropa7Variant12toLongDoubleEv0
_ZNK7crpropa7Variant14toComplexFloatEv0
_ZNK7crpropa7Variant15toComplexDoubleEv0
_ZNK7crpropa7Variant4sizeEv0
_ZNK7crpropa7Variant5checkENS0_4TypeE2
_ZNK7crpropa7Variant6toBoolEv2
_ZNK7crpropa7Variant6toCharEv0
_ZNK7crpropa7Variant7getSizeEv0
_ZNK7crpropa7Variant7isValidEv8
_ZNK7crpropa7Variant7toFloatEv0
_ZNK7crpropa7Variant7toInt16Ev0
_ZNK7crpropa7Variant7toInt32Ev0
_ZNK7crpropa7Variant7toInt64Ev2
_ZNK7crpropa7Variant7toUCharEv0
_ZNK7crpropa7Variant8toDoubleEv6
_ZNK7crpropa7Variant8toStringERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE6
_ZNK7crpropa7Variant8toUInt16Ev0
_ZNK7crpropa7Variant8toUInt32Ev0
_ZNK7crpropa7Variant8toUInt64Ev0
_ZNK7crpropa7Variant8toVectorEv0
_ZNK7crpropa7Variant9getSizeOfEv0
_ZNK7crpropa7VariantcvRKSt6vectorIS0_SaIS0_EEEv0
_ZNK7crpropa7VarianteqERKS0_4
_ZNK7crpropa7VariantixEm0
_ZNK7crpropa7VariantneEPKc0
_ZNK7crpropa7VariantneERKS0_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/Variant.cpp.gcov.html b/doc/coverageReport/src/Variant.cpp.gcov.html deleted file mode 100644 index b1925926a..000000000 --- a/doc/coverageReport/src/Variant.cpp.gcov.html +++ /dev/null @@ -1,1200 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/Variant.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - Variant.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7151913.7 %
Date:2024-04-08 14:58:22Functions:184837.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : //-------------------------------------------------------------
-       2             : // Based on Variant.cc in the Physics eXtension Library (PXL) -
-       3             : // http://vispa.physik.rwth-aachen.de/                        -
-       4             : // Licensed under a LGPL-2 or later license                   -
-       5             : //-------------------------------------------------------------
-       6             : 
-       7             : #include "crpropa/Variant.h"
-       8             : 
-       9             : 
-      10             : namespace crpropa {
-      11             : 
-      12             : 
-      13        1147 : Variant::Variant() : type(TYPE_NONE) {
-      14        1147 : }
-      15             : 
-      16           0 : Variant::Variant(Type t) : type(TYPE_NONE) {
-      17           0 :         check(t);
-      18           0 : }
-      19             : 
-      20        2306 : Variant::Variant(const Variant& v) : type(TYPE_NONE) {
-      21        2306 :         copy(v);
-      22        2306 : }
-      23             : 
-      24           3 : Variant::Variant(const char* s) {
-      25           3 :         data._t_string = new std::string(s);
-      26           3 :         type = TYPE_STRING;
-      27           3 : }
-      28             : 
-      29        4610 : Variant::~Variant() {
-      30        4610 :         clear();
-      31        4610 : }
-      32             : 
-      33           0 : const char* Variant::getTypeName() const {
-      34           0 :         return getTypeName(type);
-      35             : }
-      36             : 
-      37           0 : const char* Variant::getTypeName(Type t) {
-      38             :         if (t == TYPE_NONE)
-      39             :                 return "none";
-      40             :         else if (t == TYPE_BOOL)
-      41           0 :                 return "bool";
-      42             :         else if (t == TYPE_CHAR)
-      43           0 :                 return "char";
-      44             :         else if (t == TYPE_UCHAR)
-      45           0 :                 return "uchar";
-      46             :         else if (t == TYPE_INT16)
-      47           0 :                 return "int16";
-      48             :         else if (t == TYPE_UINT16)
-      49           0 :                 return "uint16";
-      50             :         else if (t == TYPE_INT32)
-      51           0 :                 return "int32";
-      52             :         else if (t == TYPE_UINT32)
-      53           0 :                 return "uint32";
-      54             :         else if (t == TYPE_INT64)
-      55           0 :                 return "int64";
-      56             :         else if (t == TYPE_UINT64)
-      57           0 :                 return "uint64";
-      58             :         else if (t == TYPE_FLOAT)
-      59           0 :                 return "float";
-      60             :         else if (t == TYPE_DOUBLE)
-      61           0 :                 return "double";
-      62             :         else if (t == TYPE_LONGDOUBLE)
-      63           0 :                 return "ldouble";
-      64             :         else if (t == TYPE_COMPLEXF)
-      65           0 :                 return "complex_f";
-      66             :         else if (t == TYPE_COMPLEXD)
-      67           0 :                 return "complex_d";
-      68             :         else if (t == TYPE_STRING)
-      69           0 :                 return "string";
-      70             :         else if (t == TYPE_VECTOR3F)
-      71           0 :                 return "Vector3f";
-      72             :         else if (t == TYPE_VECTOR3D)
-      73           0 :                 return "Vector3d";
-      74             :         else if (t == TYPE_VECTOR3C)
-      75           0 :                 return "Vector3c";
-      76             :         else if (t == TYPE_VECTOR)
-      77           0 :                 return "vector";
-      78             :         else
-      79           0 :                 return "unknown";
-      80             : }
-      81             : 
-      82          60 : const std::type_info& Variant::getTypeInfo() const {
-      83          60 :         if (type == TYPE_BOOL) {
-      84             :                 const std::type_info& ti = typeid(data._t_bool);
-      85             :                 return ti;
-      86             :         } else if (type == TYPE_CHAR) {
-      87             :                 const std::type_info& ti = typeid(data._t_char);
-      88             :                 return ti;
-      89             :         } else if (type == TYPE_UCHAR) {
-      90             :                 const std::type_info& ti = typeid(data._t_uchar);
-      91           0 :                 return ti;
-      92             :         } else if (type == TYPE_INT16) {
-      93             :                 const std::type_info& ti = typeid(data._t_int16);
-      94           0 :                 return ti;
-      95             :         } else if (type == TYPE_UINT16) {
-      96             :                 const std::type_info& ti = typeid(data._t_uint16);
-      97           0 :                 return ti;
-      98             :         } else if (type == TYPE_INT32) {
-      99             :                 const std::type_info& ti = typeid(data._t_int32);
-     100          12 :                 return ti;
-     101             :         } else if (type == TYPE_UINT32) {
-     102             :                 const std::type_info& ti = typeid(data._t_uint32);
-     103           0 :                 return ti;
-     104             :         } else if (type == TYPE_INT64) {
-     105             :                 const std::type_info& ti = typeid(data._t_int64);
-     106           0 :                 return ti;
-     107             :         } else if (type == TYPE_UINT64) {
-     108             :                 const std::type_info& ti = typeid(data._t_uint64);
-     109           0 :                 return ti;
-     110             :         } else if (type == TYPE_FLOAT) {
-     111             :                 const std::type_info& ti = typeid(data._t_float);
-     112           0 :                 return ti;
-     113             :         } else if (type == TYPE_DOUBLE) {
-     114             :                 const std::type_info& ti = typeid(data._t_double);
-     115          22 :                 return ti;
-     116             :         } else if (type == TYPE_LONGDOUBLE)     {
-     117             :                 const std::type_info& ti = typeid(data._t_ldouble);
-     118           0 :                 return ti;
-     119             :         } else if (type == TYPE_STRING) {
-     120             :                 const std::type_info& ti = typeid(*data._t_string);
-     121          24 :                 return ti;
-     122             :         } else if (type == TYPE_COMPLEXF) { // pointer needed?
-     123             :                 const std::type_info& ti = typeid(*data._t_complex_f);
-     124           0 :                 return ti;
-     125             :         } else if (type == TYPE_COMPLEXD) {
-     126             :                 const std::type_info& ti = typeid(*data._t_complex_d);
-     127           0 :                 return ti;
-     128             :         } else if (type == TYPE_VECTOR3D) {
-     129             :                 const std::type_info& ti = typeid(data._t_vector3d);
-     130           0 :                 return ti;
-     131             :         } else if (type == TYPE_VECTOR3F) {
-     132             :                 const std::type_info& ti = typeid(data._t_vector3f);
-     133           0 :                 return ti;
-     134             :         } else if (type == TYPE_VECTOR) {
-     135             :                 const std::type_info& ti = typeid(*data._t_vector);
-     136           0 :                 return ti;
-     137             :         } else {
-     138             :                 const std::type_info& ti = typeid(0);
-     139           0 :                 return ti;
-     140             :         }
-     141             : }
-     142             : 
-     143           0 : Variant::Type Variant::toType(const std::string& name) {
-     144           0 :         if (name == "none")
-     145             :                 return TYPE_NONE;
-     146           0 :         else if (name == "bool")
-     147             :                 return TYPE_BOOL;
-     148           0 :         else if (name == "char") 
-     149             :                 return TYPE_CHAR;
-     150           0 :         else if (name == "uchar")
-     151             :                 return TYPE_UCHAR;
-     152           0 :         else if (name == "int16")
-     153             :                 return TYPE_INT16;
-     154           0 :         else if (name == "uint16")
-     155             :                 return TYPE_UINT16;
-     156           0 :         else if (name == "int32")
-     157             :                 return TYPE_INT32;
-     158           0 :         else if (name == "uint32")
-     159             :                 return TYPE_UINT32;
-     160           0 :         else if (name == "int64")
-     161             :                 return TYPE_INT64;
-     162           0 :         else if (name == "uint64")
-     163             :                 return TYPE_UINT64;
-     164           0 :         else if (name == "float")
-     165             :                 return TYPE_FLOAT;
-     166           0 :         else if (name == "double")
-     167             :                 return TYPE_DOUBLE;
-     168           0 :         else if (name == "long double")
-     169             :                 return TYPE_LONGDOUBLE;
-     170           0 :         else if (name == "complex_f")
-     171             :                 return TYPE_COMPLEXF;
-     172           0 :         else if (name == "complex_d")
-     173             :                 return TYPE_COMPLEXD;
-     174           0 :          else if (name == "string")
-     175             :                 return TYPE_STRING;
-     176           0 :         else if (name == "Vector3f")
-     177             :                 return TYPE_VECTOR3F;
-     178           0 :         else if (name == "Vector3d")
-     179             :                 return TYPE_VECTOR3D;
-     180           0 :         else if (name == "Vector3c")
-     181             :                 return TYPE_VECTOR3C;
-     182           0 :         else if (name == "vector")
-     183             :                 return TYPE_VECTOR;
-     184             :         else
-     185           0 :                 return TYPE_NONE;
-     186             : }
-     187             : 
-     188           2 : bool Variant::toBool() const {
-     189           2 :         switch (type) {
-     190           2 :                 case TYPE_BOOL:
-     191           2 :                         return data._t_bool;
-     192             :                         break;
-     193           0 :                 case TYPE_CHAR:
-     194           0 :                         return data._t_char != 0;
-     195             :                         break;
-     196           0 :                 case TYPE_UCHAR:
-     197           0 :                         return data._t_uchar != 0;
-     198             :                         break;
-     199           0 :                 case TYPE_INT16:
-     200           0 :                         return data._t_int16 != 0;
-     201             :                         break;
-     202           0 :                 case TYPE_UINT16:
-     203           0 :                         return data._t_uint16 != 0;
-     204             :                         break;
-     205           0 :                 case TYPE_INT32:
-     206           0 :                         return data._t_int32 != 0;
-     207             :                         break;
-     208           0 :                 case TYPE_UINT32:
-     209           0 :                         return data._t_uint32 != 0;
-     210             :                         break;
-     211           0 :                 case TYPE_INT64:
-     212           0 :                         return data._t_int64 != 0;
-     213             :                         break;
-     214           0 :                 case TYPE_UINT64:
-     215           0 :                         return data._t_uint64 != 0;
-     216             :                         break;
-     217           0 :                 case TYPE_STRING: {
-     218           0 :                                 std::string upperstr(*data._t_string);
-     219             :                                 std::transform(upperstr.begin(), upperstr.end(), upperstr.begin(), (int(*) (int)) toupper);
-     220           0 :                                 if (upperstr == "YES" || upperstr == "TRUE" || upperstr == "1")
-     221           0 :                                         return true;
-     222           0 :                                 else if (upperstr == "NO" || upperstr == "FALSE" || upperstr == "0")
-     223           0 :                                         return false;
-     224             :                                 else
-     225           0 :                                         throw bad_conversion(type, TYPE_BOOL);
-     226             :                         }
-     227             :                         break;
-     228           0 :                 case TYPE_COMPLEXF: {
-     229           0 :                                 if (data._t_complex_f->real() == 0 && data._t_complex_f->imag() == 0)
-     230           0 :                                         return true;
-     231             :                                 else
-     232             :                                         return false;
-     233             :                         }
-     234             :                         break;
-     235           0 :                 case TYPE_COMPLEXD: {
-     236           0 :                                 if (data._t_complex_d->real() == 0 && data._t_complex_d->imag() == 0)
-     237           0 :                                         return true;
-     238             :                                 else
-     239             :                                         return false;
-     240             :                         }
-     241             :                         break;
-     242           0 :                 case TYPE_VECTOR:
-     243           0 :                         return data._t_vector->size() != 0;
-     244             :                         break;
-     245           0 :                 case TYPE_FLOAT:
-     246             :                 case TYPE_DOUBLE:
-     247             :                 case TYPE_LONGDOUBLE:
-     248             :                 default:
-     249           0 :                         throw bad_conversion(type, TYPE_BOOL);
-     250             :                         break;
-     251             :         }
-     252             : 
-     253             :         return false;
-     254             : }
-     255             : 
-     256           0 : float Variant::toFloat() const {
-     257           0 :         switch (type) {
-     258           0 :                 case TYPE_BOOL:
-     259           0 :                         return data._t_bool ? (float) 1.0 : (float) 0.0; 
-     260             :                         break;
-     261           0 :                 case TYPE_CHAR:
-     262           0 :                         return static_cast<float>(data._t_char);
-     263             :                         break;
-     264           0 :                 case TYPE_UCHAR:
-     265           0 :                         return static_cast<float>(data._t_uchar);
-     266             :                         break;
-     267           0 :                 case TYPE_INT16:
-     268           0 :                         return static_cast<float>(data._t_int16);
-     269             :                         break;
-     270           0 :                 case TYPE_INT32:
-     271           0 :                         return static_cast<float>(data._t_int32);
-     272             :                         break;
-     273           0 :                 case TYPE_INT64:
-     274           0 :                         return static_cast<float>(data._t_int64);
-     275             :                         break;
-     276           0 :                 case TYPE_UINT16:
-     277           0 :                         return static_cast<float>(data._t_uint16);
-     278             :                         break;
-     279           0 :                 case TYPE_UINT32:
-     280           0 :                         return static_cast<float>(data._t_uint32);
-     281             :                         break;
-     282           0 :                 case TYPE_UINT64:
-     283           0 :                         return static_cast<float>(data._t_uint64);
-     284             :                         break;
-     285           0 :                 case TYPE_FLOAT:
-     286           0 :                         return static_cast<float>(data._t_float);
-     287             :                         break;
-     288           0 :                 case TYPE_DOUBLE:
-     289           0 :                         return static_cast<float>(data._t_double);
-     290             :                         break;
-     291           0 :                 case TYPE_LONGDOUBLE:
-     292           0 :                         return static_cast<float>(data._t_ldouble);
-     293             :                         break;
-     294           0 :                 case TYPE_STRING:
-     295           0 :                         return static_cast<float>(std::atof(data._t_string->c_str()));
-     296             :                         break;
-     297           0 :                 case TYPE_COMPLEXF: {
-     298           0 :                                 if (data._t_complex_f->imag() == 0)
-     299           0 :                                         return static_cast<float>(data._t_complex_f->real());
-     300             :                                 else
-     301           0 :                                         throw bad_conversion(type, TYPE_COMPLEXF);
-     302             :                         }
-     303             :                         break;
-     304           0 :                 case TYPE_COMPLEXD: {
-     305           0 :                                 if (data._t_complex_d->imag() == 0)
-     306           0 :                                         return static_cast<float>(data._t_complex_d->real());
-     307             :                                 else
-     308           0 :                                         throw bad_conversion(type, TYPE_COMPLEXD);
-     309             :                         }
-     310             :                         break;
-     311           0 :                 default:
-     312           0 :                         throw bad_conversion(type, TYPE_FLOAT);
-     313             :                         break;
-     314             :         }
-     315             : 
-     316             :         return 0.;
-     317             : }
-     318             : 
-     319           6 : double Variant::toDouble() const {
-     320           6 :         switch (type) {
-     321           0 :                 case TYPE_BOOL:
-     322           0 :                         return data._t_bool ? (double) 1.0 : (double) 0.0; 
-     323             :                         break;
-     324           0 :                 case TYPE_CHAR:
-     325           0 :                         return static_cast<double>(data._t_char);
-     326             :                         break;
-     327           0 :                 case TYPE_UCHAR:
-     328           0 :                         return static_cast<double>(data._t_uchar);
-     329             :                         break;
-     330           0 :                 case TYPE_INT16:
-     331           0 :                         return static_cast<double>(data._t_int16);
-     332             :                         break;
-     333           0 :                 case TYPE_INT32:
-     334           0 :                         return static_cast<double>(data._t_int32);
-     335             :                         break;
-     336           0 :                 case TYPE_INT64:
-     337           0 :                         return static_cast<double>(data._t_int64);
-     338             :                         break;
-     339           0 :                 case TYPE_UINT16:
-     340           0 :                         return static_cast<double>(data._t_uint16);
-     341             :                         break;
-     342           0 :                 case TYPE_UINT32:
-     343           0 :                         return static_cast<double>(data._t_uint32);
-     344             :                         break;
-     345           0 :                 case TYPE_UINT64:
-     346           0 :                         return static_cast<double>(data._t_uint64);
-     347             :                         break;
-     348           0 :                 case TYPE_FLOAT:
-     349           0 :                         return static_cast<double>(data._t_float);
-     350             :                         break;
-     351           6 :                 case TYPE_DOUBLE:
-     352           6 :                         return static_cast<double>(data._t_double);
-     353             :                         break;
-     354           0 :                 case TYPE_LONGDOUBLE:
-     355           0 :                         return static_cast<double>(data._t_ldouble);
-     356             :                         break;
-     357           0 :                 case TYPE_COMPLEXF: {
-     358           0 :                                 if (data._t_complex_f->imag() == 0)
-     359           0 :                                         return static_cast<double>(data._t_complex_f->real());
-     360             :                                 else
-     361           0 :                                         throw bad_conversion(type, TYPE_COMPLEXF);
-     362             :                         }
-     363             :                         break;
-     364           0 :                 case TYPE_COMPLEXD: {
-     365           0 :                                 if (data._t_complex_d->imag() == 0)
-     366           0 :                                         return static_cast<double>(data._t_complex_d->real());
-     367             :                                 else
-     368           0 :                                         throw bad_conversion(type, TYPE_COMPLEXD);
-     369             :                         }
-     370             :                         break;
-     371           0 :                 case TYPE_STRING:
-     372           0 :                         return static_cast<double>(std::atof(data._t_string->c_str()));
-     373             :                         break;
-     374           0 :                 default:
-     375           0 :                         throw bad_conversion(type, TYPE_DOUBLE);
-     376             :                         break;
-     377             :         }
-     378             : 
-     379             :         return 0.;
-     380             : }
-     381             : 
-     382           0 : long double Variant::toLongDouble() const {
-     383           0 :         switch (type) {
-     384           0 :                 case TYPE_BOOL:
-     385           0 :                         return data._t_bool ? (long double) 1.0 : (long double) 0.0; 
-     386             :                         break;
-     387           0 :                 case TYPE_CHAR:
-     388           0 :                         return static_cast<long double>(data._t_char);
-     389             :                         break;
-     390           0 :                 case TYPE_UCHAR:
-     391           0 :                         return static_cast<long double>(data._t_uchar);
-     392             :                         break;
-     393           0 :                 case TYPE_INT16:
-     394           0 :                         return static_cast<long double>(data._t_int16);
-     395             :                         break;
-     396           0 :                 case TYPE_INT32:
-     397           0 :                         return static_cast<long double>(data._t_int32);
-     398             :                         break;
-     399           0 :                 case TYPE_INT64:
-     400           0 :                         return static_cast<long double>(data._t_int64);
-     401             :                         break;
-     402           0 :                 case TYPE_UINT16:
-     403           0 :                         return static_cast<long double>(data._t_uint16);
-     404             :                         break;
-     405           0 :                 case TYPE_UINT32:
-     406           0 :                         return static_cast<long double>(data._t_uint32);
-     407             :                         break;
-     408           0 :                 case TYPE_UINT64:
-     409           0 :                         return static_cast<long double>(data._t_uint64);
-     410             :                         break;
-     411           0 :                 case TYPE_FLOAT:
-     412           0 :                         return static_cast<long double>(data._t_float);
-     413             :                         break;
-     414           0 :                 case TYPE_DOUBLE:
-     415           0 :                         return static_cast<long double>(data._t_double);
-     416             :                         break;
-     417           0 :                 case TYPE_LONGDOUBLE:
-     418           0 :                         return static_cast<long double>(data._t_ldouble);
-     419             :                         break;
-     420           0 :                 case TYPE_COMPLEXF: {
-     421           0 :                                 if (data._t_complex_f->imag() == 0)
-     422           0 :                                         return static_cast<long double>(data._t_complex_f->real());
-     423             :                                 else
-     424           0 :                                         throw bad_conversion(type, TYPE_COMPLEXF);
-     425             :                         }
-     426             :                         break;
-     427           0 :                 case TYPE_COMPLEXD: {
-     428           0 :                                 if (data._t_complex_d->imag() == 0)
-     429           0 :                                         return static_cast<long double>(data._t_complex_d->real());
-     430             :                                 else
-     431           0 :                                         throw bad_conversion(type, TYPE_COMPLEXD);
-     432             :                         }
-     433             :                         break;
-     434           0 :                 case TYPE_STRING:
-     435           0 :                         return static_cast<double>(std::atof(data._t_string->c_str()));
-     436             :                         break;
-     437           0 :                 default:
-     438           0 :                         throw bad_conversion(type, TYPE_LONGDOUBLE);
-     439             :                         break;
-     440             :         }
-     441             : 
-     442             :         return 0.;
-     443             : }
-     444             : 
-     445           0 : std::complex<float> Variant::toComplexFloat() const {
-     446           0 :         switch (type) {
-     447           0 :                 case TYPE_COMPLEXF:
-     448           0 :                         return static_cast<std::complex<float>>(*data._t_complex_f);
-     449             :                         break;
-     450           0 :                 case TYPE_COMPLEXD:
-     451           0 :                         return static_cast<std::complex<float>>(*data._t_complex_d);
-     452             :                         break;
-     453           0 :                 default:
-     454           0 :                         throw bad_conversion(type, TYPE_COMPLEXF);
-     455             :                         break;
-     456             :         }
-     457             : }  
-     458             : 
-     459           0 : std::complex<double> Variant::toComplexDouble() const {
-     460           0 :         switch (type) {
-     461           0 :                 case TYPE_COMPLEXF:
-     462           0 :                         return static_cast<std::complex<double>>(*data._t_complex_f);
-     463             :                         break;
-     464           0 :                 case TYPE_COMPLEXD:
-     465           0 :                         return static_cast<std::complex<double>>(*data._t_complex_d);
-     466             :                         break;
-     467           0 :                 default:
-     468           0 :                         throw bad_conversion(type, TYPE_COMPLEXD);
-     469             :                         break;
-     470             :         }
-     471             : }  
-     472             : 
-     473           0 : Vector3f Variant::toVector3f() const {
-     474           0 :         switch (type) {
-     475           0 :                 case TYPE_VECTOR3F:
-     476           0 :                         return static_cast<Vector3f>(*data._t_vector3f);
-     477             :                         break;
-     478           0 :                 case TYPE_VECTOR3D:
-     479           0 :                         return static_cast<Vector3f>(*data._t_vector3d);
-     480             :                         break;
-     481           0 :                 default:
-     482           0 :                         throw bad_conversion(type, TYPE_VECTOR3F);
-     483             :                         break;
-     484             :         }
-     485             : }
-     486             : 
-     487           0 : Vector3d Variant::toVector3d() const {
-     488           0 :         switch (type) {
-     489           0 :                 case TYPE_VECTOR3F:
-     490           0 :                         return static_cast<Vector3d>(*data._t_vector3f);
-     491             :                         break;
-     492           0 :                 case TYPE_VECTOR3D:
-     493           0 :                         return static_cast<Vector3d>(*data._t_vector3d);
-     494             :                         break;
-     495           0 :                 default:
-     496           0 :                         throw bad_conversion(type, TYPE_VECTOR3D);
-     497             :                         break;
-     498             :         }
-     499             : }
-     500             : 
-     501           0 : Vector3<std::complex<double>> Variant::toVector3c() const {
-     502           0 :         switch (type) {
-     503           0 :                 case TYPE_VECTOR3C:
-     504           0 :                         return static_cast<Vector3c>(*data._t_vector3c);
-     505             :                         break;
-     506           0 :                 default:
-     507           0 :                         throw bad_conversion(type, TYPE_VECTOR3C);
-     508             :                         break;
-     509             :         }
-     510             : }
-     511             : 
-     512           6 : std::string Variant::toString(const std::string& delimiter) const {
-     513           6 :         if (type == TYPE_STRING)
-     514           3 :                 return *data._t_string;
-     515             : 
-     516           3 :         std::stringstream ss;
-     517             : 
-     518           3 :         if (type == TYPE_BOOL) {
-     519           0 :                 ss << data._t_bool;
-     520             :         } else if (type == TYPE_CHAR) {
-     521           0 :                 ss << data._t_char;
-     522             :         } else if (type == TYPE_UCHAR) {
-     523           0 :                 ss << data._t_uchar;
-     524             :         } else if (type == TYPE_INT16) {
-     525           0 :                 ss << data._t_int16;
-     526             :         } else if (type == TYPE_UINT16) {
-     527           0 :                 ss << data._t_uint16;
-     528             :         } else if (type == TYPE_INT32) {
-     529           1 :                 ss << data._t_int32;
-     530             :         } else if (type == TYPE_UINT32) {
-     531           0 :                 ss << data._t_uint32;
-     532             :         } else if (type == TYPE_INT64) {
-     533           1 :                 ss << data._t_int64;
-     534             :         } else if (type == TYPE_UINT64) {
-     535           0 :                 ss << data._t_uint64;
-     536             :         } else if (type == TYPE_FLOAT) {
-     537           0 :                 ss << std::scientific << data._t_float;
-     538             :         } else if (type == TYPE_DOUBLE) {
-     539           1 :                 ss << std::scientific << data._t_double;
-     540             :         } else if (type == TYPE_LONGDOUBLE) {
-     541           0 :                 ss << std::scientific << data._t_ldouble;
-     542             :         } else if (type == TYPE_COMPLEXF) {
-     543           0 :                 ss << std::scientific << data._t_complex_f->real() << delimiter; 
-     544           0 :                 ss << std::scientific << data._t_complex_f->imag();
-     545             :         } else if (type == TYPE_COMPLEXD) {
-     546           0 :                 ss << std::scientific << data._t_complex_d->real() << delimiter; 
-     547           0 :                 ss << std::scientific << data._t_complex_d->imag();
-     548             :         } else if (type == TYPE_VECTOR3F) {
-     549           0 :                 ss << *data._t_vector3f;
-     550             :         } else if (type == TYPE_VECTOR3D) {
-     551           0 :                 ss << *data._t_vector3d;
-     552             :         } else if (type == TYPE_VECTOR) {
-     553           0 :                 ss << *data._t_vector;
-     554             :         }
-     555             : 
-     556             :         return ss.str();
-     557           3 : }
-     558             : 
-     559           0 : Variant::vector_t Variant::toVector() const {
-     560           0 :         if (type == TYPE_VECTOR)
-     561           0 :                 return *data._t_vector;
-     562             :         else
-     563           0 :                 throw bad_conversion(type, TYPE_VECTOR);
-     564             : }
-     565             : 
-     566           2 : Variant Variant::fromString(const std::string& s, Type t) {
-     567           2 :         std::stringstream ss(s);
-     568             : 
-     569             :         if (t == TYPE_BOOL) {
-     570             :                 std::string upperstr(s);
-     571             :                 std::transform(upperstr.begin(), upperstr.end(), upperstr.begin(), (int (*)(int)) toupper);
-     572           0 :                 if (upperstr == "YES" || upperstr == "TRUE" || upperstr == "1") 
-     573             :                         return Variant(true);
-     574           0 :                 else if (upperstr == "NO" || upperstr == "FALSE" || upperstr == "0")
-     575             :                         return Variant(false);
-     576           0 :                 throw bad_conversion(t, TYPE_BOOL);
-     577             :         } else if (t == TYPE_CHAR) {
-     578             :                 char c;
-     579           0 :                 ss >> c;
-     580             :                 return Variant(c);
-     581             :         } else if (t == TYPE_UCHAR) {
-     582             :                 unsigned char c;
-     583             :                 ss >> c;
-     584             :                 return Variant(c);
-     585             :         } else if (t == TYPE_INT16) {
-     586             :                 int16_t c;
-     587           0 :                 ss >> c;
-     588             :                 return Variant(c);
-     589             :         } else if (t == TYPE_INT32) {
-     590             :                 int32_t c;
-     591           1 :                 ss >> c;
-     592             :                 return Variant(c);
-     593             :         } else if (t == TYPE_INT64) {
-     594             :                 int64_t c;
-     595             :                 ss >> c;
-     596             :                 return Variant(c);
-     597             :         } else if (t == TYPE_UINT16) {
-     598             :                 uint16_t c;
-     599             :                 ss >> c;
-     600             :                 return Variant(c);
-     601             :         } else if (t == TYPE_UINT32) {
-     602             :                 uint32_t c;
-     603             :                 ss >> c;
-     604             :                 return Variant(c);
-     605             :         } else if (t == TYPE_UINT64) {
-     606             :                 uint64_t c;
-     607             :                 ss >> c;
-     608             :                 return Variant(c);
-     609             :         } else if (t == TYPE_FLOAT) {
-     610             :                 float c;
-     611             :                 ss >> c;
-     612             :                 return Variant(c);
-     613             :         } else if (t == TYPE_DOUBLE) {
-     614             :                 double c;
-     615             :                 ss >> c;
-     616             :                 return Variant(c);
-     617             :         } else if (t == TYPE_LONGDOUBLE) {
-     618             :                 long double c;
-     619             :                 ss >> c;
-     620             :                 return Variant(c);
-     621             :         } else if (t == TYPE_STRING) {
-     622           0 :                 return Variant(s);
-     623             :         } else if (t == TYPE_COMPLEXF) {
-     624             :                 float _vr, _vi;
-     625             :                 ss >> _vr >> _vi;
-     626           0 :                 complex_f v(_vr, _vi);
-     627             :                 return Variant(v);
-     628             :         } else if (t == TYPE_COMPLEXD) {
-     629             :                 double _vr, _vi;
-     630             :                 ss >> _vr >> _vi;
-     631           0 :                 complex_d v(_vr, _vi);
-     632             :                 return Variant(v);
-     633             :         } else if (t == TYPE_VECTOR3F) {
-     634             :                 Vector3f v;
-     635             :                 float _val;
-     636             :                 ss >> _val;
-     637           0 :                 v.setX(_val);
-     638             :                 ss >> _val;
-     639           0 :                 v.setY(_val);
-     640             :                 ss >> _val;
-     641           0 :                 v.setZ(_val);
-     642             :                 return Variant(v);
-     643             :         } else if (t == TYPE_VECTOR3D) {
-     644             :                 Vector3d v;
-     645             :                 double _val;
-     646             :                 ss >> _val;
-     647           0 :                 v.setX(_val);
-     648             :                 ss >> _val;
-     649           0 :                 v.setY(_val);
-     650             :                 ss >> _val;
-     651           0 :                 v.setZ(_val);
-     652             :                 return Variant(v);
-     653             :         } else if (t == TYPE_VECTOR3C) {
-     654             :                 Vector3c v;
-     655           0 :                 std::complex<double> _val;
-     656           0 :                 ss >> _val;
-     657             :                 v.setX(_val);
-     658           0 :                 ss >> _val;
-     659             :                 v.setY(_val);
-     660           0 :                 ss >> _val;
-     661             :                 v.setZ(_val);
-     662             :                 return Variant(v);
-     663             :         } else if (t == TYPE_VECTOR) {
-     664             :                 // std::regex useless("(|)|[|]| ");
-     665             :                 vector_t v;
-     666           0 :                 while (ss.good()) {
-     667             :                         std::string s;
-     668           0 :                         v.push_back(s);
-     669             :                 }
-     670           0 :         } else {
-     671             :                 std::string msg; 
-     672             :                 msg += "fromString not implemented for type ";
-     673           0 :         msg += getTypeName(t);
-     674           0 :         throw std::runtime_error("Variant: " + msg);
-     675             :         }
-     676           2 : }
-     677             : 
-     678        5785 : void Variant::clear(Type t) {
-     679             :         if (t == TYPE_STRING)
-     680           0 :                 safeDelete(data._t_string);
-     681             :         else if (t == TYPE_VECTOR3F)
-     682             :                 safeDelete(data._t_vector3f);
-     683             :         else if (t == TYPE_VECTOR3D)
-     684             :                 safeDelete(data._t_vector3d);
-     685             :         else if (t == TYPE_VECTOR3C)
-     686             :                 safeDelete(data._t_vector3c);
-     687             :         else if (t == TYPE_COMPLEXF)
-     688             :                 safeDelete(data._t_complex_f);
-     689             :         else if (t == TYPE_COMPLEXD)
-     690             :                 safeDelete(data._t_complex_d);
-     691             :         else if (t == TYPE_VECTOR)
-     692           0 :                 safeDelete(data._t_vector);
-     693             : 
-     694             :         // set the type to TYPE_NONE which will be used for checks
-     695        5785 :     type = TYPE_NONE;
-     696        5785 :     check(t);
-     697        5785 : }
-     698             : 
-     699        3459 : void Variant::copy(const Variant& v) {
-     700        3459 :         Type t = v.type;
-     701             : 
-     702        3459 :         if (t == TYPE_BOOL) 
-     703             :                 operator = (v.data._t_bool);
-     704             :         else if (t == TYPE_CHAR)
-     705             :                 operator = (v.data._t_char);
-     706             :         else if (t == TYPE_UCHAR)
-     707             :                 operator = (v.data._t_uchar);
-     708             :         else if (t == TYPE_INT16)
-     709             :                 operator = (v.data._t_int16);
-     710             :         else if (t == TYPE_UINT16)
-     711             :                 operator = (v.data._t_uint16);
-     712             :         else if (t == TYPE_INT32)
-     713             :                 operator = (v.data._t_int32);
-     714             :         else if (t == TYPE_UINT32)
-     715             :                 operator = (v.data._t_uint32);
-     716             :         else if (t == TYPE_INT64)
-     717             :                 operator = (v.data._t_int64);
-     718             :         else if (t == TYPE_UINT64)
-     719             :                 operator = (v.data._t_uint64);
-     720             :         else if (t == TYPE_FLOAT)
-     721             :                 operator = (v.data._t_float);
-     722             :         else if (t == TYPE_DOUBLE)
-     723             :                 operator = (v.data._t_double);
-     724             :         else if (t == TYPE_LONGDOUBLE)
-     725             :                 operator = (v.data._t_ldouble);
-     726             :         else if (t == TYPE_STRING)
-     727        1136 :                 operator = (*v.data._t_string);
-     728             :         else if (t == TYPE_COMPLEXF)
-     729           0 :                 operator = (*v.data._t_complex_f);
-     730             :         else if (t == TYPE_COMPLEXD)
-     731           0 :                 operator = (*v.data._t_complex_d);
-     732             :         else if (t == TYPE_VECTOR3F)
-     733           0 :                 operator = (*v.data._t_vector3f);
-     734             :         else if (t == TYPE_VECTOR3D)
-     735           0 :                 operator = (*v.data._t_vector3d);
-     736             :         else if (t == TYPE_VECTOR3C)
-     737           0 :                 operator = (*v.data._t_vector3c);
-     738             :         else if (t == TYPE_VECTOR)
-     739           0 :                 operator = (*v.data._t_vector);
-     740             :         else
-     741        2279 :                 type = TYPE_NONE;
-     742        3459 : }
-     743             : 
-     744           2 : void Variant::check(const Type t) const {
-     745           2 :         if (type != t) {
-     746           0 :                 throw bad_conversion(type, t);
-     747             :         }
-     748           2 : }
-     749             : 
-     750        5793 : void Variant::check(const Type t) {
-     751        5793 :         if (type == TYPE_NONE) {
-     752        5785 :                 memset(&data, 0, sizeof(data));
-     753        5785 :                 if (t == TYPE_VECTOR3F)
-     754           0 :                         data._t_vector3f = new Vector3f(); 
-     755             :                 else if (t == TYPE_VECTOR3D)
-     756           0 :                         data._t_vector3d = new Vector3d(); 
-     757             :                 else if (t == TYPE_VECTOR3C)
-     758           0 :                         data._t_vector3c = new Vector3c(); 
-     759             :                 else if (t == TYPE_COMPLEXF)
-     760           0 :                         data._t_complex_f = new complex_f(); 
-     761             :                 else if (t == TYPE_COMPLEXD)
-     762           0 :                         data._t_complex_d = new complex_d(); 
-     763             :                 else if (t == TYPE_STRING)
-     764           0 :                         data._t_string = new std::string();
-     765             :                 else if (t == TYPE_VECTOR)
-     766           0 :                         data._t_vector = new vector_t();
-     767             :                 else
-     768        5785 :                         type = t;
-     769           8 :         } else if (type != t)  {
-     770           0 :         throw bad_conversion(type, t);
-     771             :         }
-     772        5793 : }
-     773             : 
-     774           8 : bool Variant::isValid() const {
-     775           8 :         return (type != TYPE_NONE);
-     776             : }
-     777             : 
-     778           0 : size_t Variant::size() const {
-     779           0 :         if (type == TYPE_VECTOR) {
-     780           0 :                 return data._t_vector->size();
-     781             :         } else {
-     782             :                 std::string msg; 
-     783             :                 msg += "size() not implemented for type ";
-     784           0 :                 msg += getTypeName(type);
-     785           0 :                 throw std::runtime_error("Variant: " + msg);
-     786             :         }
-     787             : }
-     788             : 
-     789           0 : size_t Variant::getSizeOf() const {
-     790           0 :         switch (type) {
-     791             :                 case TYPE_BOOL:
-     792             :                         return sizeof(data._t_bool);
-     793             :                         break;
-     794             :                 case TYPE_CHAR:
-     795             :                         return sizeof(data._t_char);
-     796             :                         break;
-     797             :                 case TYPE_UCHAR:
-     798             :                         return sizeof(data._t_uchar);
-     799             :                         break;
-     800           0 :                 case TYPE_INT16:
-     801           0 :                         return sizeof(data._t_int16);
-     802             :                         break;
-     803           0 :                 case TYPE_UINT16:
-     804           0 :                         return sizeof(data._t_uint16);
-     805             :                         break;
-     806           0 :                 case TYPE_INT32:
-     807           0 :                         return sizeof(data._t_int32);
-     808             :                         break;
-     809           0 :                 case TYPE_UINT32:
-     810           0 :                         return sizeof(data._t_uint32);
-     811             :                         break;
-     812           0 :                 case TYPE_INT64:
-     813           0 :                         return sizeof(data._t_int64);
-     814             :                         break;
-     815           0 :                 case TYPE_UINT64:
-     816           0 :                         return sizeof(data._t_uint64);
-     817             :                         break;
-     818           0 :                 case TYPE_FLOAT:
-     819           0 :                         return sizeof(data._t_float);
-     820             :                         break;
-     821           0 :                 case TYPE_DOUBLE:
-     822           0 :                         return sizeof(data._t_double);
-     823             :                         break;
-     824           0 :                 case TYPE_LONGDOUBLE:
-     825           0 :                         return sizeof(data._t_ldouble);
-     826             :                         break;
-     827           0 :                 case TYPE_COMPLEXF:
-     828           0 :                         return sizeof(data._t_complex_f);
-     829             :                         break;
-     830           0 :                 case TYPE_COMPLEXD:
-     831           0 :                         return sizeof(data._t_complex_d);
-     832             :                         break;
-     833           0 :                 case TYPE_VECTOR3F:
-     834           0 :                         return sizeof(data._t_vector3f);
-     835             :                         break;
-     836           0 :                 case TYPE_VECTOR3D:
-     837           0 :                         return sizeof(data._t_vector3d);
-     838             :                         break;
-     839           0 :                 case TYPE_VECTOR3C:
-     840           0 :                         return sizeof(data._t_vector3c);
-     841             :                         break;
-     842           0 :                 case TYPE_STRING: {
-     843           0 :                                 size_t len = strlen(data._t_string->c_str() + 1);
-     844           0 :                                 return len;
-     845             :                         }
-     846             :                         break;
-     847           0 :                 case TYPE_NONE:
-     848           0 :                         return 0;
-     849             :                         break;
-     850           0 :                 default:
-     851           0 :                         throw std::runtime_error("Function getSize() cannot handle this type.");
-     852             :         }
-     853             : }
-     854             : 
-     855           0 : size_t Variant::getSize() const {
-     856           0 :         return getSizeOf();
-     857             : }
-     858             : 
-     859           0 : void Variant::resize(size_t i) {
-     860           0 :         check(TYPE_VECTOR);
-     861           0 :         return data._t_vector->resize(i);
-     862             : }
-     863             : 
-     864           1 : size_t Variant::copyToBuffer(void* buffer) {
-     865           1 :         if (type == TYPE_BOOL) {
-     866           0 :                 memcpy(buffer, &data._t_bool, sizeof(bool));
-     867           0 :                 return sizeof(data._t_bool);
-     868             :         } else if (type == TYPE_CHAR) {
-     869           0 :                 memcpy(buffer, &data._t_char, sizeof(char));
-     870           0 :                 return sizeof(data._t_char);
-     871             :         }  else if (type == TYPE_UCHAR) {
-     872           0 :                 memcpy(buffer, &data._t_uchar, sizeof(unsigned char));
-     873           0 :                 return sizeof(data._t_uchar);
-     874             :         } else if (type == TYPE_INT16) {
-     875           0 :                 memcpy(buffer, &data._t_int16, sizeof(int16_t));
-     876           0 :                 return sizeof(data._t_int16);
-     877             :         } else if (type == TYPE_UINT16) {
-     878           0 :                 memcpy(buffer, &data._t_uint16, sizeof(uint16_t));
-     879           0 :                 return sizeof(data._t_uint16);
-     880             :         } else if (type == TYPE_INT32) {
-     881           0 :                 memcpy(buffer, &data._t_int32, sizeof(int32_t));
-     882           0 :                 return sizeof(data._t_int32);
-     883             :         } else if (type == TYPE_UINT32) {
-     884           0 :                 memcpy(buffer, &data._t_uint32, sizeof(uint32_t));
-     885           0 :                 return sizeof(data._t_uint32);
-     886             :         } else if (type == TYPE_INT64) {
-     887           0 :                 memcpy(buffer, &data._t_int64, sizeof(int64_t));
-     888           0 :                 return sizeof(data._t_int64);
-     889             :         } else if (type == TYPE_UINT64) {
-     890           0 :                 memcpy(buffer, &data._t_uint64, sizeof(uint64_t));
-     891           0 :                 return sizeof(data._t_uint64);
-     892             :         } else if (type == TYPE_FLOAT) {
-     893           0 :                 memcpy(buffer, &data._t_float, sizeof(float));
-     894           0 :                 return sizeof(data._t_float);
-     895             :         } else if (type == TYPE_DOUBLE) {
-     896           1 :                 memcpy(buffer, &data._t_double, sizeof(double));
-     897           1 :                 return sizeof(data._t_double);
-     898             :         } else if (type == TYPE_LONGDOUBLE) {
-     899           0 :                 memcpy(buffer, &data._t_ldouble, sizeof(long double));
-     900           0 :                 return sizeof(data._t_ldouble);
-     901             :         }  else if (type == TYPE_STRING) {
-     902           0 :                 size_t len = data._t_string->size();
-     903             :                 memcpy(buffer, data._t_string->c_str(), len);
-     904           0 :                 return len;
-     905             :         } else if (type == TYPE_NONE) {
-     906             :                 return 0;
-     907             :         } else {
-     908           0 :                 throw std::runtime_error("This type cannot be handled by copyToBuffer().");
-     909             :         }
-     910             : }
-     911             : 
-     912        1153 : Variant& Variant::operator=(const Variant &v) {
-     913        1153 :         copy(v);
-     914        1153 :         return *this;
-     915             : }
-     916             : 
-     917           4 : bool Variant::operator==(const Variant& v) const {
-     918           4 :         if (type != v.type)
-     919             :                 return false;
-     920             : 
-     921             :         if (type == TYPE_BOOL) {
-     922           0 :                 return (data._t_bool == v.data._t_bool);
-     923             :         } else if (type == TYPE_CHAR) {
-     924           0 :                 return (data._t_char == v.data._t_char);
-     925             :         } else if (type == TYPE_UCHAR) {
-     926           0 :                 return (data._t_uchar == v.data._t_uchar);
-     927             :         } else if (type == TYPE_INT16) {
-     928           0 :                 return (data._t_int16 == v.data._t_int16);
-     929             :         } else if (type == TYPE_UINT16) {
-     930           0 :                 return (data._t_uint16 == v.data._t_uint16);
-     931             :         } else if (type == TYPE_INT32) {
-     932           0 :                 return (data._t_int32 == v.data._t_int32);
-     933             :         } else if (type == TYPE_UINT32) {
-     934           0 :                 return (data._t_uint32 == v.data._t_uint32);
-     935             :         } else if (type == TYPE_INT64) {
-     936           0 :                 return (data._t_int64 == v.data._t_int64);
-     937             :         } else if (type == TYPE_UINT64) {
-     938           0 :                 return (data._t_uint64 == v.data._t_uint64);
-     939             :         } else if (type == TYPE_FLOAT) {
-     940           0 :                 return (data._t_float == v.data._t_float);
-     941             :         } else if (type == TYPE_DOUBLE) {
-     942           4 :                 return (data._t_double == v.data._t_double);
-     943             :         } else if (type == TYPE_LONGDOUBLE) {
-     944           0 :                 return (data._t_ldouble == v.data._t_ldouble);
-     945             :         } else if (type == TYPE_STRING) {
-     946           0 :                 return (*data._t_string == *v.data._t_string);
-     947             :         } else if (type == TYPE_COMPLEXF) {
-     948           0 :                 return (*data._t_complex_f == *v.data._t_complex_f);
-     949             :         } else if (type == TYPE_COMPLEXD) {
-     950           0 :                 return (*data._t_complex_d == *v.data._t_complex_d);
-     951             :         } else if (type == TYPE_VECTOR3F) {
-     952           0 :                 return (*data._t_vector3f == *v.data._t_vector3f);
-     953             :         } else if (type == TYPE_VECTOR3D) {
-     954           0 :                 return (*data._t_vector3d == *v.data._t_vector3d);
-     955             :         } else if (type == TYPE_VECTOR3C) {
-     956           0 :                 return (*data._t_vector3c == *v.data._t_vector3c);
-     957             :         } else if (type == TYPE_VECTOR) {
-     958           0 :                 return (*data._t_vector == *v.data._t_vector);
-     959             :         } else {
-     960           0 :                 throw std::runtime_error("compare operator not implemented");
-     961             :         }
-     962             : }
-     963             : 
-     964           0 : bool Variant::operator!=(const Variant& v) const {
-     965           0 :         if (type != v.type)
-     966             :                 return true;
-     967             :         
-     968           0 :         if (*this == v)
-     969             :                 return false;
-     970             :         else
-     971           0 :                 return true;
-     972             : }
-     973             : 
-     974           0 : bool Variant::operator!=(const char* v) const {
-     975           0 :         check(TYPE_STRING);
-     976           0 :         return data._t_string->compare(v) != 0;
-     977             : }
-     978             : 
-     979           0 : Variant& Variant::operator[](size_t i) {
-     980           0 :         check(TYPE_VECTOR);
-     981           0 :         return (*data._t_vector)[i];
-     982             : }
-     983             : 
-     984           0 : const Variant& Variant::operator[](size_t i) const {
-     985           0 :         check(TYPE_VECTOR);
-     986           0 :         return (*data._t_vector)[i];
-     987             : }
-     988             : 
-     989           0 : Variant::operator std::vector<Variant>&() {
-     990           0 :         check(TYPE_VECTOR);
-     991           0 :         return *data._t_vector;
-     992             : }
-     993             : 
-     994           0 : Variant::operator const std::vector<Variant>&() const {
-     995           0 :         check(TYPE_VECTOR);
-     996           0 :         return *data._t_vector;
-     997             : }
-     998             : 
-     999             : 
-    1000             : 
-    1001             : #define INT_CASE(from_var, from_type, to_type, to)                                                                                                                         \
-    1002             :     case Variant::from_type: {                                                                                         \
-    1003             :                 if (data._t_##from_var <std::numeric_limits<to>::min() || data._t_##from_var> std::numeric_limits<to>::max())  \
-    1004             :                         throw bad_conversion(type, to_type);                                                                       \
-    1005             :                 else                                                                                                           \
-    1006             :                         return static_cast<to>(data._t_##from_var);                                                                \
-    1007             :                 }                                                                                                              \
-    1008             :         break;                                                                                                         \
-    1009             : 
-    1010             : #define INT_FUNCTION(to_type, fun, to)                                                                                 \
-    1011             :         to Variant::fun() const {                                                                                          \
-    1012             :                 switch (type) {                                                                                                \
-    1013             :                         case Variant::TYPE_BOOL:                                                                                   \
-    1014             :                                 return data._t_bool ? 1 : 0;                                                                           \
-    1015             :                                 break;                                                                                                 \
-    1016             :                                 INT_CASE(char, TYPE_CHAR, to_type, to)                                                                 \
-    1017             :                                 INT_CASE(uchar, TYPE_UCHAR, to_type, to)                                                               \
-    1018             :                                 INT_CASE(int16, TYPE_INT16, to_type, to)                                                               \
-    1019             :                                 INT_CASE(uint16, TYPE_UINT16, to_type, to)                                                             \
-    1020             :                                 INT_CASE(int32, TYPE_INT32, to_type, to)                                                               \
-    1021             :                                 INT_CASE(uint32, TYPE_UINT32, to_type, to)                                                             \
-    1022             :                                 INT_CASE(int64, TYPE_INT64, to_type, to)                                                               \
-    1023             :                                 INT_CASE(uint64, TYPE_UINT64, to_type, to)                                                             \
-    1024             :                                 INT_CASE(float, TYPE_FLOAT, to_type, to)                                                               \
-    1025             :                                 INT_CASE(double, TYPE_DOUBLE, to_type, to)                                                             \
-    1026             :                                 INT_CASE(ldouble, TYPE_LONGDOUBLE, to_type, to)                                                        \
-    1027             :                         case Variant::TYPE_STRING: {                                                                               \
-    1028             :                                 long l = atol(data._t_string->c_str());                                                                \
-    1029             :                                 if (l <std::numeric_limits<to>::min() || l > std::numeric_limits<to>::max())                           \
-    1030             :                                         throw bad_conversion(type, to_type);                                                               \
-    1031             :                                 else                                                                                                   \
-    1032             :                                         return l;                                                                                          \
-    1033             :                                 }                                                                                                      \
-    1034             :                                 break;                                                                                                 \
-    1035             :                         case Variant::TYPE_COMPLEXF:                                                                               \
-    1036             :                         case Variant::TYPE_COMPLEXD:                                                                               \
-    1037             :                         case Variant::TYPE_VECTOR3F:                                                                               \
-    1038             :                         case Variant::TYPE_VECTOR3D:                                                                               \
-    1039             :                         case Variant::TYPE_VECTOR3C:                                                                               \
-    1040             :                         case Variant::TYPE_VECTOR:                                                                                 \
-    1041             :                         case Variant::TYPE_NONE:                                                                                   \
-    1042             :                                 throw bad_conversion(type, to_type);                                                                   \
-    1043             :                                 break;                                                                                                 \
-    1044             :                 }                                                                                                              \
-    1045             :                 return 0;                                                                                                      \
-    1046             :         } 
-    1047             : 
-    1048           0 : INT_FUNCTION(TYPE_CHAR, toChar, char)
-    1049           0 : INT_FUNCTION(TYPE_UCHAR, toUChar, unsigned char)
-    1050           0 : INT_FUNCTION(TYPE_INT16, toInt16, int16_t)
-    1051           0 : INT_FUNCTION(TYPE_UINT16, toUInt16, uint16_t)
-    1052           0 : INT_FUNCTION(TYPE_INT32, toInt32, int32_t)
-    1053           0 : INT_FUNCTION(TYPE_UINT32, toUInt32, uint32_t)
-    1054           2 : INT_FUNCTION(TYPE_INT64, toInt64, int64_t)
-    1055           0 : INT_FUNCTION(TYPE_UINT64, toUInt64, uint64_t)
-    1056             : 
-    1057             : 
-    1058             : 
-    1059           0 : std::ostream& operator <<(std::ostream& os, const Variant& v) {
-    1060           0 :         switch (v.getType()) {
-    1061             :                 case Variant::TYPE_BOOL:
-    1062           0 :                         os << v.asBool();
-    1063             :                         break;
-    1064             :                 case Variant::TYPE_CHAR:
-    1065           0 :                         os << v.asChar();
-    1066           0 :                         break;
-    1067             :                 case Variant::TYPE_UCHAR:
-    1068           0 :                         os << v.asUChar();
-    1069             :                         break;
-    1070             :                 case Variant::TYPE_INT16:
-    1071           0 :                         os << v.asInt16();
-    1072           0 :                         break;
-    1073             :                 case Variant::TYPE_UINT16:
-    1074           0 :                         os << v.asUInt16();
-    1075             :                         break;
-    1076             :                 case Variant::TYPE_INT32:
-    1077           0 :                         os << v.asInt32();
-    1078           0 :                         break;
-    1079             :                 case Variant::TYPE_UINT32:
-    1080           0 :                         os << v.asUInt32();
-    1081             :                         break;
-    1082             :                 case Variant::TYPE_INT64:
-    1083           0 :                         os << v.asInt64();
-    1084             :                         break;
-    1085             :                 case Variant::TYPE_UINT64:
-    1086           0 :                         os << v.asUInt64();
-    1087             :                         break;
-    1088             :                 case Variant::TYPE_FLOAT:
-    1089           0 :                         os << v.asFloat();
-    1090             :                         break;
-    1091             :                 case Variant::TYPE_DOUBLE:
-    1092           0 :                         os << v.asDouble();
-    1093             :                         break;
-    1094             :                 case Variant::TYPE_LONGDOUBLE:
-    1095           0 :                         os << v.asLongDouble();
-    1096             :                         break;
-    1097             :                 case Variant::TYPE_COMPLEXF:
-    1098           0 :                         os << v.asComplexFloat();
-    1099           0 :                         break;
-    1100             :                 case Variant::TYPE_COMPLEXD:
-    1101           0 :                         os << v.asComplexDouble();
-    1102           0 :                         break;
-    1103             :                 case Variant::TYPE_STRING:
-    1104             :                         os << v.asString();
-    1105             :                         break;
-    1106             :                 case Variant::TYPE_VECTOR3F:
-    1107           0 :                         os << v.asVector3f();
-    1108           0 :                         break;
-    1109             :                 case Variant::TYPE_VECTOR3D:
-    1110           0 :                         os << v.asVector3d();
-    1111           0 :                         break;
-    1112             :                 case Variant::TYPE_VECTOR3C:
-    1113           0 :                         os << v.asVector3c();
-    1114           0 :                         break;
-    1115             :                 default:
-    1116             :                         break;
-    1117             :         }
-    1118             : 
-    1119           0 :         return os;
-    1120             : }
-    1121             : 
-    1122             : 
-    1123             : 
-    1124             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html b/doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html deleted file mode 100644 index 39a908092..000000000 --- a/doc/coverageReport/src/advectionField/AdvectionField.cpp.func-sort-c.html +++ /dev/null @@ -1,408 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/advectionField/AdvectionField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/advectionField - AdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ObliqueAdvectionShock13setShockwidthEd0
_ZN7crpropa21ObliqueAdvectionShock5setVyEd0
_ZN7crpropa21ObliqueAdvectionShock6setVupEd0
_ZN7crpropa21ObliqueAdvectionShock7setCompEd0
_ZN7crpropa21ObliqueAdvectionShockC2Edddd0
_ZN7crpropa28OneDimensionalCartesianShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalCartesianShock6setVupEd0
_ZN7crpropa28OneDimensionalCartesianShock7setCompEd0
_ZN7crpropa28OneDimensionalCartesianShockC2Eddd0
_ZN7crpropa28OneDimensionalSphericalShock10setCoolingEb0
_ZN7crpropa28OneDimensionalSphericalShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalSphericalShock14setShockRadiusEd0
_ZN7crpropa28OneDimensionalSphericalShock6setVupEd0
_ZN7crpropa28OneDimensionalSphericalShock7setCompEd0
_ZN7crpropa28OneDimensionalSphericalShockC2Eddddb0
_ZNK7crpropa21ObliqueAdvectionShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa21ObliqueAdvectionShock13getShockwidthEv0
_ZNK7crpropa21ObliqueAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObliqueAdvectionShock5getVyEv0
_ZNK7crpropa21ObliqueAdvectionShock6getVupEv0
_ZNK7crpropa21ObliqueAdvectionShock7getCompEv0
_ZNK7crpropa21ObliqueAdvectionShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa21UniformAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalCartesianShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalCartesianShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalCartesianShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalCartesianShock6getVupEv0
_ZNK7crpropa28OneDimensionalCartesianShock7getCompEv0
_ZNK7crpropa28OneDimensionalCartesianShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock10getCoolingEv0
_ZNK7crpropa28OneDimensionalSphericalShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalSphericalShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalSphericalShock14getShockRadiusEv0
_ZNK7crpropa28OneDimensionalSphericalShock6getVupEv0
_ZNK7crpropa28OneDimensionalSphericalShock7getCompEv0
_ZNK7crpropa28OneDimensionalSphericalShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa31ConstantSphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZN7crpropa23SphericalAdvectionField6setTauEd1
_ZN7crpropa23SphericalAdvectionField7setVMaxEd1
_ZN7crpropa23SphericalAdvectionField8setAlphaEd1
_ZN7crpropa23SphericalAdvectionField9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionField9setRadiusEd1
_ZN7crpropa23SphericalAdvectionFieldC2ENS_7Vector3IdEEdddd1
_ZN7crpropa23SphericalAdvectionShock5setR0Ed1
_ZN7crpropa23SphericalAdvectionShock5setV0Ed1
_ZN7crpropa23SphericalAdvectionShock9setLambdaEd1
_ZN7crpropa23SphericalAdvectionShock9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionShockC2ENS_7Vector3IdEEddd1
_ZNK7crpropa18AdvectionFieldList13getDivergenceERKNS_7Vector3IdEE1
_ZNK7crpropa18AdvectionFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa23SphericalAdvectionField6getTauEv1
_ZNK7crpropa23SphericalAdvectionField7getVMaxEv1
_ZNK7crpropa23SphericalAdvectionField8getAlphaEv1
_ZNK7crpropa23SphericalAdvectionField9getRadiusEv1
_ZNK7crpropa23SphericalAdvectionShock5getR0Ev1
_ZNK7crpropa23SphericalAdvectionShock5getV0Ev1
_ZNK7crpropa23SphericalAdvectionShock9getLambdaEv1
_ZNK7crpropa31ConstantSphericalAdvectionField8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa31ConstantSphericalAdvectionField8getVWindEv1
_ZN7crpropa23SphericalAdvectionShock17setAzimuthalSpeedEd2
_ZN7crpropa23SphericalAdvectionShock7setRRotEd2
_ZN7crpropa31ConstantSphericalAdvectionField8setVWindEd2
_ZN7crpropa31ConstantSphericalAdvectionField9setOriginENS_7Vector3IdEE2
_ZN7crpropa31ConstantSphericalAdvectionFieldC2ENS_7Vector3IdEEd2
_ZNK7crpropa23SphericalAdvectionField4getVERKd2
_ZNK7crpropa23SphericalAdvectionShock13getDivergenceERKNS_7Vector3IdEE2
_ZNK7crpropa23SphericalAdvectionShock17getAzimuthalSpeedEv2
_ZNK7crpropa23SphericalAdvectionShock7g_primeEd2
_ZNK7crpropa23SphericalAdvectionShock7getRRotEv2
_ZNK7crpropa31ConstantSphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE2
_ZN7crpropa18AdvectionFieldList8addFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZNK7crpropa23SphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField9getOriginEv3
_ZNK7crpropa23SphericalAdvectionShock8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionShock9getOriginEv3
_ZNK7crpropa31ConstantSphericalAdvectionField9getOriginEv3
_ZNK7crpropa21UniformAdvectionField13getDivergenceERKNS_7Vector3IdEE5
_ZNK7crpropa23SphericalAdvectionShock1gEd5
_ZN7crpropa21UniformAdvectionFieldC2ERKNS_7Vector3IdEE8
_ZNK7crpropa21UniformAdvectionField8getFieldERKNS_7Vector3IdEE120005
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html b/doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html deleted file mode 100644 index c7c1f546f..000000000 --- a/doc/coverageReport/src/advectionField/AdvectionField.cpp.func.html +++ /dev/null @@ -1,408 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/advectionField/AdvectionField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/advectionField - AdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18AdvectionFieldList8addFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZN7crpropa21ObliqueAdvectionShock13setShockwidthEd0
_ZN7crpropa21ObliqueAdvectionShock5setVyEd0
_ZN7crpropa21ObliqueAdvectionShock6setVupEd0
_ZN7crpropa21ObliqueAdvectionShock7setCompEd0
_ZN7crpropa21ObliqueAdvectionShockC2Edddd0
_ZN7crpropa21UniformAdvectionFieldC2ERKNS_7Vector3IdEE8
_ZN7crpropa23SphericalAdvectionField6setTauEd1
_ZN7crpropa23SphericalAdvectionField7setVMaxEd1
_ZN7crpropa23SphericalAdvectionField8setAlphaEd1
_ZN7crpropa23SphericalAdvectionField9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionField9setRadiusEd1
_ZN7crpropa23SphericalAdvectionFieldC2ENS_7Vector3IdEEdddd1
_ZN7crpropa23SphericalAdvectionShock17setAzimuthalSpeedEd2
_ZN7crpropa23SphericalAdvectionShock5setR0Ed1
_ZN7crpropa23SphericalAdvectionShock5setV0Ed1
_ZN7crpropa23SphericalAdvectionShock7setRRotEd2
_ZN7crpropa23SphericalAdvectionShock9setLambdaEd1
_ZN7crpropa23SphericalAdvectionShock9setOriginENS_7Vector3IdEE1
_ZN7crpropa23SphericalAdvectionShockC2ENS_7Vector3IdEEddd1
_ZN7crpropa28OneDimensionalCartesianShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalCartesianShock6setVupEd0
_ZN7crpropa28OneDimensionalCartesianShock7setCompEd0
_ZN7crpropa28OneDimensionalCartesianShockC2Eddd0
_ZN7crpropa28OneDimensionalSphericalShock10setCoolingEb0
_ZN7crpropa28OneDimensionalSphericalShock13setShockwidthEd0
_ZN7crpropa28OneDimensionalSphericalShock14setShockRadiusEd0
_ZN7crpropa28OneDimensionalSphericalShock6setVupEd0
_ZN7crpropa28OneDimensionalSphericalShock7setCompEd0
_ZN7crpropa28OneDimensionalSphericalShockC2Eddddb0
_ZN7crpropa31ConstantSphericalAdvectionField8setVWindEd2
_ZN7crpropa31ConstantSphericalAdvectionField9setOriginENS_7Vector3IdEE2
_ZN7crpropa31ConstantSphericalAdvectionFieldC2ENS_7Vector3IdEEd2
_ZNK7crpropa18AdvectionFieldList13getDivergenceERKNS_7Vector3IdEE1
_ZNK7crpropa18AdvectionFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa21ObliqueAdvectionShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa21ObliqueAdvectionShock13getShockwidthEv0
_ZNK7crpropa21ObliqueAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObliqueAdvectionShock5getVyEv0
_ZNK7crpropa21ObliqueAdvectionShock6getVupEv0
_ZNK7crpropa21ObliqueAdvectionShock7getCompEv0
_ZNK7crpropa21ObliqueAdvectionShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa21UniformAdvectionField13getDivergenceERKNS_7Vector3IdEE5
_ZNK7crpropa21UniformAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa21UniformAdvectionField8getFieldERKNS_7Vector3IdEE120005
_ZNK7crpropa23SphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionField4getVERKd2
_ZNK7crpropa23SphericalAdvectionField6getTauEv1
_ZNK7crpropa23SphericalAdvectionField7getVMaxEv1
_ZNK7crpropa23SphericalAdvectionField8getAlphaEv1
_ZNK7crpropa23SphericalAdvectionField8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionField9getOriginEv3
_ZNK7crpropa23SphericalAdvectionField9getRadiusEv1
_ZNK7crpropa23SphericalAdvectionShock13getDivergenceERKNS_7Vector3IdEE2
_ZNK7crpropa23SphericalAdvectionShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa23SphericalAdvectionShock17getAzimuthalSpeedEv2
_ZNK7crpropa23SphericalAdvectionShock1gEd5
_ZNK7crpropa23SphericalAdvectionShock5getR0Ev1
_ZNK7crpropa23SphericalAdvectionShock5getV0Ev1
_ZNK7crpropa23SphericalAdvectionShock7g_primeEd2
_ZNK7crpropa23SphericalAdvectionShock7getRRotEv2
_ZNK7crpropa23SphericalAdvectionShock8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa23SphericalAdvectionShock9getLambdaEv1
_ZNK7crpropa23SphericalAdvectionShock9getOriginEv3
_ZNK7crpropa28OneDimensionalCartesianShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalCartesianShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalCartesianShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalCartesianShock6getVupEv0
_ZNK7crpropa28OneDimensionalCartesianShock7getCompEv0
_ZNK7crpropa28OneDimensionalCartesianShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock10getCoolingEv0
_ZNK7crpropa28OneDimensionalSphericalShock13getDivergenceERKNS_7Vector3IdEE0
_ZNK7crpropa28OneDimensionalSphericalShock13getShockwidthEv0
_ZNK7crpropa28OneDimensionalSphericalShock14getDescriptionB5cxx11Ev0
_ZNK7crpropa28OneDimensionalSphericalShock14getShockRadiusEv0
_ZNK7crpropa28OneDimensionalSphericalShock6getVupEv0
_ZNK7crpropa28OneDimensionalSphericalShock7getCompEv0
_ZNK7crpropa28OneDimensionalSphericalShock8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa31ConstantSphericalAdvectionField13getDivergenceERKNS_7Vector3IdEE2
_ZNK7crpropa31ConstantSphericalAdvectionField14getDescriptionB5cxx11Ev0
_ZNK7crpropa31ConstantSphericalAdvectionField8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa31ConstantSphericalAdvectionField8getVWindEv1
_ZNK7crpropa31ConstantSphericalAdvectionField9getOriginEv3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html b/doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html deleted file mode 100644 index 69ab19d58..000000000 --- a/doc/coverageReport/src/advectionField/AdvectionField.cpp.gcov.html +++ /dev/null @@ -1,610 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/advectionField/AdvectionField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/advectionField - AdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/advectionField/AdvectionField.h"
-       2             : 
-       3             : 
-       4             : namespace crpropa {
-       5             : 
-       6             : 
-       7             : 
-       8           3 : void AdvectionFieldList::addField(ref_ptr<AdvectionField> field) {
-       9           3 :         fields.push_back(field);
-      10           3 : }
-      11             : 
-      12           1 : Vector3d AdvectionFieldList::getField(const Vector3d &position) const {
-      13             :         Vector3d b(0.);
-      14           4 :         for (int i = 0; i < fields.size(); i++)
-      15           3 :                 b += fields[i]->getField(position);
-      16           1 :         return b;
-      17             : }
-      18             : 
-      19           1 : double AdvectionFieldList::getDivergence(const Vector3d &position) const {
-      20             :         double D=0.;
-      21             :         // Work on default values for divergence or an error handling
-      22           4 :         for (int i = 0; i < fields.size(); i++)
-      23           3 :                 D += fields[i]->getDivergence(position);
-      24           1 :         return D;
-      25             : }
-      26             : 
-      27             : 
-      28             : //----------------------------------------------------------------
-      29           8 : UniformAdvectionField::UniformAdvectionField(const Vector3d &value) :
-      30           8 :                         value(value) {
-      31           8 :         }
-      32             : 
-      33      120005 : Vector3d UniformAdvectionField::getField(const Vector3d &position) const {
-      34      120005 :         return value;
-      35             :         }
-      36             : 
-      37           5 : double UniformAdvectionField::getDivergence(const Vector3d &position) const {
-      38           5 :         return 0.;
-      39             :         }
-      40             : 
-      41           0 : std::string UniformAdvectionField::getDescription() const {
-      42           0 :         std::stringstream s;
-      43           0 :         s << "v0: " << value / km * sec << " km/s, ";
-      44           0 :         return s.str();
-      45           0 : }
-      46             : 
-      47             : //----------------------------------------------------------------
-      48             : 
-      49           2 : ConstantSphericalAdvectionField::ConstantSphericalAdvectionField(const Vector3d origin, double vWind) {
-      50           2 :         setOrigin(origin);
-      51           2 :         setVWind(vWind);
-      52           2 : }
-      53             : 
-      54           1 : Vector3d ConstantSphericalAdvectionField::getField(const Vector3d &position) const {
-      55             :         Vector3d Pos = position-origin;
-      56           1 :         return vWind * Pos.getUnitVector();
-      57             : }
-      58             : 
-      59           2 : double ConstantSphericalAdvectionField::getDivergence(const Vector3d &position) const {
-      60             :         double R = (position-origin).getR();    
-      61           2 :         return 2*vWind/R;
-      62             : }
-      63             : 
-      64           2 : void ConstantSphericalAdvectionField::setOrigin(const Vector3d o) {
-      65             :         origin=o;
-      66           2 :         return;
-      67             : }
-      68             : 
-      69           2 : void ConstantSphericalAdvectionField::setVWind(double v) {
-      70           2 :         vWind = v;
-      71           2 :         return;
-      72             : }
-      73             : 
-      74           3 : Vector3d ConstantSphericalAdvectionField::getOrigin() const {
-      75           3 :         return origin;
-      76             : }
-      77             : 
-      78           1 : double ConstantSphericalAdvectionField::getVWind() const {
-      79           1 :         return vWind;
-      80             : }
-      81             : 
-      82           0 : std::string ConstantSphericalAdvectionField::getDescription() const {
-      83           0 :         std::stringstream s;
-      84           0 :         s << "Origin: " << origin / kpc  << " kpc, ";
-      85           0 :         s << "v0: " << vWind / km * sec << " km/s, ";
-      86           0 :         return s.str();
-      87           0 : }
-      88             : 
-      89             : 
-      90             : 
-      91             : //----------------------------------------------------------------
-      92             : 
-      93           1 : SphericalAdvectionField::SphericalAdvectionField(const Vector3d origin, double radius, double vMax, double tau, double alpha) {
-      94           1 :         setOrigin(origin);
-      95           1 :         setRadius(radius);
-      96           1 :         setVMax(vMax);
-      97           1 :         setTau(tau);
-      98           1 :         setAlpha(alpha);
-      99           1 : }
-     100             : 
-     101           3 : Vector3d SphericalAdvectionField::getField(const Vector3d &position) const {
-     102             :         Vector3d Pos = position-origin;
-     103           3 :         double R = Pos.getR();
-     104           3 :         if (R>radius) {
-     105             :                 return Vector3d(0.);
-     106             :         }
-     107           2 :         double v_R = getV(R);
-     108           2 :         return v_R * Pos.getUnitVector();
-     109             : }
-     110             : 
-     111           3 : double SphericalAdvectionField::getDivergence(const Vector3d &position) const {
-     112             :         double R = (position-origin).getR();
-     113           3 :         if (R>radius) {
-     114             :                 return 0.;
-     115             :         }
-     116           2 :         double D = 2*vMax/R * ( 1-( 1-alpha*(pow(R, alpha)/(2*tau)) )*exp(-( pow(R, alpha)/tau )) );
-     117           2 :         return D;
-     118             : }
-     119             : 
-     120           2 : double SphericalAdvectionField::getV(const double &r) const {
-     121           2 :         double f = vMax * (1-exp(-(pow(r, alpha)/tau)));
-     122           2 :         return f;
-     123             : }
-     124             : 
-     125           1 : void SphericalAdvectionField::setOrigin(const Vector3d o) {
-     126             :         origin = o;
-     127           1 :         return;
-     128             : }
-     129             : 
-     130           1 : void SphericalAdvectionField::setRadius(double r) {
-     131           1 :         radius = r;
-     132           1 :         return;
-     133             : }
-     134             : 
-     135           1 : void SphericalAdvectionField::setVMax(double v) {
-     136           1 :         vMax = v;
-     137           1 :         return;
-     138             : }
-     139             : 
-     140           1 : void SphericalAdvectionField::setTau(double t) {
-     141           1 :         tau = t;
-     142           1 :         return;
-     143             : }
-     144             : 
-     145           1 : void SphericalAdvectionField::setAlpha(double a) {
-     146           1 :         alpha = a;
-     147           1 :         return;
-     148             : }
-     149             : 
-     150           3 : Vector3d SphericalAdvectionField::getOrigin() const {
-     151           3 :         return origin;
-     152             : }
-     153             : 
-     154           1 : double SphericalAdvectionField::getRadius() const {
-     155           1 :         return radius;
-     156             : }
-     157             : 
-     158           1 : double SphericalAdvectionField::getVMax() const {
-     159           1 :         return vMax;
-     160             : }
-     161             : 
-     162           1 : double SphericalAdvectionField::getTau() const {
-     163           1 :         return tau;
-     164             : }
-     165             : 
-     166           1 : double SphericalAdvectionField::getAlpha() const {
-     167           1 :         return alpha;
-     168             : }
-     169             : 
-     170           0 : std::string SphericalAdvectionField::getDescription() const {
-     171           0 :         std::stringstream s;
-     172           0 :         s << "Origin: " << origin / kpc  << " kpc, ";
-     173           0 :         s << "Radius: " << radius / kpc  << " kpc, ";
-     174           0 :         s << "vMax: " << vMax / km * sec << " km/s, ";
-     175           0 :         s << "tau: " << tau << ", ";
-     176           0 :         s << "alpha: " << alpha << "\n";
-     177           0 :         return s.str();
-     178           0 : }
-     179             : 
-     180             : //----------------------------------------------------------------
-     181             : 
-     182           0 : OneDimensionalCartesianShock::OneDimensionalCartesianShock(double compressionRatio, double vUp, double lShock){
-     183           0 :         setComp(compressionRatio);
-     184           0 :         setVup(vUp);
-     185           0 :         setShockwidth(lShock);
-     186           0 :         }
-     187             : 
-     188           0 : Vector3d OneDimensionalCartesianShock::getField(const Vector3d &position) const {
-     189           0 :         double x = position.x;
-     190           0 :         double vDown = vUp / compressionRatio;
-     191             : 
-     192           0 :         double a = (vUp + vDown) * 0.5;
-     193           0 :         double b = (vUp - vDown) * 0.5;
-     194             : 
-     195             :         Vector3d v(0.);
-     196           0 :         v.x = a - b * tanh(x / lShock);
-     197           0 :         return v;
-     198             : 
-     199             : }
-     200             : 
-     201           0 : double OneDimensionalCartesianShock::getDivergence(const Vector3d &position) const {
-     202           0 :         double x = position.x;
-     203           0 :         double vDown = vUp / compressionRatio;
-     204             : 
-     205             :         double a = (vUp + vDown) * 0.5;
-     206           0 :         double b = (vUp - vDown) * 0.5;
-     207           0 :         return -b / lShock * (1 - tanh(x / lShock) * tanh(x / lShock));
-     208             : }
-     209             : 
-     210           0 : void OneDimensionalCartesianShock::setComp(double r) {
-     211           0 :         compressionRatio = r;
-     212           0 :         return;
-     213             : }
-     214             : 
-     215           0 : void OneDimensionalCartesianShock::setVup(double v) {
-     216           0 :         vUp = v;
-     217           0 :         return;
-     218             : }
-     219           0 : void OneDimensionalCartesianShock::setShockwidth(double w) {
-     220           0 :         lShock = w;
-     221           0 :         return;
-     222             : }
-     223             : 
-     224           0 : double OneDimensionalCartesianShock::getComp() const {
-     225           0 :         return compressionRatio;
-     226             : }
-     227             : 
-     228           0 : double OneDimensionalCartesianShock::getVup() const {
-     229           0 :         return vUp;
-     230             : }
-     231             : 
-     232           0 : double OneDimensionalCartesianShock::getShockwidth() const {
-     233           0 :         return lShock;
-     234             : }
-     235             : 
-     236           0 : std::string OneDimensionalCartesianShock::getDescription() const {
-     237           0 :         std::stringstream s;
-     238           0 :         s << "Shock width: " << lShock / km  << " km, ";
-     239           0 :         s << "Vup: " << vUp / km * sec << " km/s, ";
-     240           0 :         s << "Compression: " << compressionRatio;
-     241           0 :         return s.str();
-     242           0 : }
-     243             : 
-     244             : //----------------------------------------------------------------
-     245             : 
-     246           0 : OneDimensionalSphericalShock::OneDimensionalSphericalShock(double rShock, double vUp, double compressionRatio, double lShock, bool coolUpstream ){
-     247           0 :         setComp(compressionRatio);
-     248           0 :         setVup(vUp);
-     249           0 :         setShockwidth(lShock);
-     250           0 :         setShockRadius(rShock);
-     251           0 :         setCooling(coolUpstream);
-     252           0 :         }
-     253             : 
-     254           0 : Vector3d OneDimensionalSphericalShock::getField(const Vector3d &position) const {
-     255             :         double r = position.getR();
-     256           0 :         Vector3d e_r = position.getUnitVector();
-     257             : 
-     258           0 :         double vDown = vUp / compressionRatio;
-     259           0 :         double a = (vUp + vDown) * 0.5;
-     260           0 :         double b = (vUp - vDown) * 0.5;
-     261             : 
-     262             :         double v;
-     263           0 :         if (coolUpstream == true){
-     264             :         
-     265           0 :                 if (r <= rShock)
-     266           0 :                 v = a - b * tanh((r-rShock) / lShock);
-     267             :                 else
-     268           0 :                         v = (a - b * tanh((r-rShock) / lShock)) * (rShock / r) * (rShock / r);
-     269             : 
-     270             :         }
-     271             :         else
-     272           0 :                 v = (a - b * tanh((r-rShock) / lShock)) * (rShock / r) * (rShock / r);
-     273             : 
-     274           0 :         return v * e_r;
-     275             :         }
-     276             : 
-     277           0 : double OneDimensionalSphericalShock::getDivergence(const Vector3d &position) const {
-     278             :         double r = position.getR();
-     279             :         
-     280           0 :         double vDown = vUp / compressionRatio;
-     281           0 :         double a = (vUp + vDown) * 0.5;
-     282           0 :         double b = (vUp - vDown) * 0.5;
-     283             : 
-     284           0 :         double c = tanh((r-rShock) / lShock);
-     285             : 
-     286           0 :         if (coolUpstream == true){
-     287           0 :                 if (r <= rShock)
-     288           0 :                         return 2 * a / r - 2 * b / r * c - b / lShock * (1 - c * c);
-     289             :                 else
-     290           0 :                         return -(rShock / r) * (rShock / r) * b / lShock * (1 - c * c);
-     291             :         }
-     292             :         else 
-     293           0 :                 return -(rShock / r) * (rShock / r) *  b / lShock * (1 - c * c);
-     294             : 
-     295             : }
-     296             : 
-     297           0 : void OneDimensionalSphericalShock::setComp(double r) {
-     298           0 :         compressionRatio = r;
-     299           0 :         return;
-     300             : }
-     301             : 
-     302           0 : void OneDimensionalSphericalShock::setVup(double v) {
-     303           0 :         vUp = v;
-     304           0 :         return;
-     305             : }
-     306           0 : void OneDimensionalSphericalShock::setShockwidth(double w) {
-     307           0 :         lShock = w;
-     308           0 :         return;
-     309             : }
-     310             : 
-     311           0 : void OneDimensionalSphericalShock::setShockRadius(double r) {
-     312           0 :         rShock = r;
-     313           0 :         return;
-     314             : }
-     315             : 
-     316           0 : void OneDimensionalSphericalShock::setCooling(bool c) {
-     317           0 :         coolUpstream = c;
-     318           0 :         return;
-     319             : }
-     320             : 
-     321           0 : double OneDimensionalSphericalShock::getComp() const {
-     322           0 :         return compressionRatio;
-     323             : }
-     324             : 
-     325           0 : double OneDimensionalSphericalShock::getVup() const {
-     326           0 :         return vUp;
-     327             : }
-     328             : 
-     329           0 : double OneDimensionalSphericalShock::getShockwidth() const {
-     330           0 :         return lShock;
-     331             : }
-     332             : 
-     333           0 : double OneDimensionalSphericalShock::getShockRadius() const {
-     334           0 :         return rShock;
-     335             : }
-     336             : 
-     337           0 : bool OneDimensionalSphericalShock::getCooling() const {
-     338           0 :         return coolUpstream;
-     339             : }
-     340             : 
-     341           0 : std::string OneDimensionalSphericalShock::getDescription() const {
-     342           0 :         std::stringstream s;
-     343           0 :         s << "Shock width: " << lShock / km  << " km, ";
-     344           0 :         s << "Shock radius: " << rShock / km  << " km, ";
-     345           0 :         s << "Vup: " << vUp / km * sec << " km/s, ";
-     346           0 :         s << "Comp: " << compressionRatio;
-     347             : 
-     348           0 :         return s.str();
-     349           0 : }
-     350             : 
-     351             : //----------------------------------------------------------------
-     352             : 
-     353           0 : ObliqueAdvectionShock::ObliqueAdvectionShock(double compressionRatio, double vXUp, double vY, double lShock) {
-     354           0 :         setComp(compressionRatio);
-     355           0 :         setVup(vXUp);
-     356           0 :         setVy(vY);
-     357           0 :         setShockwidth(lShock);
-     358           0 :         }
-     359             : 
-     360           0 : Vector3d ObliqueAdvectionShock::getField(const Vector3d &position) const {
-     361           0 :         double x = position.x;
-     362           0 :         double vXDown = vXUp / compressionRatio;
-     363             : 
-     364           0 :         double a = (vXUp + vXDown) * 0.5;
-     365           0 :         double b = (vXUp - vXDown) * 0.5;
-     366             : 
-     367             :         Vector3d v(0.);
-     368           0 :         v.x = a - b * tanh(x / lShock);
-     369           0 :         v.y = vY;
-     370             : 
-     371           0 :         return v;
-     372             :         }
-     373             : 
-     374           0 : double ObliqueAdvectionShock::getDivergence(const Vector3d &position) const {
-     375           0 :         double x = position.x;
-     376           0 :         double vXDown = vXUp / compressionRatio;
-     377             :         // vy = const
-     378             : 
-     379             :         double a = (vXUp + vXDown) * 0.5;
-     380           0 :         double b = (vXUp - vXDown) * 0.5;
-     381             : 
-     382           0 :         return -b / lShock * (1 - tanh(x / lShock) * tanh(x / lShock));
-     383             :         }
-     384             : 
-     385           0 : void ObliqueAdvectionShock::setComp(double r) {
-     386           0 :         compressionRatio = r;
-     387           0 :         return;
-     388             : }
-     389             : 
-     390           0 : void ObliqueAdvectionShock::setVup(double v) {
-     391           0 :         vXUp = v;
-     392           0 :         return;
-     393             : } 
-     394             : 
-     395           0 : void ObliqueAdvectionShock::setVy(double v) {
-     396           0 :         vY = v;
-     397           0 :         return;
-     398             : } 
-     399           0 : void ObliqueAdvectionShock::setShockwidth(double w) {
-     400           0 :         lShock = w;
-     401           0 :         return;
-     402             : }
-     403             : 
-     404           0 : double ObliqueAdvectionShock::getComp() const {
-     405           0 :         return compressionRatio;
-     406             : }
-     407             : 
-     408           0 : double ObliqueAdvectionShock::getVup() const {
-     409           0 :         return vXUp;
-     410             : }
-     411             : 
-     412           0 : double ObliqueAdvectionShock::getVy() const {
-     413           0 :         return vY;
-     414             : }
-     415             : 
-     416           0 : double ObliqueAdvectionShock::getShockwidth() const {
-     417           0 :         return lShock;
-     418             : }
-     419             : 
-     420           0 : std::string ObliqueAdvectionShock::getDescription() const {
-     421           0 :         std::stringstream s;
-     422           0 :         s << "Shock width: " << lShock / km  << " km, ";
-     423           0 :         s << "Vx_up: " << vXUp / km * sec << " km/s, ";
-     424           0 :         s << "Vy: " << vY / km * sec << " km/s, ";
-     425           0 :         s << "Comp: " << compressionRatio;
-     426             :         
-     427           0 :         return s.str();
-     428           0 : }
-     429             : 
-     430             : //-----------------------------------------------------------------
-     431             : 
-     432           1 : SphericalAdvectionShock::SphericalAdvectionShock(const Vector3d origin, double r_0, double v_0, double l) {
-     433           1 :         setOrigin(origin);
-     434           1 :         setR0(r_0);
-     435           1 :         setV0(v_0);
-     436           1 :         setLambda(l);
-     437           1 :         setRRot(r_0);
-     438           1 :         setAzimuthalSpeed(0.);
-     439           1 : }
-     440             : 
-     441             : 
-     442           3 : Vector3d SphericalAdvectionShock::getField(const Vector3d &pos) const {
-     443             :         Vector3d R = pos-origin;
-     444           3 :         Vector3d e_r = R.getUnitVector();
-     445           3 :         Vector3d e_phi = R.getUnitVectorPhi();
-     446             :         double r = R.getR();
-     447             : 
-     448           3 :         double v_r = v_0 * ( 1 + (pow(r_0/(2*r), 2.) -1 ) * g(r));
-     449           3 :         double v_p = v_phi * (r_rot/r); 
-     450             : 
-     451           3 :         return v_r * e_r + v_p * e_phi;
-     452             : }
-     453             : 
-     454             : 
-     455           2 : double SphericalAdvectionShock::getDivergence(const Vector3d &pos) const {
-     456             :         double r = (pos-origin).getR();
-     457             : 
-     458           2 :         double d1 = 2./r*(1-g(r));
-     459           2 :         double d2 = (pow(r_0/(2*r), 2.)-1)*g_prime(r);
-     460             : 
-     461           2 :         return v_0 * (d1+d2);
-     462             : }
-     463             : 
-     464             : 
-     465           5 : double SphericalAdvectionShock::g(double r) const {
-     466           5 :         double a = (r-r_0)/lambda;
-     467           5 :         return 1. / (1+exp(-a));
-     468             : }
-     469             : 
-     470           2 : double SphericalAdvectionShock::g_prime(double r) const {
-     471           2 :         double a = (r-r_0)/lambda;
-     472           2 :         return 1. / (2*lambda*(1+cosh(-a)));
-     473             : }       
-     474             : 
-     475           1 : void SphericalAdvectionShock::setOrigin(const Vector3d o) {
-     476             :         origin = o;
-     477           1 : }
-     478             : 
-     479           1 : void SphericalAdvectionShock::setR0(double r) {
-     480           1 :         r_0 = r;
-     481           1 : }
-     482             : 
-     483           1 : void SphericalAdvectionShock::setV0(double v) {
-     484           1 :         v_0 = v;
-     485           1 : }
-     486             : 
-     487           1 : void SphericalAdvectionShock::setLambda(double l) {
-     488           1 :         lambda = l;
-     489           1 : }
-     490             : 
-     491           2 : void SphericalAdvectionShock::setRRot(double r) {
-     492           2 :         r_rot = r;
-     493           2 : }
-     494             : 
-     495           2 : void SphericalAdvectionShock::setAzimuthalSpeed(double v) {
-     496           2 :         v_phi = v;
-     497           2 : }
-     498             : 
-     499           3 : Vector3d SphericalAdvectionShock::getOrigin() const {
-     500           3 :         return origin;
-     501             : }
-     502             : 
-     503           1 : double SphericalAdvectionShock::getR0() const {
-     504           1 :         return r_0;
-     505             : }
-     506             : 
-     507           1 : double SphericalAdvectionShock::getV0() const {
-     508           1 :         return v_0;
-     509             : }
-     510             : 
-     511           1 : double SphericalAdvectionShock::getLambda() const {
-     512           1 :         return lambda;
-     513             : }
-     514             : 
-     515           2 : double SphericalAdvectionShock::getRRot() const {
-     516           2 :         return r_rot;
-     517             : }
-     518             : 
-     519           2 : double SphericalAdvectionShock::getAzimuthalSpeed() const {
-     520           2 :         return v_phi;
-     521             : }
-     522             : 
-     523           0 : std::string SphericalAdvectionShock::getDescription() const {
-     524           0 :         std::stringstream s;
-     525           0 :         s << "Origin: " << origin / kpc  << " kpc, ";
-     526           0 :         s << "r0 (shock radius): " << r_0 / kpc  << " kpc, ";
-     527           0 :         s << "r_rot (norm. azimuthal velocity): " << r_rot / kpc  << " kpc, ";
-     528           0 :         s << "v0 (maximum radial speed): " << v_0 / km * sec << " km/s, ";
-     529           0 :         s << "v_phi (azimuthal speed @ r_rot): " << v_phi / km * sec << " km/s, ";
-     530           0 :         s << "lambda: " << lambda / pc << " pc";
-     531           0 :         return s.str();
-     532           0 : }
-     533             : 
-     534             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/advectionField/index-sort-f.html b/doc/coverageReport/src/advectionField/index-sort-f.html deleted file mode 100644 index 54baddead..000000000 --- a/doc/coverageReport/src/advectionField/index-sort-f.html +++ /dev/null @@ -1,93 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/advectionField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.cpp -
42.5%42.5%
-
42.5 %131 / 30852.4 %44 / 84
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/advectionField/index-sort-l.html b/doc/coverageReport/src/advectionField/index-sort-l.html deleted file mode 100644 index 5eed79af6..000000000 --- a/doc/coverageReport/src/advectionField/index-sort-l.html +++ /dev/null @@ -1,93 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/advectionField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.cpp -
42.5%42.5%
-
42.5 %131 / 30852.4 %44 / 84
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/advectionField/index.html b/doc/coverageReport/src/advectionField/index.html deleted file mode 100644 index c4f7d0da9..000000000 --- a/doc/coverageReport/src/advectionField/index.html +++ /dev/null @@ -1,93 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/advectionField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/advectionFieldHitTotalCoverage
Test:coverage.info.cleanedLines:13130842.5 %
Date:2024-04-08 14:58:22Functions:448452.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
AdvectionField.cpp -
42.5%42.5%
-
42.5 %131 / 30852.4 %44 / 84
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/base64.cpp.func-sort-c.html b/doc/coverageReport/src/base64.cpp.func-sort-c.html deleted file mode 100644 index 6dfadfd29..000000000 --- a/doc/coverageReport/src/base64.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/base64.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - base64.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:454991.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Base646encodeB5cxx11EPKhm99
_ZN7crpropa6Base646decodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE100
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/base64.cpp.func.html b/doc/coverageReport/src/base64.cpp.func.html deleted file mode 100644 index d68b507b6..000000000 --- a/doc/coverageReport/src/base64.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/base64.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - base64.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:454991.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Base646decodeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE100
_ZN7crpropa6Base646encodeB5cxx11EPKhm99
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/base64.cpp.gcov.html b/doc/coverageReport/src/base64.cpp.gcov.html deleted file mode 100644 index 3e0cc494c..000000000 --- a/doc/coverageReport/src/base64.cpp.gcov.html +++ /dev/null @@ -1,205 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/base64.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src - base64.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:454991.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : // base64 encodig and decoding.
-       2             : //
-       3             : // Based on the implementations by
-       4             : // Jouni Malinen <j@w1.fi> and contributors from wpa_supplicant and hostapd in
-       5             : // http://web.mit.edu/freebsd/head/contrib/wpa/ and
-       6             : // http://web.mit.edu/freebsd/head/contrib/wpa/src/utils/base64.c and
-       7             : // http://web.mit.edu/freebsd/head/contrib/wpa/src/utils/base64.h
-       8             : //
-       9             : // Published under a 3-clause BSD license
-      10             : //
-      11             : 
-      12             : #include <string>
-      13             : #include <cstring>
-      14             : #include <stdexcept>
-      15             : 
-      16             : #include "crpropa/base64.h"
-      17             : 
-      18             : namespace crpropa
-      19             : {
-      20             : 
-      21             : //Alphabet used
-      22             : static const unsigned char encode_alphabet[65] =
-      23             : "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
-      24             : static int decode_alphabet[256] = {-1};
-      25             : 
-      26             : /// Encodes data
-      27          99 : std::string Base64::encode(const unsigned char *src, size_t len)
-      28             : {
-      29          99 :                 size_t olen = 4*((len + 2) / 3); /* 3-byte blocks to 4-byte */
-      30             : 
-      31          99 :                 if (olen < len)
-      32           0 :                         throw std::runtime_error("Integer overflow in Base64::encoding, data to large!");
-      33             : 
-      34             :                 std::string outStr;
-      35             :                 outStr.resize(olen);
-      36             : 
-      37             :                 unsigned char *out = (unsigned char*) outStr.c_str();
-      38             :                 unsigned char *pos = out;
-      39             :                 const unsigned char *end, *in;
-      40             : 
-      41          99 :                 end = src + len;
-      42             :                 in = src;
-      43        6666 :                 while (end - in >= 3) {
-      44        6567 :                                 *pos++ = encode_alphabet[in[0] >> 2];
-      45        6567 :                                 *pos++ = encode_alphabet[((in[0] & 0x03) << 4) | (in[1] >> 4)];
-      46        6567 :                                 *pos++ = encode_alphabet[((in[1] & 0x0f) << 2) | (in[2] >> 6)];
-      47        6567 :                                 *pos++ = encode_alphabet[in[2] & 0x3f];
-      48        6567 :                                 in += 3;
-      49             :                 }
-      50             : 
-      51          99 :                 if (end - in) {
-      52          66 :                                 *pos++ = encode_alphabet[in[0] >> 2];
-      53          66 :                                 if (end - in == 1) {
-      54          33 :                                                 *pos++ = encode_alphabet[(in[0] & 0x03) << 4];
-      55          33 :                                                 *pos++ = '=';
-      56             :                                 }
-      57             :                                 else {
-      58          33 :                                                 *pos++ = encode_alphabet[((in[0] & 0x03) << 4) |
-      59          33 :                                                                 (in[1] >> 4)];
-      60          33 :                                                 *pos++ = encode_alphabet[(in[1] & 0x0f) << 2];
-      61             :                                 }
-      62          66 :                                 *pos++ = '=';
-      63             :                 }
-      64             : 
-      65          99 :                 return outStr;
-      66             : }
-      67             : 
-      68             : 
-      69         100 : std::string Base64::decode(const std::string &data)
-      70             : {
-      71             : const unsigned char *src = (unsigned char*) data.c_str();
-      72             : size_t len = data.size();
-      73             : 
-      74         100 : if (decode_alphabet[0] == -1)
-      75             : { // build decode alphabet
-      76             :         std::memset(decode_alphabet, 0x80, 256);
-      77          65 :         for (size_t i = 0; i < sizeof(encode_alphabet) - 1; i++)
-      78          64 :                 decode_alphabet[encode_alphabet[i]] = (unsigned char) i;
-      79           1 :         decode_alphabet['='] = 0;
-      80             : }
-      81             : 
-      82             : size_t olen = 0;
-      83       26656 : for (size_t i = 0; i < len; i++) {
-      84       26556 :         if (decode_alphabet[src[i]] != 0x80)
-      85       26556 :                 olen++;
-      86             : }
-      87             : 
-      88         100 : if (olen == 0 || olen % 4)
-      89           0 :                         throw std::runtime_error("Base64 decode, invalid input size");
-      90             : 
-      91         100 : olen = olen / 4 * 3;
-      92             : std::string str;
-      93             : str.resize(olen);
-      94             : 
-      95             : unsigned char *out = (unsigned char*) str.c_str();
-      96             : unsigned char *pos = out;
-      97             : 
-      98             : size_t count = 0;
-      99             : int pad = 0;
-     100             : unsigned char block[4];
-     101       26589 : for (size_t i = 0; i < len; i++) {
-     102       26556 :         unsigned char tmp = decode_alphabet[src[i]];
-     103       26556 :         if (tmp == 0x80)
-     104           0 :                 continue;
-     105             : 
-     106       26556 :         if (src[i] == '=')
-     107         101 :                 pad++;
-     108       26556 :         block[count] = tmp;
-     109       26556 :         count++;
-     110       26556 :         if (count == 4) {
-     111        6639 :                 *pos++ = (block[0] << 2) | (block[1] >> 4);
-     112        6639 :                 *pos++ = (block[1] << 4) | (block[2] >> 2);
-     113        6639 :                 *pos++ = (block[2] << 6) | block[3];
-     114             :                 count = 0;
-     115        6639 :                 if (pad) {
-     116          67 :                         if (pad == 1)
-     117             :                                 pos--;
-     118          34 :                         else if (pad == 2)
-     119             :                                 pos -= 2;
-     120             :                         else {
-     121           0 :                                 throw std::runtime_error("Base64 decode, invalid padding");
-     122             :                         }
-     123             :                         break;
-     124             :                 }
-     125             :         }
-     126             : }
-     127         100 : return str;
-     128             : }
-     129             : };
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/index-sort-f.html b/doc/coverageReport/src/index-sort-f.html deleted file mode 100644 index b4c3a6afb..000000000 --- a/doc/coverageReport/src/index-sort-f.html +++ /dev/null @@ -1,253 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - srcHitTotalCoverage
Test:coverage.info.cleanedLines:1361270750.3 %
Date:2024-04-08 14:58:22Functions:25142958.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Clock.cpp -
0.0%
-
0.0 %0 / 270.0 %0 / 8
GridTools.cpp -
27.3%27.3%
-
27.3 %67 / 24536.8 %7 / 19
Variant.cpp -
13.7%13.7%
-
13.7 %71 / 51937.5 %18 / 48
Cosmology.cpp -
47.8%47.8%
-
47.8 %44 / 9240.0 %6 / 15
Geometry.cpp -
36.0%36.0%
-
36.0 %18 / 5046.2 %6 / 13
EmissionMap.cpp -
53.2%53.2%
-
53.2 %83 / 15654.5 %18 / 33
Source.cpp -
58.5%58.5%
-
58.5 %459 / 78455.5 %81 / 146
Random.cpp -
57.7%57.7%
-
57.7 %139 / 24156.5 %26 / 46
Module.cpp -
77.1%77.1%
-
77.1 %37 / 4875.0 %9 / 12
ParticleID.cpp -
53.3%53.3%
-
53.3 %16 / 3080.0 %4 / 5
ProgressBar.cpp -
78.0%78.0%
-
78.0 %39 / 5080.0 %4 / 5
PhotonBackground.cpp -
73.3%73.3%
-
73.3 %88 / 12080.0 %12 / 15
Common.cpp -
77.4%77.4%
-
77.4 %48 / 6283.3 %5 / 6
ParticleState.cpp -
85.7%85.7%
-
85.7 %48 / 5694.1 %16 / 17
Candidate.cpp -
87.8%87.8%
-
87.8 %129 / 14794.3 %33 / 35
base64.cpp -
91.8%91.8%
-
91.8 %45 / 49100.0 %2 / 2
ParticleMass.cpp -
96.8%96.8%
-
96.8 %30 / 31100.0 %4 / 4
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/index-sort-l.html b/doc/coverageReport/src/index-sort-l.html deleted file mode 100644 index f65520a55..000000000 --- a/doc/coverageReport/src/index-sort-l.html +++ /dev/null @@ -1,253 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - srcHitTotalCoverage
Test:coverage.info.cleanedLines:1361270750.3 %
Date:2024-04-08 14:58:22Functions:25142958.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Clock.cpp -
0.0%
-
0.0 %0 / 270.0 %0 / 8
Variant.cpp -
13.7%13.7%
-
13.7 %71 / 51937.5 %18 / 48
GridTools.cpp -
27.3%27.3%
-
27.3 %67 / 24536.8 %7 / 19
Geometry.cpp -
36.0%36.0%
-
36.0 %18 / 5046.2 %6 / 13
Cosmology.cpp -
47.8%47.8%
-
47.8 %44 / 9240.0 %6 / 15
EmissionMap.cpp -
53.2%53.2%
-
53.2 %83 / 15654.5 %18 / 33
ParticleID.cpp -
53.3%53.3%
-
53.3 %16 / 3080.0 %4 / 5
Random.cpp -
57.7%57.7%
-
57.7 %139 / 24156.5 %26 / 46
Source.cpp -
58.5%58.5%
-
58.5 %459 / 78455.5 %81 / 146
PhotonBackground.cpp -
73.3%73.3%
-
73.3 %88 / 12080.0 %12 / 15
Module.cpp -
77.1%77.1%
-
77.1 %37 / 4875.0 %9 / 12
Common.cpp -
77.4%77.4%
-
77.4 %48 / 6283.3 %5 / 6
ProgressBar.cpp -
78.0%78.0%
-
78.0 %39 / 5080.0 %4 / 5
ParticleState.cpp -
85.7%85.7%
-
85.7 %48 / 5694.1 %16 / 17
Candidate.cpp -
87.8%87.8%
-
87.8 %129 / 14794.3 %33 / 35
base64.cpp -
91.8%91.8%
-
91.8 %45 / 49100.0 %2 / 2
ParticleMass.cpp -
96.8%96.8%
-
96.8 %30 / 31100.0 %4 / 4
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/index.html b/doc/coverageReport/src/index.html deleted file mode 100644 index 6e1fed226..000000000 --- a/doc/coverageReport/src/index.html +++ /dev/null @@ -1,253 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - srcHitTotalCoverage
Test:coverage.info.cleanedLines:1361270750.3 %
Date:2024-04-08 14:58:22Functions:25142958.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Candidate.cpp -
87.8%87.8%
-
87.8 %129 / 14794.3 %33 / 35
Clock.cpp -
0.0%
-
0.0 %0 / 270.0 %0 / 8
Common.cpp -
77.4%77.4%
-
77.4 %48 / 6283.3 %5 / 6
Cosmology.cpp -
47.8%47.8%
-
47.8 %44 / 9240.0 %6 / 15
EmissionMap.cpp -
53.2%53.2%
-
53.2 %83 / 15654.5 %18 / 33
Geometry.cpp -
36.0%36.0%
-
36.0 %18 / 5046.2 %6 / 13
GridTools.cpp -
27.3%27.3%
-
27.3 %67 / 24536.8 %7 / 19
Module.cpp -
77.1%77.1%
-
77.1 %37 / 4875.0 %9 / 12
ParticleID.cpp -
53.3%53.3%
-
53.3 %16 / 3080.0 %4 / 5
ParticleMass.cpp -
96.8%96.8%
-
96.8 %30 / 31100.0 %4 / 4
ParticleState.cpp -
85.7%85.7%
-
85.7 %48 / 5694.1 %16 / 17
PhotonBackground.cpp -
73.3%73.3%
-
73.3 %88 / 12080.0 %12 / 15
ProgressBar.cpp -
78.0%78.0%
-
78.0 %39 / 5080.0 %4 / 5
Random.cpp -
57.7%57.7%
-
57.7 %139 / 24156.5 %26 / 46
Source.cpp -
58.5%58.5%
-
58.5 %459 / 78455.5 %81 / 146
Variant.cpp -
13.7%13.7%
-
13.7 %71 / 51937.5 %18 / 48
base64.cpp -
91.8%91.8%
-
91.8 %45 / 49100.0 %2 / 2
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html deleted file mode 100644 index a7bc79210..000000000 --- a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func-sort-c.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/ArchimedeanSpiralField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - ArchimedeanSpiralField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0420.0 %
Date:2024-04-08 14:58:22Functions:0100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ArchimedeanSpiralField5setB0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setR0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setVwEd0
_ZN7crpropa22ArchimedeanSpiralField8setOmegaEd0
_ZN7crpropa22ArchimedeanSpiralFieldC2Edddd0
_ZNK7crpropa22ArchimedeanSpiralField5getB0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getR0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getVwEv0
_ZNK7crpropa22ArchimedeanSpiralField8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa22ArchimedeanSpiralField8getOmegaEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html deleted file mode 100644 index 547d3e58d..000000000 --- a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.func.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/ArchimedeanSpiralField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - ArchimedeanSpiralField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0420.0 %
Date:2024-04-08 14:58:22Functions:0100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ArchimedeanSpiralField5setB0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setR0Ed0
_ZN7crpropa22ArchimedeanSpiralField5setVwEd0
_ZN7crpropa22ArchimedeanSpiralField8setOmegaEd0
_ZN7crpropa22ArchimedeanSpiralFieldC2Edddd0
_ZNK7crpropa22ArchimedeanSpiralField5getB0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getR0Ev0
_ZNK7crpropa22ArchimedeanSpiralField5getVwEv0
_ZNK7crpropa22ArchimedeanSpiralField8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa22ArchimedeanSpiralField8getOmegaEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html b/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html deleted file mode 100644 index 0b5c7b362..000000000 --- a/doc/coverageReport/src/magneticField/ArchimedeanSpiralField.cpp.gcov.html +++ /dev/null @@ -1,162 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/ArchimedeanSpiralField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - ArchimedeanSpiralField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0420.0 %
Date:2024-04-08 14:58:22Functions:0100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/ArchimedeanSpiralField.h"
-       2             : 
-       3             : namespace crpropa {
-       4             : 
-       5           0 : ArchimedeanSpiralField::ArchimedeanSpiralField(double B_0, double R_0, double Omega, double V_w) {
-       6           0 :         setB0(B_0);
-       7           0 :         setR0(R_0);
-       8           0 :         setOmega(Omega);
-       9           0 :         setVw(V_w);
-      10           0 : }
-      11             : 
-      12           0 : Vector3d ArchimedeanSpiralField::getField(const Vector3d &pos) const {
-      13             :         
-      14             :         double r = pos.getR();
-      15           0 :         double theta = pos.getTheta();
-      16           0 :         double phi =pos.getPhi();
-      17             :         
-      18           0 :         double cos_phi = cos(phi);
-      19           0 :         double sin_phi = sin(phi);
-      20           0 :         double cos_theta = cos(theta);
-      21           0 :         double sin_theta = sin(theta);
-      22             : 
-      23             :         Vector3d B(0.);
-      24             : 
-      25             :         // radial direction
-      26           0 :         double C1 = R_0*R_0/r/r;
-      27           0 :         B.x += C1 * cos_phi * sin_theta;
-      28           0 :         B.y += C1 * sin_phi * sin_theta;
-      29           0 :         B.z += C1 * cos_theta;
-      30             :         
-      31             :         // azimuthal direction  
-      32           0 :         double C2 = - (Omega*R_0*R_0*sin_theta) / (r*V_w);
-      33           0 :         B.x += C2 * (-sin_phi);
-      34           0 :         B.y += C2 * cos_phi;
-      35             : 
-      36             :         // magnetic field switch at z = 0
-      37           0 :         if (pos.z<0.) {
-      38             :                 B *= -1;
-      39             :         }
-      40             : 
-      41             :         // overall scaling
-      42             :         B *= B_0;
-      43             :         
-      44             : 
-      45           0 :         return B;
-      46             : }
-      47             : 
-      48           0 : void ArchimedeanSpiralField::setR0(double R) {
-      49           0 :         R_0 = R;
-      50           0 :         return;
-      51             : }
-      52             : 
-      53           0 : void ArchimedeanSpiralField::setB0(double B) {
-      54           0 :         B_0 = B;
-      55           0 :         return;
-      56             : }
-      57             : 
-      58           0 : void ArchimedeanSpiralField::setOmega(double Om) {
-      59           0 :         Omega = Om;
-      60           0 :         return;
-      61             : }
-      62             : 
-      63           0 : void ArchimedeanSpiralField::setVw(double v) {
-      64           0 :         V_w = v;
-      65           0 :         return;
-      66             : }
-      67             : 
-      68             : 
-      69           0 : double ArchimedeanSpiralField::getR0() const {
-      70           0 :         return R_0;
-      71             : }
-      72             : 
-      73           0 : double ArchimedeanSpiralField::getB0() const{
-      74           0 :         return B_0;
-      75             : }
-      76             : 
-      77           0 : double ArchimedeanSpiralField::getOmega() const{
-      78           0 :         return Omega;
-      79             : }
-      80             : 
-      81           0 : double ArchimedeanSpiralField::getVw() const {
-      82           0 :         return V_w;
-      83             : }
-      84             : 
-      85             : 
-      86             : } //end namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html deleted file mode 100644 index 57aca7fcf..000000000 --- a/doc/coverageReport/src/magneticField/CMZField.cpp.func-sort-c.html +++ /dev/null @@ -1,144 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/CMZField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - CMZField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10310796.3 %
Date:2024-04-08 14:58:22Functions:1818100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8CMZField13setUseICFieldEb1
_ZN7crpropa8CMZField13setUseMCFieldEb1
_ZN7crpropa8CMZField14setUseNTFFieldEb1
_ZN7crpropa8CMZField14setUseRadioArcEb1
_ZNK7crpropa8CMZField10getICFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField10getMCFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField11getNTFFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField16getRadioArcFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField13getUseICFieldEv2
_ZNK7crpropa8CMZField13getUseMCFieldEv2
_ZNK7crpropa8CMZField14getUseNTFFieldEv2
_ZNK7crpropa8CMZField14getUseRadioArcEv2
_ZN7crpropa8CMZFieldC2Ev5
_ZNK7crpropa8CMZField4getAEd8
_ZNK7crpropa8CMZField4getLEd8
_ZNK7crpropa8CMZField4BPolERKNS_7Vector3IdEES4_ddd9
_ZNK7crpropa8CMZField3BAzERKNS_7Vector3IdEES4_ddd14
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/CMZField.cpp.func.html b/doc/coverageReport/src/magneticField/CMZField.cpp.func.html deleted file mode 100644 index d0edc51bc..000000000 --- a/doc/coverageReport/src/magneticField/CMZField.cpp.func.html +++ /dev/null @@ -1,144 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/CMZField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - CMZField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10310796.3 %
Date:2024-04-08 14:58:22Functions:1818100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8CMZField13setUseICFieldEb1
_ZN7crpropa8CMZField13setUseMCFieldEb1
_ZN7crpropa8CMZField14setUseNTFFieldEb1
_ZN7crpropa8CMZField14setUseRadioArcEb1
_ZN7crpropa8CMZFieldC2Ev5
_ZNK7crpropa8CMZField10getICFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField10getMCFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField11getNTFFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField13getUseICFieldEv2
_ZNK7crpropa8CMZField13getUseMCFieldEv2
_ZNK7crpropa8CMZField14getUseNTFFieldEv2
_ZNK7crpropa8CMZField14getUseRadioArcEv2
_ZNK7crpropa8CMZField16getRadioArcFieldERKNS_7Vector3IdEE1
_ZNK7crpropa8CMZField3BAzERKNS_7Vector3IdEES4_ddd14
_ZNK7crpropa8CMZField4BPolERKNS_7Vector3IdEES4_ddd9
_ZNK7crpropa8CMZField4getAEd8
_ZNK7crpropa8CMZField4getLEd8
_ZNK7crpropa8CMZField8getFieldERKNS_7Vector3IdEE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html b/doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html deleted file mode 100644 index 20cf216cb..000000000 --- a/doc/coverageReport/src/magneticField/CMZField.cpp.gcov.html +++ /dev/null @@ -1,382 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/CMZField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - CMZField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10310796.3 %
Date:2024-04-08 14:58:22Functions:1818100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/CMZField.h"
-       2             : #include "crpropa/Units.h"
-       3             : 
-       4             : namespace crpropa {
-       5             : 
-       6           5 : CMZField::CMZField() {
-       7           5 :     useMCField = false;
-       8           5 :     useICField = true;
-       9           5 :     useNTFField = false;
-      10           5 :     useRadioArc = false;
-      11           5 : }
-      12             : 
-      13           8 : double CMZField::getA(double a1) const {
-      14           8 :     return 4*log(2)/a1/a1;  
-      15             : }
-      16             : 
-      17           8 : double CMZField::getL(double a2) const {
-      18           8 :     return a2/2*log(2);
-      19             : }
-      20             : 
-      21           9 : Vector3d CMZField::BPol(const Vector3d& position,const Vector3d& mid, double B1, double a, double L) const{
-      22             :     // cylindircal coordinates
-      23             :     Vector3d pos = position - mid;
-      24           9 :     double r = sqrt(pos.x*pos.x + pos.y*pos.y);
-      25           9 :     double phi = std::atan2(pos.y, pos.x);
-      26             : 
-      27           9 :     double r1 = 1/(1+a*pos.z*pos.z);
-      28           9 :     double Bs = B1*exp(-r1*r/L);
-      29           9 :     double Br = 2*a*pow_integer<3>(r1)*r*pos.z*Bs;
-      30             :     
-      31             :     Vector3d b = Vector3d(0.);
-      32           9 :     b.z = r1*r1*Bs;
-      33             :     // transform to cartesian coordinates
-      34           9 :     b.x = Br*cos(phi);
-      35           9 :     b.y = Br*sin(phi);
-      36           9 :     return b;
-      37             : }
-      38             : 
-      39          14 : Vector3d CMZField::BAz(const Vector3d& position, const Vector3d& mid, double B1, double eta, double R) const {
-      40             :     // cylindrical coordinates
-      41             :     Vector3d pos = position - mid;
-      42          14 :     double r = sqrt(pos.x*pos.x + pos.y*pos.y);
-      43          14 :     double phi = std::atan2(pos.y,pos.x);
-      44             : 
-      45             :     Vector3d bVec(0.);
-      46          14 :     double Hc = R/sqrt(log(2));
-      47             :     double b = 1.;
-      48             :     double m = 1;
-      49          14 :     double r1 = R/10;
-      50          14 :     double v = m/eta*log((r+b)/(R+b));
-      51          14 :     double cosV = cos(v + m*phi);
-      52             : 
-      53             :     double Br=0;
-      54             :     double Bphi=0;
-      55             :     
-      56          14 :     if(r>r1){
-      57          13 :         double Pre = B1*cosV*exp(-pos.z*pos.z/Hc/Hc);
-      58          13 :         Br = Pre*R/r;
-      59          13 :         Bphi=-Pre/eta*R/(r+b);
-      60             :     }
-      61             :     else{
-      62           1 :         double Pre = B1*exp(-pos.z*pos.z/Hc/Hc)*R/r1*(3*r/r1 - 2*r*r/r1/r1)*cosV;
-      63             :         Br = Pre;
-      64           1 :         Bphi = 1 + 6*(r-r1)/(2*r-3*r1)*(sin(v+m*phi)-sin(v))/cosV;
-      65           1 :         Bphi *= -Pre*r/eta/(r+b);
-      66             :     }
-      67             : 
-      68          14 :     bVec.x = Br*cos(phi) - Bphi*sin(phi);
-      69          14 :     bVec.y = Br*sin(phi) + Bphi*cos(phi);
-      70             : 
-      71          14 :     return bVec;
-      72             : }
-      73             : 
-      74           2 : bool CMZField::getUseMCField() const {
-      75           2 :     return useMCField;
-      76             : }
-      77           2 : bool CMZField::getUseICField() const {
-      78           2 :     return useICField;
-      79             : }
-      80           2 : bool CMZField::getUseNTFField() const {
-      81           2 :     return useNTFField;
-      82             : }
-      83           2 : bool CMZField::getUseRadioArc() const {
-      84           2 :     return useRadioArc;
-      85             : }
-      86             : 
-      87           1 : void CMZField::setUseMCField(bool use) {
-      88           1 :     useMCField = use;
-      89           1 : }
-      90           1 : void CMZField::setUseICField(bool use) {
-      91           1 :     useICField = use;
-      92           1 : }
-      93           1 : void CMZField::setUseNTFField(bool use) {
-      94           1 :     useNTFField = use;
-      95           1 : }
-      96           1 : void CMZField::setUseRadioArc(bool use) {
-      97           1 :     useRadioArc = use;
-      98           1 : }
-      99             : 
-     100           1 : Vector3d CMZField::getMCField(const Vector3d& pos) const {//Field in molecular clouds
-     101             :     Vector3d b(0.);
-     102             :     double eta=0.01;
-     103             :     double N=59; // normalization factor, depends on eta
-     104             : 
-     105             :         // azimuthal component in dense clouds
-     106             :     //A=SgrC 
-     107             :     Vector3d mid(0,-81.59*pc, -16.32*pc);
-     108             :     double R = 1.7*pc; 
-     109             :     double B1=2.1e-3/N;
-     110           1 :     b += BAz(pos, mid, B1, eta, R);
-     111             : 
-     112             :     // A=G0.253+0.016 Dust Ridge A
-     113             :     mid = Vector3d(0, 37.53*pc, -2.37*pc);
-     114             :     R=2.4*pc; 
-     115             :     B1=2.5e-3/N;
-     116           1 :     b += BAz(pos, mid, B1, eta, R);
-     117             : 
-     118             :     //A=Dust Ridge B
-     119             :     mid = Vector3d(0, 50.44, 8.16)*pc;
-     120             :     R=1.9*pc; 
-     121             :     B1=0.9e-3/N;
-     122           1 :     b += BAz(pos, mid, B1, eta, R);
-     123             :     
-     124             :     //A=Dust Ridge C
-     125             :     mid = Vector3d(0,56.37,7.71)*pc;
-     126             :     R=1.9*pc; 
-     127             :     B1=1.2e-3/N;
-     128           1 :     b += BAz(pos, mid, B1, eta, R);
-     129             : 
-     130             :     //A=Dust Ridge D
-     131             :     mid = Vector3d(0, 60.82, 7.42)*pc;
-     132             :     R=3.3*pc; 
-     133             :     B1=1.7e-3/N;
-     134           1 :     b += BAz(pos, mid, B1, eta, R);
-     135             :     
-     136             :     //A=Dust Ridge E
-     137             :     mid = Vector3d(0, 70.91, 0.74)*pc;
-     138             :     R=3.5*pc; 
-     139             :     B1=4.1e-3/N;
-     140           1 :     b += BAz(pos, mid, B1, eta, R);
-     141             :         
-     142             :     //A=Dust Ridge F
-     143             :     mid = Vector3d(0, 73.58, 2.97)*pc;
-     144             :     R=2.4*pc; 
-     145             :     B1=3.9e-3/N;
-     146           1 :     b += BAz(pos, mid, B1, eta, R);
-     147             : 
-     148             :     //Sgr D
-     149             :     mid = Vector3d(0, 166.14, -10.38)*pc;
-     150             :     R=1.8*pc;
-     151             :     B1=0.8e-3/N;
-     152           1 :     b += BAz(pos, mid, B1, eta, R);
-     153             : 
-     154             :     //Sgr B2
-     155             :     mid = Vector3d(0, 97.01, -5.93)*pc;
-     156             :     R=14*pc; 
-     157             :     B1=1.0e-3/N;
-     158           1 :     b += BAz(pos, mid, B1, eta, R);
-     159             :         
-     160             :     //A=Inner R=5pc
-     161             :     mid = Vector3d(0, -8.3, -6.9)*pc;
-     162             :     R=5*pc; 
-     163             :     B1=3.0e-3/0.91;    
-     164           1 :     b += BAz(pos, mid, B1, 0.77, R); // different eta value!
-     165             : 
-     166             :     //20 km s^-1
-     167             :     mid = Vector3d(0, -19.29,-11.87)*pc;
-     168             :     R=9.4*pc; 
-     169             :     B1=2.7e-3/N;
-     170           1 :     b += BAz(pos, mid, B1, eta, R);    
-     171             :     
-     172             :     //50 km s^-1
-     173             :     mid = Vector3d(0, -2.97, -10.38)*pc;
-     174             :     R=9.4*pc; 
-     175             :     B1=3.7e-3/N;
-     176           1 :     b += BAz(pos, mid, B1, eta, R);    
-     177             :     
-     178             :     //SgrA* is different orrientated! 
-     179             :     //only phi component
-     180           1 :     double x = pos.x;
-     181           1 :     double y = pos.y + 8.3*pc;
-     182           1 :     double z = pos.z + 6.9*pc;
-     183             :     R=1.2e12; 
-     184             :     B1=65./3.07;
-     185             :     double Hc = R/sqrt(log(2));
-     186           1 :     double r = sqrt(x*x + y*y);
-     187             :     double r1 = R/10;
-     188           1 :     double phi= std::atan2(y,x);
-     189             :     double Bphi;
-     190             : 
-     191           1 :     if(r>r1){
-     192           1 :         Bphi = - B1*exp(-z*z/Hc/Hc)*R/r;
-     193             :     }
-     194             :     else{
-     195           0 :         - B1*exp(-z*z/Hc/Hc)*R/r1*(3*r/r1- 2*r*r/r1*r1);
-     196             :     }
-     197             : 
-     198           1 :     b.x -= Bphi*sin(phi);
-     199           1 :     b.y += Bphi*cos(phi);
-     200             : 
-     201           1 :     return b*gauss;
-     202             : } 
-     203             : 
-     204           1 : Vector3d CMZField::getICField(const Vector3d& pos) const {//Field in intercloud medium--> poloidal field
-     205             :     Vector3d mid(0.,-8.3*pc,-6.9*pc);
-     206             : 
-     207             :     double eta = 0.85;
-     208             :     double B1 = 1e-5*gauss;
-     209             :     double B2 = B1/eta;
-     210             :     double a = 4*log(2)/pow(70*pc, 2); 
-     211             :     double L = 158*pc/log(2);
-     212             : 
-     213           1 :     return BPol(pos, mid, B2, a, L);
-     214             : }                                                         
-     215             :   
-     216           1 : Vector3d CMZField::getNTFField(const Vector3d& pos) const {//Field in the non-thermal filaments--> predominantly poloidal field (except "pelical"-> azimuthal)
-     217             :     Vector3d b(0.); 
-     218             :     Vector3d mid(0.);
-     219             : 
-     220             :     //A=SgrC
-     221             :     mid = Vector3d(0., -81.59,-1.48)*pc;
-     222             :     double a1=27.44*pc;
-     223             :     double a2=1.73*pc;
-     224             :     double eta=0.48;
-     225             :     double B1=1.e-4;
-     226           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
-     227             : 
-     228             :     //A=G359.15-0.2 The Snake
-     229             :     mid = Vector3d(0, -126.1,-25.22)*pc;
-     230             :     a1=12.86*pc;
-     231             :     a2=2.22*pc;
-     232             :     B1=88.e-6;
-     233           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
-     234             : 
-     235             :     //A=G359.54+0.18 Nonthermal Filament
-     236             :     mid = Vector3d(0, -68.24,25.22)*pc;
-     237             :     a1=15.08*pc;
-     238             :     a2=2.72;
-     239             :     B1=1.e-3;
-     240           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
-     241             : 
-     242             :     //A=G359.79 +17 Nonthermal Filament
-     243             :     mid = Vector3d(0,-31.15,23.74)*pc;
-     244             :     a1=16.07*pc;
-     245             :     a2=3.46*pc;
-     246             :     B1=1.e-3;
-     247           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
-     248             : 
-     249             :     //A=G359.96 +0.09  Nonthermal Filament Southern Thread
-     250             :     mid = Vector3d(0, 5.93, 16.32)*pc;
-     251             :     a1=28.68*pc;
-     252             :     a2=1.73*pc;
-     253             :     B1=1.e-4;
-     254           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
-     255             : 
-     256             :     //A=G0.09 +0.17  Nonthermal Filament Northern thread
-     257             :     mid = Vector3d(0, 13.35, 25.22)*pc;
-     258             :     a1=29.42*pc;
-     259             :     a2=2.23*pc;
-     260             :     B1=140.e-6;
-     261           1 :     b += BPol(pos, mid, B1/eta, getA(a1), getL(a2));
-     262             : 
-     263             :     //A=G359.85+0.47  Nonthermal Filament The Pelican  is not poloidal but azimuthal
-     264             :     mid = Vector3d(0, -22.25, 69.73)*pc;
-     265             :     a1=11.37*pc;
-     266             :     a2=2.23*pc;
-     267             :     B1=70.e-6 /eta;
-     268             :     // by and bz switched because pelican is differently oriented
-     269           1 :     Vector3d bPelican = BPol(pos, mid, B1/eta, getA(a1), getL(a2));
-     270           1 :     b.x += bPelican.x;
-     271           1 :     b.y += bPelican.z;
-     272           1 :     b.z += bPelican.y;
-     273             :     
-     274           1 :         return b*gauss;
-     275             : }
-     276             :   
-     277           1 : Vector3d CMZField::getRadioArcField(const Vector3d& pos) const {//Field in the non-thermal filaments--> predominantly poloidal field
-     278             :     //poloidal field in the non-thermal filament region A=RadioArc
-     279             :     double eta=0.48;
-     280             :     Vector3d mid(0,26.7*pc,10.38*pc);
-     281             :     double a1=70.47*pc;// arcmin-> deg->cm
-     282             :     double a2=9.89*pc;// arcmin-> deg-> cm
-     283             :     double B1=1.e-3;
-     284           1 :     return BPol(pos, mid, B1/eta, getA(a1), getL(a2))*gauss;
-     285             : }
-     286             : 
-     287           1 : Vector3d CMZField::getField(const Vector3d& pos) const{
-     288             :     Vector3d b(0.);
-     289             : 
-     290           1 :     if(useMCField){
-     291           0 :         b += getMCField(pos);
-     292             :     }
-     293           1 :     if(useICField){
-     294           1 :         b += getICField(pos);
-     295             :     }
-     296           1 :     if(useNTFField){
-     297           0 :         b += getNTFField(pos);
-     298             :     }
-     299           1 :     if(useRadioArc){
-     300           0 :         b += getRadioArcField(pos);
-     301             :     }
-     302             : 
-     303           1 :     return b;
-     304             : }
-     305             : 
-     306             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html deleted file mode 100644 index 4cfb03c01..000000000 --- a/doc/coverageReport/src/magneticField/JF12Field.cpp.func-sort-c.html +++ /dev/null @@ -1,188 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/JF12Field.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - JF12Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:02310.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16PlanckJF12bFieldC2Ev0
_ZN7crpropa9JF12Field12setUseXFieldEb0
_ZN7crpropa9JF12Field13isUsingXFieldEv0
_ZN7crpropa9JF12Field14randomStriatedEi0
_ZN7crpropa9JF12Field15getStriatedGridEv0
_ZN7crpropa9JF12Field15randomTurbulentEi0
_ZN7crpropa9JF12Field15setStriatedGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa9JF12Field15setUseDiskFieldEb0
_ZN7crpropa9JF12Field16getTurbulentGridEv0
_ZN7crpropa9JF12Field16isUsingDiskFieldEv0
_ZN7crpropa9JF12Field16setTurbulentGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa9JF12Field18setUseRegularFieldEb0
_ZN7crpropa9JF12Field19isUsingRegularFieldEv0
_ZN7crpropa9JF12Field19setUseStriatedFieldEb0
_ZN7crpropa9JF12Field20isUsingStriatedFieldEv0
_ZN7crpropa9JF12Field20setUseTurbulentFieldEb0
_ZN7crpropa9JF12Field21isUsingTurbulentFieldEv0
_ZN7crpropa9JF12Field23setUseToroidalHaloFieldEb0
_ZN7crpropa9JF12Field24isUsingToroidalHaloFieldEv0
_ZN7crpropa9JF12FieldC2Ev0
_ZNK7crpropa9JF12Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9JF12Field15getRegularFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16getStriatedFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16logisticFunctionERKdS2_S2_0
_ZNK7crpropa9JF12Field17getTurbulentFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field20getToroidalHaloFieldERKdS2_S2_S2_0
_ZNK7crpropa9JF12Field20getTurbulentStrengthERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field9getXFieldERKdS2_S2_S2_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/JF12Field.cpp.func.html b/doc/coverageReport/src/magneticField/JF12Field.cpp.func.html deleted file mode 100644 index f4e99fdd5..000000000 --- a/doc/coverageReport/src/magneticField/JF12Field.cpp.func.html +++ /dev/null @@ -1,188 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/JF12Field.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - JF12Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:02310.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16PlanckJF12bFieldC2Ev0
_ZN7crpropa9JF12Field12setUseXFieldEb0
_ZN7crpropa9JF12Field13isUsingXFieldEv0
_ZN7crpropa9JF12Field14randomStriatedEi0
_ZN7crpropa9JF12Field15getStriatedGridEv0
_ZN7crpropa9JF12Field15randomTurbulentEi0
_ZN7crpropa9JF12Field15setStriatedGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa9JF12Field15setUseDiskFieldEb0
_ZN7crpropa9JF12Field16getTurbulentGridEv0
_ZN7crpropa9JF12Field16isUsingDiskFieldEv0
_ZN7crpropa9JF12Field16setTurbulentGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa9JF12Field18setUseRegularFieldEb0
_ZN7crpropa9JF12Field19isUsingRegularFieldEv0
_ZN7crpropa9JF12Field19setUseStriatedFieldEb0
_ZN7crpropa9JF12Field20isUsingStriatedFieldEv0
_ZN7crpropa9JF12Field20setUseTurbulentFieldEb0
_ZN7crpropa9JF12Field21isUsingTurbulentFieldEv0
_ZN7crpropa9JF12Field23setUseToroidalHaloFieldEb0
_ZN7crpropa9JF12Field24isUsingToroidalHaloFieldEv0
_ZN7crpropa9JF12FieldC2Ev0
_ZNK7crpropa9JF12Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9JF12Field15getRegularFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16getStriatedFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field16logisticFunctionERKdS2_S2_0
_ZNK7crpropa9JF12Field17getTurbulentFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field20getToroidalHaloFieldERKdS2_S2_S2_0
_ZNK7crpropa9JF12Field20getTurbulentStrengthERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa9JF12Field9getXFieldERKdS2_S2_S2_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html b/doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html deleted file mode 100644 index 71e09d723..000000000 --- a/doc/coverageReport/src/magneticField/JF12Field.cpp.gcov.html +++ /dev/null @@ -1,452 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/JF12Field.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - JF12Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:02310.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/JF12Field.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
-       4             : #include "crpropa/Random.h"
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           0 : JF12Field::JF12Field() {
-       9           0 :         useRegularField = true;
-      10           0 :         useStriatedField = false;
-      11           0 :         useTurbulentField = false;
-      12           0 :         useDiskField = true;
-      13           0 :         useToroidalHaloField = true;
-      14           0 :         useXField = true;
-      15             : 
-      16             :         // spiral arm parameters
-      17           0 :         pitch = 11.5 * M_PI / 180;
-      18           0 :         sinPitch = sin(pitch);
-      19           0 :         cosPitch = cos(pitch);
-      20           0 :         tanPitch = tan(pitch);
-      21           0 :         cotPitch =  1. / tanPitch;
-      22           0 :         tan90MinusPitch = tan(M_PI / 2 - pitch);
-      23             : 
-      24           0 :         rArms[0] = 5.1 * kpc;
-      25           0 :         rArms[1] = 6.3 * kpc;
-      26           0 :         rArms[2] = 7.1 * kpc;
-      27           0 :         rArms[3] = 8.3 * kpc;
-      28           0 :         rArms[4] = 9.8 * kpc;
-      29           0 :         rArms[5] = 11.4 * kpc;
-      30           0 :         rArms[6] = 12.7 * kpc;
-      31           0 :         rArms[7] = 15.5 * kpc;
-      32             : 
-      33             :         // regular field parameters
-      34           0 :         bRing = 0.1 * muG;
-      35           0 :         hDisk = 0.40 * kpc;
-      36           0 :         wDisk = 0.27 * kpc;
-      37             : 
-      38           0 :         bDisk[0] = 0.1 * muG;
-      39           0 :         bDisk[1] = 3.0 * muG;
-      40           0 :         bDisk[2] = -0.9 * muG;
-      41           0 :         bDisk[3] = -0.8 * muG;
-      42           0 :         bDisk[4] = -2.0 * muG;
-      43           0 :         bDisk[5] = -4.2 * muG;
-      44           0 :         bDisk[6] = 0.0 * muG;
-      45           0 :         bDisk[7] = 2.7 * muG;
-      46             : 
-      47           0 :         bNorth = 1.4 * muG;
-      48           0 :         bSouth = -1.1 * muG;
-      49           0 :         rNorth = 9.22 * kpc;
-      50           0 :         rSouth = 17 * kpc;
-      51           0 :         wHalo = 0.20 * kpc;
-      52           0 :         z0 = 5.3 * kpc;
-      53             : 
-      54           0 :         bX = 4.6 * muG;
-      55           0 :         thetaX0 = 49.0 * M_PI / 180;
-      56           0 :         sinThetaX0 = sin(thetaX0);
-      57           0 :         cosThetaX0 = cos(thetaX0);
-      58           0 :         tanThetaX0 = tan(thetaX0);
-      59           0 :         cotThetaX0 = 1. / tanThetaX0;
-      60           0 :         rXc = 4.8 * kpc;
-      61           0 :         rX = 2.9 * kpc;
-      62             : 
-      63             :         // striated field parameter
-      64           0 :         sqrtbeta = sqrt(1.36);
-      65             : 
-      66             :         // turbulent field parameters
-      67           0 :         bDiskTurb[0] = 10.81 * muG;
-      68           0 :         bDiskTurb[1] = 6.96 * muG;
-      69           0 :         bDiskTurb[2] = 9.59 * muG;
-      70           0 :         bDiskTurb[3] = 6.96 * muG;
-      71           0 :         bDiskTurb[4] = 1.96 * muG;
-      72           0 :         bDiskTurb[5] = 16.34 * muG;
-      73           0 :         bDiskTurb[6] = 37.29 * muG;
-      74           0 :         bDiskTurb[7] = 10.35 * muG;
-      75             : 
-      76           0 :         bDiskTurb5 = 7.63 * muG;
-      77           0 :         zDiskTurb = 0.61 * kpc;
-      78             : 
-      79           0 :         bHaloTurb = 4.68 * muG;
-      80           0 :         rHaloTurb = 10.97 * kpc;
-      81           0 :         zHaloTurb = 2.84 * kpc;
-      82           0 : }
-      83             : 
-      84           0 : void JF12Field::randomStriated(int seed) {
-      85           0 :         useStriatedField = true;
-      86             :         int N = 100;
-      87           0 :         striatedGrid = new Grid1f(Vector3d(0.), N, 0.1 * kpc);
-      88             : 
-      89           0 :         Random random;
-      90           0 :         if (seed != 0)
-      91           0 :                 random.seed(seed);
-      92             : 
-      93           0 :         for (int ix = 0; ix < N; ix++)
-      94           0 :                 for (int iy = 0; iy < N; iy++)
-      95           0 :                         for (int iz = 0; iz < N; iz++) {
-      96           0 :                                 float &f = striatedGrid->get(ix, iy, iz);
-      97           0 :                                 f = round(random.rand()) * 2 - 1;
-      98             :                         }
-      99           0 : }
-     100             : 
-     101             : #ifdef CRPROPA_HAVE_FFTW3F
-     102           0 : void JF12Field::randomTurbulent(int seed) {
-     103           0 :         useTurbulentField = true;
-     104             :         // turbulent field with Kolmogorov spectrum, B_rms = 1 (will be scaled) and Lc = 60 parsec, and 256 grid points.
-     105             :         // Note that the inertial range of the turbulence is less than 2 orders of magnitude.
-     106             :     const double lMin = 8 * parsec;
-     107             :     const double lMax = 272 * parsec;
-     108             :     const double Brms = 1;
-     109             :     const double spacing = 4 * parsec;
-     110             :     const double grid_n = 256;
-     111             : 
-     112             :     auto spectrum = SimpleTurbulenceSpectrum(Brms, lMin, lMax);
-     113             :     auto gp = GridProperties(Vector3d(0.), grid_n, spacing);
-     114           0 :     auto tf = SimpleGridTurbulence(spectrum, gp, seed);
-     115           0 :     turbulentGrid = tf.getGrid();
-     116             : 
-     117           0 : }
-     118             : #endif
-     119             : 
-     120           0 : void JF12Field::setStriatedGrid(ref_ptr<Grid1f> grid) {
-     121           0 :         useStriatedField = true;
-     122           0 :         striatedGrid = grid;
-     123           0 : }
-     124             : 
-     125           0 : void JF12Field::setTurbulentGrid(ref_ptr<Grid3f> grid) {
-     126           0 :         useTurbulentField = true;
-     127           0 :         turbulentGrid = grid;
-     128           0 : }
-     129             : 
-     130           0 : ref_ptr<Grid1f> JF12Field::getStriatedGrid() {
-     131           0 :         return striatedGrid;
-     132             : }
-     133             : 
-     134           0 : ref_ptr<Grid3f> JF12Field::getTurbulentGrid() {
-     135           0 :         return turbulentGrid;
-     136             : }
-     137             : 
-     138           0 : void JF12Field::setUseRegularField(bool use) {
-     139           0 :         useRegularField = use;
-     140           0 : }
-     141             : 
-     142           0 : void JF12Field::setUseDiskField(bool use) {
-     143           0 :         useDiskField = use;
-     144           0 : }
-     145             : 
-     146           0 : void JF12Field::setUseToroidalHaloField(bool use) {
-     147           0 :         useToroidalHaloField = use;
-     148           0 : }
-     149             : 
-     150           0 : void JF12Field::setUseXField(bool use) {
-     151           0 :         useXField = use;
-     152           0 : }
-     153             : 
-     154           0 : void JF12Field::setUseStriatedField(bool use) {
-     155           0 :         if ((use) and !(striatedGrid)) {
-     156           0 :                 KISS_LOG_WARNING << "JF12Field: No striated field set: ignored. Run e.g. randomStriated().";
-     157           0 :                 return;
-     158             :         }
-     159           0 :         useStriatedField = use;
-     160             : }
-     161             : 
-     162           0 : void JF12Field::setUseTurbulentField(bool use) {
-     163           0 :         if ((use) and !(turbulentGrid)) {
-     164           0 :                 KISS_LOG_WARNING << "JF12Field: No turbulent field set: ignored. Run e.g. randomTurbulent().";
-     165           0 :                 return;
-     166             :         }
-     167           0 :         useTurbulentField = use;
-     168             : }
-     169             : 
-     170           0 : bool JF12Field::isUsingRegularField() {
-     171           0 :         return useRegularField;
-     172             : }
-     173             : 
-     174           0 : bool JF12Field::isUsingDiskField() {
-     175           0 :         return useDiskField;
-     176             : }
-     177             : 
-     178           0 : bool JF12Field::isUsingToroidalHaloField() {
-     179           0 :         return useToroidalHaloField;
-     180             : }
-     181             : 
-     182           0 : bool JF12Field::isUsingXField() {
-     183           0 :         return useXField;
-     184             : }
-     185             : 
-     186           0 : bool JF12Field::isUsingStriatedField() {
-     187           0 :         return useStriatedField;
-     188             : }
-     189             : 
-     190           0 : bool JF12Field::isUsingTurbulentField() {
-     191           0 :         return useTurbulentField;
-     192             : }
-     193             : 
-     194           0 : double JF12Field::logisticFunction(const double& x, const double& x0, const double& w) const {
-     195           0 :         return 1. / (1. + exp(-2. * (fabs(x) - x0) / w));
-     196             : }
-     197             : 
-     198           0 : Vector3d JF12Field::getRegularField(const Vector3d& pos) const {
-     199             :         Vector3d b(0.);
-     200             : 
-     201             :         double d = pos.getR(); // distance to galactic center
-     202             : 
-     203           0 :         if (d < 20 * kpc) {
-     204           0 :                 double r = sqrt(pos.x * pos.x + pos.y * pos.y); // in-plane radius
-     205           0 :                 double phi = pos.getPhi(); // azimuth
-     206           0 :                 double sinPhi = sin(phi);
-     207           0 :                 double cosPhi = cos(phi);
-     208             : 
-     209           0 :                 b += getDiskField(r, pos.z, phi, sinPhi, cosPhi);
-     210           0 :                 b += getToroidalHaloField(r, pos.z, sinPhi, cosPhi);
-     211           0 :                 b += getXField(r, pos.z, sinPhi, cosPhi);
-     212             :         }
-     213             : 
-     214           0 :         return b;
-     215             : }
-     216             : 
-     217           0 : Vector3d JF12Field::getDiskField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
-     218             :         Vector3d b(0.);
-     219           0 :         if (useDiskField) {
-     220           0 :                 double lfDisk = logisticFunction(z, hDisk, wDisk);
-     221           0 :                 if (r > 3 * kpc) {
-     222             :                         double bMag;
-     223           0 :                         if (r < 5 * kpc) {
-     224             :                                 // molecular ring
-     225           0 :                                 bMag = bRing * (5 * kpc / r) * (1 - lfDisk);
-     226           0 :                                 b.x += -bMag * sinPhi;
-     227           0 :                                 b.y += bMag * cosPhi;
-     228             :                         } else {
-     229             :                                 // spiral region
-     230           0 :                                 double r_negx = r * exp(-(phi - M_PI) / tan90MinusPitch);
-     231           0 :                                 if (r_negx > rArms[7])
-     232           0 :                                         r_negx = r * exp(-(phi + M_PI) / tan90MinusPitch);
-     233           0 :                                 if (r_negx > rArms[7])
-     234           0 :                                         r_negx = r * exp(-(phi + 3 * M_PI) / tan90MinusPitch);
-     235             : 
-     236           0 :                                 for (int i = 7; i >= 0; i--)
-     237           0 :                                         if (r_negx < rArms[i])
-     238           0 :                                                 bMag = bDisk[i];
-     239             : 
-     240           0 :                                 bMag *= (5 * kpc / r) * (1 - lfDisk);
-     241           0 :                                 b.x += bMag * (sinPitch * cosPhi - cosPitch * sinPhi);
-     242           0 :                                 b.y += bMag * (sinPitch * sinPhi + cosPitch * cosPhi);
-     243             :                         }
-     244             :                 }
-     245             :         }
-     246           0 :         return b;
-     247             : }
-     248             : 
-     249           0 : Vector3d JF12Field::getToroidalHaloField(const double& r, const double& z, const double& sinPhi, const double& cosPhi) const {
-     250             :         Vector3d b(0.);
-     251             : 
-     252           0 :         if (useToroidalHaloField && (r * r + z * z > 1 * kpc * kpc)){
-     253             : 
-     254           0 :                 double lfDisk = logisticFunction(z, hDisk, wDisk);
-     255           0 :                 double bMagH = exp(-fabs(z) / z0) * lfDisk;
-     256             : 
-     257           0 :                 if (z >= 0)
-     258           0 :                         bMagH *= bNorth * (1 - logisticFunction(r, rNorth, wHalo));
-     259             :                 else
-     260           0 :                         bMagH *= bSouth * (1 - logisticFunction(r, rSouth, wHalo));
-     261           0 :                 b.x += -bMagH * sinPhi;
-     262           0 :                 b.y += bMagH * cosPhi;
-     263             :         }
-     264           0 :         return b;
-     265             : }
-     266             : 
-     267           0 : Vector3d JF12Field::getXField(const double& r, const double& z, const double& sinPhi, const double& cosPhi) const {
-     268             :         Vector3d b(0.);
-     269             : 
-     270           0 :         if (useXField && (r * r + z * z > 1 * kpc * kpc)){
-     271             :                 double bMagX;
-     272             :                 double sinThetaX, cosThetaX;
-     273             :                 double rp;
-     274           0 :                 double rc = rXc + fabs(z) / tanThetaX0;
-     275           0 :                 if (r < rc) {
-     276             :                         // varying elevation region
-     277           0 :                         rp = r * rXc / rc;
-     278           0 :                         bMagX = bX * exp(-1 * rp / rX) * pow(rXc / rc, 2.);
-     279           0 :                         double thetaX = atan2(fabs(z), (r - rp));
-     280           0 :                         if (z == 0)
-     281             :                                 thetaX = M_PI / 2.;
-     282           0 :                         sinThetaX = sin(thetaX);
-     283           0 :                         cosThetaX = cos(thetaX);
-     284             :                 } else {
-     285             :                         // constant elevation region
-     286           0 :                         rp = r - fabs(z) / tanThetaX0;
-     287           0 :                         bMagX = bX * exp(-rp / rX) * (rp / r);
-     288           0 :                         sinThetaX = sinThetaX0;
-     289           0 :                         cosThetaX = cosThetaX0;
-     290             :                 }
-     291           0 :                 double zsign = z < 0 ? -1 : 1;
-     292           0 :                 b.x += zsign * bMagX * cosThetaX * cosPhi;
-     293           0 :                 b.y += zsign * bMagX * cosThetaX * sinPhi;
-     294           0 :                 b.z += bMagX * sinThetaX;
-     295             :         }
-     296           0 :         return b;
-     297             : }
-     298             : 
-     299           0 : Vector3d JF12Field::getStriatedField(const Vector3d& pos) const {
-     300           0 :         return (getRegularField(pos)
-     301           0 :                         * (1. + sqrtbeta * striatedGrid->closestValue(pos)));
-     302             : }
-     303             : 
-     304           0 : double JF12Field::getTurbulentStrength(const Vector3d& pos) const {
-     305           0 :         if (pos.getR() > 20 * kpc)
-     306             :                 return 0;
-     307             : 
-     308           0 :         double r = sqrt(pos.x * pos.x + pos.y * pos.y); // in-plane radius
-     309           0 :         double phi = pos.getPhi(); // azimuth
-     310             : 
-     311             :         // disk
-     312             :         double bDisk = 0;
-     313           0 :         if (r < 5 * kpc) {
-     314           0 :                 bDisk = bDiskTurb5;
-     315             :         } else {
-     316             :                 // spiral region
-     317           0 :                 double r_negx = r * exp(-(phi - M_PI) / tan90MinusPitch);
-     318           0 :                 if (r_negx > rArms[7])
-     319           0 :                         r_negx = r * exp(-(phi + M_PI) / tan90MinusPitch);
-     320           0 :                 if (r_negx > rArms[7])
-     321           0 :                         r_negx = r * exp(-(phi + 3 * M_PI) / tan90MinusPitch);
-     322             : 
-     323           0 :                 for (int i = 7; i >= 0; i--)
-     324           0 :                         if (r_negx < rArms[i])
-     325           0 :                                 bDisk = bDiskTurb[i];
-     326             : 
-     327           0 :                 bDisk *= (5 * kpc) / r;
-     328             :         }
-     329           0 :         bDisk *= exp(-0.5 * pow(pos.z / zDiskTurb, 2));
-     330             : 
-     331             :         // halo
-     332           0 :         double bHalo = bHaloTurb * exp(-r / rHaloTurb)
-     333           0 :                         * exp(-0.5 * pow(pos.z / zHaloTurb, 2));
-     334             : 
-     335             :         // modulate turbulent field
-     336           0 :         return sqrt(pow(bDisk, 2) + pow(bHalo, 2));
-     337             : }
-     338             : 
-     339           0 : Vector3d JF12Field::getTurbulentField(const Vector3d& pos) const {
-     340           0 :         return (turbulentGrid->interpolate(pos) * getTurbulentStrength(pos));
-     341             : }
-     342             : 
-     343           0 : Vector3d JF12Field::getField(const Vector3d& pos) const {
-     344             :         Vector3d b(0.);
-     345           0 :         if (useTurbulentField)
-     346           0 :                 b += getTurbulentField(pos);
-     347           0 :         if (useStriatedField)
-     348           0 :                 b += getStriatedField(pos);
-     349           0 :         else if (useRegularField)
-     350           0 :                 b += getRegularField(pos);
-     351           0 :         return b;
-     352             : }
-     353             : 
-     354             : 
-     355             : 
-     356           0 : PlanckJF12bField::PlanckJF12bField() : JF12Field::JF12Field(){
-     357             :         // regular field parameters
-     358           0 :         bDisk[5] = -3.5 * muG;
-     359           0 :         bX = 1.8 * muG;
-     360             : 
-     361             :         // turbulent field parameters;
-     362           0 :         bDiskTurb[0] = 3.12 * muG;
-     363           0 :         bDiskTurb[1] = 6.24 * muG;
-     364           0 :         bDiskTurb[2] = 3.12 * muG;
-     365           0 :         bDiskTurb[3] = 6.24 * muG;
-     366           0 :         bDiskTurb[4] = 3.12 * muG;
-     367           0 :         bDiskTurb[5] = 6.24 * muG;
-     368           0 :         bDiskTurb[6] = 3.12 * muG;
-     369           0 :         bDiskTurb[7] = 6.24 * muG;
-     370             : 
-     371           0 :         bDiskTurb5 = 3.90 * muG;
-     372             : 
-     373           0 :         bHaloTurb = 7.332 * muG;
-     374           0 : }
-     375             : 
-     376             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html deleted file mode 100644 index 5057574e8..000000000 --- a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func-sort-c.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/JF12FieldSolenoidal.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - JF12FieldSolenoidal.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01420.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19JF12FieldSolenoidal15setXScaleHeightEd0
_ZN7crpropa19JF12FieldSolenoidal19setUseStriatedFieldEb0
_ZN7crpropa19JF12FieldSolenoidal20setUseTurbulentFieldEb0
_ZN7crpropa19JF12FieldSolenoidal22setDiskTransitionWidthEd0
_ZN7crpropa19JF12FieldSolenoidal25deactivateOuterTransitionEv0
_ZN7crpropa19JF12FieldSolenoidalC2Edd0
_ZNK7crpropa19JF12FieldSolenoidal12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa19JF12FieldSolenoidal15getHPhiIntegralERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal15getXScaleHeightEv0
_ZNK7crpropa19JF12FieldSolenoidal22getDiskTransitionWidthEv0
_ZNK7crpropa19JF12FieldSolenoidal27getDiskTransitionPolynomialERKd0
_ZNK7crpropa19JF12FieldSolenoidal30getSpiralFieldStrengthConstantERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal37getDiskTransitionPolynomialDerivativeERKd0
_ZNK7crpropa19JF12FieldSolenoidal9getXFieldERKdS2_S2_S2_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html deleted file mode 100644 index 539e7551e..000000000 --- a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.func.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/JF12FieldSolenoidal.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - JF12FieldSolenoidal.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01420.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19JF12FieldSolenoidal15setXScaleHeightEd0
_ZN7crpropa19JF12FieldSolenoidal19setUseStriatedFieldEb0
_ZN7crpropa19JF12FieldSolenoidal20setUseTurbulentFieldEb0
_ZN7crpropa19JF12FieldSolenoidal22setDiskTransitionWidthEd0
_ZN7crpropa19JF12FieldSolenoidal25deactivateOuterTransitionEv0
_ZN7crpropa19JF12FieldSolenoidalC2Edd0
_ZNK7crpropa19JF12FieldSolenoidal12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa19JF12FieldSolenoidal15getHPhiIntegralERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal15getXScaleHeightEv0
_ZNK7crpropa19JF12FieldSolenoidal22getDiskTransitionWidthEv0
_ZNK7crpropa19JF12FieldSolenoidal27getDiskTransitionPolynomialERKd0
_ZNK7crpropa19JF12FieldSolenoidal30getSpiralFieldStrengthConstantERKdS2_0
_ZNK7crpropa19JF12FieldSolenoidal37getDiskTransitionPolynomialDerivativeERKd0
_ZNK7crpropa19JF12FieldSolenoidal9getXFieldERKdS2_S2_S2_0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html b/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html deleted file mode 100644 index ae5d894a4..000000000 --- a/doc/coverageReport/src/magneticField/JF12FieldSolenoidal.cpp.gcov.html +++ /dev/null @@ -1,378 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/JF12FieldSolenoidal.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - JF12FieldSolenoidal.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01420.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/JF12FieldSolenoidal.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/GridTools.h"
-       4             : #include "crpropa/Random.h"
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           0 : JF12FieldSolenoidal::JF12FieldSolenoidal(double delta, double zs) {
-       9           0 :         zS = zs; // set scale heigth for the parabolic X field lines
-      10           0 :         r1 = 5 * kpc; // inner boundary of the disk field
-      11           0 :         r2 = 20 * kpc; // outer boudary of the disk field
-      12           0 :         r1s = r1 + delta; // the magnetic flux of the spirals is redirected for r in [r1,r1s]
-      13           0 :         r2s = r2 - delta; // same here at outer boundary between r2s and r2
-      14           0 :         phi0 = 0.; // somewhat arbitrary choice, has to be chosen in [-pi,pi]
-      15             : 
-      16           0 :         for (int i = 1;i < 9; i++){
-      17             :                 // fill the array with angles in [-pi,pi] where the 8 spiral arms intersect the r1 - ring
-      18             :                 // indexing starts at 1 to match the indexing in the papers on the JF12 field!
-      19           0 :                 phi0Arms[i] = M_PI - cotPitch * log(rArms[i-1] / r1);
-      20             :         }
-      21             : 
-      22             :         // cyclic closure of the array, with next values periodically continued
-      23             :         // outside [-pi,pi] to simplify looping and searching for correct spiral arms
-      24           0 :         phi0Arms[0] = phi0Arms[8] + 2 * M_PI;
-      25           0 :         phi0Arms[9] = phi0Arms[1] - 2 * M_PI;
-      26           0 :         phi0Arms[10] = phi0Arms[2] - 2 *M_PI;
-      27             : 
-      28             :         // determine the position of phi0 in the array, i.e. find the correct spiral arm.
-      29             :         int idx0 = 1; // corresponding index in phi0Arms such that phi0Arms[idx0] < phi0 < phi0Arms[idx0-1]
-      30           0 :         while (phi0 < phi0Arms[idx0]){
-      31           0 :                 idx0 += 1; // search clockwise, starting with the check if phi0Arms[1] < phi0 < phi0Arms[0]
-      32             :         }
-      33             : 
-      34             :         // fill the bDisk array with spiral field strengths at r = r1.
-      35             :         // note the indexing starting with 1 here to match the indexing in the JF12 papers!
-      36             :         // for a position (r1,phi), phi in [-pi,pi], the correct field strength is given by
-      37             :         // bDisk[i] if phi0Arms[i] < phi0 < phi0Arms[i-1].
-      38           0 :         bDisk[1] = 0.1 * muG;
-      39           0 :         bDisk[2] = 3.0 * muG;
-      40           0 :         bDisk[3] = -0.9 * muG;
-      41           0 :         bDisk[4] = -0.8 * muG;
-      42           0 :         bDisk[5] = -2.0 * muG;
-      43           0 :         bDisk[6] = -4.2 * muG;
-      44           0 :         bDisk[7] = 0.0 * muG;
-      45             : 
-      46             :         // re-compute b_8 for actual (net flux = 0)-correction of the spiral field with minimal round-off errors
-      47             :         double flux1to7 = 0.;
-      48           0 :         for (int i = 1; i < 8; i++){
-      49           0 :                 flux1to7 += (phi0Arms[i-1] - phi0Arms[i]) * bDisk[i];
-      50             :         }
-      51           0 :         bDisk[8] = -flux1to7 / (phi0Arms[7] - phi0Arms[8]);
-      52             : 
-      53           0 :         bDisk[0] = bDisk[8]; // again close the array periodically
-      54           0 :         bDisk[9] = bDisk[1];
-      55           0 :         bDisk[10] = bDisk[2];
-      56             : 
-      57             :         // set coefficients for the evaluation of the phi-integral over the piecewise constant field strengths at r=r1
-      58             :         // such that it may be evaluated as H(phi) = phiCoeff[j] + bDisk[j] * phi later on
-      59             :         // start integration at phi0Arms[0] first, shift to lower integration boundary phi0 later
-      60           0 :         phiCoeff[0] = 0;
-      61           0 :         for (int i = 1; i < 10; i++){
-      62           0 :                 phiCoeff[i] = phiCoeff[i-1] + (bDisk[i-1] - bDisk[i]) * phi0Arms[i-1];
-      63             :         }
-      64             : 
-      65             :         // correct for H(phi0) = 0
-      66           0 :         corr = phiCoeff[idx0] + bDisk[idx0] * phi0;
-      67           0 :         for (int i = 1; i < 10; i++){
-      68           0 :                 phiCoeff[i] = phiCoeff[i] - corr;
-      69             :         }
-      70           0 : }
-      71             : 
-      72           0 : void JF12FieldSolenoidal::setDiskTransitionWidth(double delta) {
-      73           0 :         r1s = r1 + delta;
-      74           0 :         r2s = r2 - delta;
-      75           0 : }
-      76             : 
-      77           0 : void JF12FieldSolenoidal::setXScaleHeight(double zs) {
-      78           0 :         zS = zs;
-      79           0 : }
-      80             : 
-      81           0 : double JF12FieldSolenoidal::getDiskTransitionWidth() const {
-      82           0 :         return (r1s - r1);
-      83             : }
-      84             : 
-      85           0 : double JF12FieldSolenoidal::getXScaleHeight() const {
-      86           0 :         return zS;
-      87             : }
-      88             : 
-      89           0 : void JF12FieldSolenoidal::deactivateOuterTransition() {
-      90           0 :         r2s = r2;
-      91           0 : }
-      92             : 
-      93           0 : void JF12FieldSolenoidal::setUseStriatedField(bool use) {
-      94           0 :         if ((use) and (striatedGrid)) {
-      95           0 :                 KISS_LOG_WARNING << "JF12FieldSolenoidal: No striated field set: ignored.";
-      96           0 :                 return;
-      97             :         }
-      98           0 :         useStriatedField = use;
-      99             : }
-     100             : 
-     101           0 : void JF12FieldSolenoidal::setUseTurbulentField(bool use) {
-     102           0 :         if ((use) and (turbulentGrid)) {
-     103           0 :                 KISS_LOG_WARNING << "JF12FieldSolenoidal: No turbulent field set: ignored.";
-     104           0 :                 return;
-     105             :         }
-     106           0 :         useTurbulentField = use;
-     107             : }
-     108             : 
-     109           0 : Vector3d JF12FieldSolenoidal::getDiskField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
-     110             :         Vector3d b(0.);
-     111             : 
-     112           0 :         if (useDiskField){
-     113           0 :                 double lfDisk = logisticFunction(z, hDisk, wDisk); // for vertical scaling as in initial JF12
-     114             : 
-     115           0 :                 double hint = getHPhiIntegral(r, phi); // phi integral to restore solenoidality in transition region, only enters if r is in [r1,r1s] or [r2s,r2]
-     116           0 :                 double mag1 = getSpiralFieldStrengthConstant(r, phi); // returns bDisk[j] for the current spiral arm
-     117             : 
-     118           0 :                 if ((r1 < r) && (r < r2)) {
-     119           0 :                         double pdelta = getDiskTransitionPolynomial(r);
-     120           0 :                         double qdelta = getDiskTransitionPolynomialDerivative(r);
-     121           0 :                         double br = pdelta * mag1 * sinPitch;
-     122           0 :                         double bphi = pdelta * mag1 * cosPitch - qdelta * hint * sinPitch;
-     123             : 
-     124           0 :                         b.x += br * cosPhi - bphi * sinPhi;
-     125           0 :                         b.y += br * sinPhi + bphi * cosPhi;
-     126             : 
-     127           0 :                         b *= (1 - lfDisk);
-     128             :                 }
-     129             :         }
-     130           0 :         return b;
-     131             : }
-     132             : 
-     133           0 : Vector3d JF12FieldSolenoidal::getXField(const double& r, const double& z, const double& sinPhi, const double& cosPhi) const {
-     134             :         Vector3d b(0.);
-     135             : 
-     136           0 :         if (useXField){
-     137             :                 double bMagX;
-     138             :                 double sinThetaX, cosThetaX;
-     139             :                 double rp; // radius where current intial field line passes z = 0
-     140           0 :                 double rc = rXc + fabs(z) / tanThetaX0;
-     141           0 :                 double r0c = rXc + zS / tanThetaX0; // radius where field line through rXc passes z = zS
-     142             :                 double f, r0, br0, bz0;
-     143             :                 bool inner = true; // distinguish between inner and outer region
-     144             : 
-     145             :                 // return intial field if z>=zS
-     146           0 :                 if (fabs(z) > zS){
-     147           0 :                         if ((r == 0.)){
-     148           0 :                                 b.z = bX / ((1. + fabs(z) * cotThetaX0 / rXc) * (1. + fabs(z) * cotThetaX0 / rXc));
-     149           0 :                                 return b;
-     150             :                         }
-     151             : 
-     152           0 :                         if (r < rc) {
-     153             :                         // inner varying elevation region
-     154           0 :                                 rp = r * rXc / rc;
-     155           0 :                                 bMagX = bX * exp(-1 * rp / rX) * (rXc / rc) * (rXc / rc);
-     156             : 
-     157           0 :                                 double thetaX = atan(fabs(z) / (r - rp));
-     158             : 
-     159           0 :                                 if (z == 0)
-     160             :                                         thetaX = M_PI / 2.;
-     161             : 
-     162           0 :                                 sinThetaX = sin(thetaX);
-     163           0 :                                 cosThetaX = cos(thetaX);
-     164             :                         }
-     165             :                         else {
-     166             :                         // outer constant elevation region
-     167           0 :                                 rp = r - fabs(z) / tanThetaX0;
-     168           0 :                                 bMagX = bX * exp(-rp / rX) * (rp / r);
-     169             : 
-     170           0 :                                 sinThetaX = sinThetaX0;
-     171           0 :                                 cosThetaX = cosThetaX0;
-     172             :                         }
-     173           0 :                         double zsign = z < 0 ? -1 : 1;
-     174           0 :                         b.x += zsign * bMagX * cosThetaX * cosPhi;
-     175           0 :                         b.y += zsign * bMagX * cosThetaX * sinPhi;
-     176           0 :                         b.z += bMagX * sinThetaX;
-     177             :                 }
-     178             :                 // parabolic field lines for z<zS
-     179             :                 else {
-     180             :                                 // determine r at which parabolic field line through (r,z) passes z = zS
-     181           0 :                                 r0 = r * 1. / (1.- 1./ (2. * (zS + rXc * tanThetaX0)) * (zS - z * z / zS));
-     182             : 
-     183             :                                 // determine correct region (inner/outer)
-     184             :                                 // and compute factor F for solenoidality
-     185           0 :                                 if (r0 >= r0c){
-     186           0 :                                         r0 = r + 1. / (2. * tanThetaX0) * (zS - z * z / zS);
-     187           0 :                                         f = 1. + 1/ (2 * r * tanThetaX0/ zS) * (1. - (z / zS) * (z / zS));
-     188             :                                 }
-     189             :                                 else
-     190             :                                 {
-     191           0 :                                          f = 1. / ((1. - 1./( 2. + 2. * (rXc * tanThetaX0/ zS)) * (1. - (z / zS) * (z / zS))) * (1. - 1./( 2. + 2. * (rXc * tanThetaX0/ zS)) * (1. - (z / zS) * (z / zS))));
-     192             :                                 }
-     193             : 
-     194             :                                 // field strength at that position
-     195           0 :                                 if (r0 < r0c){
-     196           0 :                                          rp = r0 * rXc / r0c;
-     197           0 :                                          double thetaX = atan(zS / (r0 - rp));
-     198             : 
-     199             :                                          // field strength at (r0,zS) for inner region
-     200           0 :                                          br0 = bX * exp(- rp / rX) * (rXc/ r0c) * (rXc/ r0c) * cos(thetaX);
-     201           0 :                                          bz0 = bX * exp(- rp / rX) * (rXc/ r0c) * (rXc/ r0c) * sin(thetaX);
-     202             :                                  }
-     203             :                                  else {
-     204             :                                          // field strength at (r0,zS) for outer region
-     205           0 :                                          rp = r0 - zS / tanThetaX0;
-     206           0 :                                          br0 =  bX * exp(- rp / rX) * (rp/r0) * cosThetaX0;
-     207           0 :                                          bz0 =  bX * exp(- rp / rX) * (rp/r0) * sinThetaX0;
-     208             :                                  }
-     209             : 
-     210           0 :                                  double br = z / zS * f * br0;
-     211           0 :                                  double bz = bz0 * f;
-     212             : 
-     213           0 :                                  b.x += br * cosPhi;
-     214           0 :                                  b.y += br * sinPhi;
-     215           0 :                                  b.z += bz;
-     216             :                 }
-     217             :         }
-     218             :         return b;
-     219             : }
-     220             : 
-     221           0 : double JF12FieldSolenoidal::getDiskTransitionPolynomial(const double& r) const {
-     222             :         // 0 disk field outside
-     223           0 :         if ((r < r1) || (r > r2)) {
-     224             :                 return 0.;
-     225             :         }
-     226             :         // unchanged field
-     227           0 :         if ((r > r1s) && (r < r2s)) {
-     228           0 :                 return r1/r;
-     229             :         }
-     230             :         // transitions region parameters
-     231             :         double r_a = r1;
-     232             :         double r_b = r1s;
-     233             : 
-     234           0 :         if (r >= r2s) {
-     235             :                 r_a = r2;
-     236             :                 r_b = r2s;
-     237             :         }
-     238             :         // differentiable transition at r_s, continous at r_a
-     239           0 :         double fakt = (r_a / r_b - 2.) / ((r_a - r_b) *  (r_a - r_b));
-     240           0 :         return (r1/r_b) * (2. - r / r_b + fakt * (r-r_b) * (r-r_b));
-     241             : }
-     242             : 
-     243           0 : double JF12FieldSolenoidal::getDiskTransitionPolynomialDerivative(const double& r) const {
-     244             :         // 0 disk field outside
-     245           0 :         if ((r < r1) || (r > r2)) {
-     246             :                 return 0.;
-     247             :         }
-     248             :         // unchanged field
-     249           0 :         if ((r > r1s) && (r < r2s)) {
-     250             :                 return 0.;
-     251             :         }
-     252             :         // transitions region parameters
-     253             :         double r_a = r1;
-     254             :         double r_b = r1s;
-     255             : 
-     256           0 :         if (r >= r2s) {
-     257             :                 r_a = r2;
-     258             :                 r_b = r2s;
-     259             :         }
-     260             :         // differentiable transition polynomial at r_s, continous at r_a
-     261           0 :         double fakt = (r_a / r_b - 2.) / ((r_a - r_b) * (r_a - r_b));
-     262           0 :         return (r1/r_b) * (2. - 2. * r/r_b + fakt * (3. * r * r - 4. * r * r_b + r_b * r_b));
-     263             : }
-     264             : 
-     265           0 : double JF12FieldSolenoidal::getHPhiIntegral(const double& r, const double& phi) const {
-     266             :         // Evaluates the H(phi1) integral for solenoidality for the position (r,phi) which is mapped back to (r1=5kpc,phi1)
-     267             :         // along the spiral field line.
-     268             :         double H_ret = 0.;
-     269             : 
-     270           0 :         if ((r1 < r) && (r < r2)){
-     271             :                 // find index of the correct spiral arm for (r1,phi1) just like in getSpiralFieldStrengthConstant
-     272             :                 int idx = 1;
-     273           0 :                 double phi1 = phi - log(r/r1) * cotPitch;
-     274           0 :                 phi1 = atan2(sin(phi1), cos(phi1));
-     275           0 :                 while (phi1 < phi0Arms[idx]){
-     276           0 :                         idx += 1;
-     277             :                 }
-     278           0 :                 H_ret = phi1 * bDisk[idx] + phiCoeff[idx];
-     279             :         }
-     280           0 :         return H_ret;
-     281             : }
-     282             : 
-     283           0 : double JF12FieldSolenoidal::getSpiralFieldStrengthConstant(const double& r, const double& phi) const {
-     284             :         // For a given position (r, phi) in polar coordinates, this method returns the field strength
-     285             :         // of the spiral field at r1 = 5 kpc for the magnetic spiral arm where (r, phi) is located.
-     286             :         // The method first computes the angle phi1 at which the spiral field line passing through (r, phi) intersects
-     287             :         // the circle with radius r1 = 5 kpc. Afterwards, the correct spiral arm is found by searching the index idx
-     288             :         // such that phi0Arms[idx] < phi1 < phi0Arms[idx-1]. The correct field strength of the respective spiral arm
-     289             :         // where (r, phi) is located is then given as bDisk[idx].
-     290             :         double b_ret = 0.;
-     291             :         int idx = 1;
-     292           0 :         if ((r1 < r) && (r < r2)){
-     293           0 :                 double phi1 = phi - log(r/r1) * cotPitch; // map the position (r, phi) to (5 kpc, phi1) along the logarithmic spiral field line
-     294           0 :                 phi1 = atan2(sin(phi1), cos(phi1)); // map this angle to [-pi,+pi]
-     295           0 :                 while (phi1 < phi0Arms[idx]){
-     296           0 :                         idx += 1; // run clockwise through the spiral arms; the cyclic closure of phi0Arms[9] = phi0Arms[1] - 2 pi is needed if -pi <= phi1 <= phi0Arms[8].
-     297             :                 }
-     298           0 :                 b_ret = bDisk[idx];
-     299             :         }
-     300           0 :         return b_ret;
-     301             : }
-     302             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html deleted file mode 100644 index b8384f639..000000000 --- a/doc/coverageReport/src/magneticField/MagneticField.cpp.func-sort-c.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/MagneticField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - MagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486672.7 %
Date:2024-04-08 14:58:22Functions:91656.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21PeriodicMagneticField10getExtendsEv0
_ZN7crpropa21PeriodicMagneticField10setExtendsERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticField12isReflectiveEv0
_ZN7crpropa21PeriodicMagneticField13setReflectiveEb0
_ZN7crpropa21PeriodicMagneticField9getOriginEv0
_ZN7crpropa21PeriodicMagneticField9setOriginERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEES7_b1
_ZN7crpropa22MagneticFieldEvolutionC2ENS_7ref_ptrINS_13MagneticFieldEEEd1
_ZN7crpropa24RenormalizeMagneticField8getFieldERKNS_7Vector3IdEE1
_ZN7crpropa24RenormalizeMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17MagneticFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa19MagneticDipoleField8getFieldERKNS_7Vector3IdEE2
_ZNK7crpropa22MagneticFieldEvolution8getFieldERKNS_7Vector3IdEEd2
_ZN7crpropa17MagneticFieldList8addFieldENS_7ref_ptrINS_13MagneticFieldEEE3
_ZNK7crpropa21PeriodicMagneticField8getFieldERKNS_7Vector3IdEE3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/MagneticField.cpp.func.html b/doc/coverageReport/src/magneticField/MagneticField.cpp.func.html deleted file mode 100644 index 2a5f1bfd3..000000000 --- a/doc/coverageReport/src/magneticField/MagneticField.cpp.func.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/MagneticField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - MagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486672.7 %
Date:2024-04-08 14:58:22Functions:91656.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17MagneticFieldList8addFieldENS_7ref_ptrINS_13MagneticFieldEEE3
_ZN7crpropa21PeriodicMagneticField10getExtendsEv0
_ZN7crpropa21PeriodicMagneticField10setExtendsERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticField12isReflectiveEv0
_ZN7crpropa21PeriodicMagneticField13setReflectiveEb0
_ZN7crpropa21PeriodicMagneticField9getOriginEv0
_ZN7crpropa21PeriodicMagneticField9setOriginERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEE0
_ZN7crpropa21PeriodicMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEERKNS_7Vector3IdEES7_b1
_ZN7crpropa22MagneticFieldEvolutionC2ENS_7ref_ptrINS_13MagneticFieldEEEd1
_ZN7crpropa24RenormalizeMagneticField8getFieldERKNS_7Vector3IdEE1
_ZN7crpropa24RenormalizeMagneticFieldC2ENS_7ref_ptrINS_13MagneticFieldEEENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17MagneticFieldList8getFieldERKNS_7Vector3IdEE1
_ZNK7crpropa19MagneticDipoleField8getFieldERKNS_7Vector3IdEE2
_ZNK7crpropa21PeriodicMagneticField8getFieldERKNS_7Vector3IdEE3
_ZNK7crpropa22MagneticFieldEvolution8getFieldERKNS_7Vector3IdEEd2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html b/doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html deleted file mode 100644 index 086759e57..000000000 --- a/doc/coverageReport/src/magneticField/MagneticField.cpp.gcov.html +++ /dev/null @@ -1,188 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/MagneticField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - MagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:486672.7 %
Date:2024-04-08 14:58:22Functions:91656.2 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/MagneticField.h"
-       2             : 
-       3             : namespace crpropa {
-       4             : 
-       5           0 : PeriodicMagneticField::PeriodicMagneticField(ref_ptr<MagneticField> field,
-       6           0 :                 const Vector3d &extends) :
-       7           0 :                 field(field), extends(extends), origin(0, 0, 0), reflective(false) {
-       8             : 
-       9           0 : }
-      10             : 
-      11           1 : PeriodicMagneticField::PeriodicMagneticField(ref_ptr<MagneticField> field,
-      12           1 :                 const Vector3d &extends, const Vector3d &origin, bool reflective) :
-      13           1 :                 field(field), extends(extends), origin(origin), reflective(reflective) {
-      14             : 
-      15           1 : }
-      16             : 
-      17           0 : Vector3d &PeriodicMagneticField::getOrigin() {
-      18           0 :         return origin;
-      19             : }
-      20             : 
-      21           0 : void PeriodicMagneticField::setOrigin(const Vector3d &origin) {
-      22             :         this->origin = origin;
-      23           0 : }
-      24             : 
-      25           0 : Vector3d &PeriodicMagneticField::getExtends() {
-      26           0 :         return extends;
-      27             : }
-      28             : 
-      29           0 : void PeriodicMagneticField::setExtends(const Vector3d &origin) {
-      30             :         this->extends = extends;
-      31           0 : }
-      32             : 
-      33           0 : bool PeriodicMagneticField::isReflective() {
-      34           0 :         return reflective;
-      35             : }
-      36             : 
-      37           0 : void PeriodicMagneticField::setReflective(bool reflective) {
-      38           0 :         this->reflective = reflective;
-      39           0 : }
-      40             : 
-      41           3 : Vector3d PeriodicMagneticField::getField(const Vector3d &position) const {
-      42           3 :         Vector3d n = ((position - origin) / extends).floor();
-      43             :         Vector3d p = position - origin - n * extends;
-      44             : 
-      45           3 :         if (reflective) {
-      46           3 :                 long mx = (long) ::fabs(n.x) % 2;
-      47           3 :                 if (mx == 1)
-      48           2 :                         p.x = extends.x - p.x;
-      49           3 :                 long my = (long) ::fabs(n.y) % 2;
-      50           3 :                 if (my == 1)
-      51           0 :                         p.y = extends.y - p.y;
-      52           3 :                 long mz = (long) ::fabs(n.z) % 2;
-      53           3 :                 if (mz == 1)
-      54           2 :                         p.z = extends.z - p.z;
-      55             :         }
-      56             : 
-      57           3 :         return field->getField(p);
-      58             : }
-      59             : 
-      60           3 : void MagneticFieldList::addField(ref_ptr<MagneticField> field) {
-      61           3 :         fields.push_back(field);
-      62           3 : }
-      63             : 
-      64           1 : Vector3d MagneticFieldList::getField(const Vector3d &position) const {
-      65             :         Vector3d b;
-      66           4 :         for (int i = 0; i < fields.size(); i++)
-      67           3 :                 b += fields[i]->getField(position);
-      68           1 :         return b;
-      69             : }
-      70             : 
-      71           1 : MagneticFieldEvolution::MagneticFieldEvolution(ref_ptr<MagneticField> field,
-      72           1 :         double m) :
-      73           1 :         field(field), m(m) {
-      74           1 : }
-      75             : 
-      76           2 : Vector3d MagneticFieldEvolution::getField(const Vector3d &position,
-      77             :         double z) const {
-      78           2 :         return field->getField(position) * pow(1+z, m);
-      79             : }
-      80             : 
-      81           2 : Vector3d MagneticDipoleField::getField(const Vector3d &position) const {
-      82             :                 Vector3d r = (position - origin);
-      83           2 :                 Vector3d unit_r = r.getUnitVector();
-      84             :                 
-      85           2 :                 if (r.getR() == 0) { // singularity
-      86             :                         return moment * 2 * mu0 / 3;
-      87             :                 }
-      88           2 :                 return (unit_r * (unit_r.dot(moment)) * 3 - moment) / pow(r.getR() / radius, 3) * mu0 / (4*M_PI);
-      89             : }
-      90             : 
-      91             : #ifdef CRPROPA_HAVE_MUPARSER
-      92           1 : RenormalizeMagneticField::RenormalizeMagneticField(ref_ptr<MagneticField> field,
-      93           1 :                 std::string expression) :
-      94           2 :                 field(field), expression(expression) {
-      95             : 
-      96           1 :         p =  new mu::Parser();
-      97           1 :         p->DefineVar("B", &Bmag);
-      98           1 :         p->DefineConst("tesla", tesla);
-      99           1 :         p->DefineConst("gauss", gauss);
-     100           1 :         p->DefineConst("muG", muG);
-     101           1 :         p->DefineConst("nG", nG);
-     102           1 :         p->SetExpr(expression);
-     103           1 : }
-     104             : 
-     105           1 : Vector3d RenormalizeMagneticField::getField(const Vector3d &position) {
-     106           1 :         Vector3d B = field->getField(position);
-     107           1 :         Bmag = B.getR();
-     108           1 :         return B * p->Eval();
-     109             : }
-     110             : #endif
-     111             : 
-     112             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html deleted file mode 100644 index 6c98862d1..000000000 --- a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func-sort-c.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/MagneticFieldGrid.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - MagneticFieldGrid.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0310.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17MagneticFieldGrid7getGridEv0
_ZN7crpropa17MagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17MagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid13setReflectiveEbb0
_ZN7crpropa26ModulatedMagneticFieldGrid17getModulationGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid17setModulationGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid7getGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS1_INS2_IfEEEE0
_ZNK7crpropa17MagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa26ModulatedMagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html deleted file mode 100644 index 10a3651e7..000000000 --- a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.func.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/MagneticFieldGrid.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - MagneticFieldGrid.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0310.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17MagneticFieldGrid7getGridEv0
_ZN7crpropa17MagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa17MagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid13setReflectiveEbb0
_ZN7crpropa26ModulatedMagneticFieldGrid17getModulationGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid17setModulationGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa26ModulatedMagneticFieldGrid7getGridEv0
_ZN7crpropa26ModulatedMagneticFieldGrid7setGridENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEE0
_ZN7crpropa26ModulatedMagneticFieldGridC2ENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEENS1_INS2_IfEEEE0
_ZNK7crpropa17MagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
_ZNK7crpropa26ModulatedMagneticFieldGrid8getFieldERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html b/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html deleted file mode 100644 index 9a3f969fb..000000000 --- a/doc/coverageReport/src/magneticField/MagneticFieldGrid.cpp.gcov.html +++ /dev/null @@ -1,133 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/MagneticFieldGrid.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - MagneticFieldGrid.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0310.0 %
Date:2024-04-08 14:58:22Functions:0110.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/MagneticFieldGrid.h"
-       2             : 
-       3             : namespace crpropa {
-       4             : 
-       5           0 : MagneticFieldGrid::MagneticFieldGrid(ref_ptr<Grid3f> grid) {
-       6           0 :         setGrid(grid);
-       7           0 : }
-       8             : 
-       9           0 : void MagneticFieldGrid::setGrid(ref_ptr<Grid3f> grid) {
-      10           0 :         this->grid = grid;
-      11           0 : }
-      12             : 
-      13           0 : ref_ptr<Grid3f> MagneticFieldGrid::getGrid() {
-      14           0 :         return grid;
-      15             : }
-      16             : 
-      17           0 : Vector3d MagneticFieldGrid::getField(const Vector3d &pos) const {
-      18           0 :         return grid->interpolate(pos);
-      19             : }
-      20             : 
-      21           0 : ModulatedMagneticFieldGrid::ModulatedMagneticFieldGrid(ref_ptr<Grid3f> grid,
-      22           0 :                 ref_ptr<Grid1f> modGrid) {
-      23             :         grid->setReflective(false);
-      24             :         modGrid->setReflective(true);
-      25           0 :         setGrid(grid);
-      26           0 :         setModulationGrid(modGrid);
-      27           0 : }
-      28             : 
-      29           0 : void ModulatedMagneticFieldGrid::setGrid(ref_ptr<Grid3f> g) {
-      30           0 :         grid = g;
-      31           0 : }
-      32             : 
-      33           0 : ref_ptr<Grid3f> ModulatedMagneticFieldGrid::getGrid() {
-      34           0 :         return grid;
-      35             : }
-      36             : 
-      37           0 : void ModulatedMagneticFieldGrid::setModulationGrid(ref_ptr<Grid1f> g) {
-      38           0 :         modGrid = g;
-      39           0 : }
-      40             : 
-      41           0 : ref_ptr<Grid1f> ModulatedMagneticFieldGrid::getModulationGrid() {
-      42           0 :         return modGrid;
-      43             : }
-      44             : 
-      45           0 : void ModulatedMagneticFieldGrid::setReflective(bool gridReflective,
-      46             :                 bool modGridReflective) {
-      47             :         grid->setReflective(gridReflective);
-      48             :         modGrid->setReflective(modGridReflective);
-      49           0 : }
-      50             : 
-      51           0 : Vector3d ModulatedMagneticFieldGrid::getField(const Vector3d &pos) const {
-      52           0 :         float m = modGrid->interpolate(pos);
-      53           0 :         Vector3d b = grid->interpolate(pos);
-      54           0 :         return b * m;
-      55             : }
-      56             : 
-      57             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html deleted file mode 100644 index 1594ee831..000000000 --- a/doc/coverageReport/src/magneticField/PT11Field.cpp.func-sort-c.html +++ /dev/null @@ -1,108 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/PT11Field.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - PT11Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9PT11Field10isUsingASSEv0
_ZN7crpropa9PT11Field10isUsingBSSEv0
_ZN7crpropa9PT11Field10setUseHaloEb0
_ZN7crpropa9PT11Field11isUsingHaloEv0
_ZN7crpropa9PT11Field9SetParamsEv0
_ZN7crpropa9PT11Field9setUseASSEb0
_ZN7crpropa9PT11Field9setUseBSSEb0
_ZN7crpropa9PT11FieldC2Ev0
_ZNK7crpropa9PT11Field8getFieldERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/PT11Field.cpp.func.html b/doc/coverageReport/src/magneticField/PT11Field.cpp.func.html deleted file mode 100644 index 62ece690d..000000000 --- a/doc/coverageReport/src/magneticField/PT11Field.cpp.func.html +++ /dev/null @@ -1,108 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/PT11Field.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - PT11Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9PT11Field10isUsingASSEv0
_ZN7crpropa9PT11Field10isUsingBSSEv0
_ZN7crpropa9PT11Field10setUseHaloEb0
_ZN7crpropa9PT11Field11isUsingHaloEv0
_ZN7crpropa9PT11Field9SetParamsEv0
_ZN7crpropa9PT11Field9setUseASSEb0
_ZN7crpropa9PT11Field9setUseBSSEb0
_ZN7crpropa9PT11FieldC2Ev0
_ZNK7crpropa9PT11Field8getFieldERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html b/doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html deleted file mode 100644 index 36fdae7a3..000000000 --- a/doc/coverageReport/src/magneticField/PT11Field.cpp.gcov.html +++ /dev/null @@ -1,206 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/PT11Field.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - PT11Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/PT11Field.h"
-       2             : #include "crpropa/Units.h"
-       3             : 
-       4             : #include <algorithm>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           0 : PT11Field::PT11Field() : useASS(true), useBSS(false), useHalo(true) {
-       9             :         // disk parameters
-      10           0 :         d = - 0.6 * kpc;
-      11           0 :         R_sun = 8.5 * kpc;
-      12           0 :         R_c = 5.0 * kpc;
-      13           0 :         z0_D = 1.0 * kpc;
-      14           0 :         B0_D = 2.0 * muG;
-      15             : 
-      16             :         // halo parameters
-      17           0 :         z0_H = 1.3 * kpc;
-      18           0 :         R0_H = 8.0 * kpc;
-      19           0 :         B0_Hn = 4.0 * muG;
-      20           0 :         B0_Hs = 4.0 * muG;
-      21           0 :         z11_H = 0.25 * kpc;
-      22           0 :         z12_H = 0.4 * kpc;
-      23             : 
-      24             :         // set ASS specific parameters
-      25           0 :         setUseASS(true);
-      26           0 : }
-      27             : 
-      28           0 : void PT11Field::SetParams() {
-      29           0 :         cos_pitch = cos(pitch);
-      30           0 :         sin_pitch = sin(pitch);
-      31           0 :         PHI = cos_pitch / sin_pitch * log1p(d / R_sun) - M_PI / 2;
-      32           0 :         cos_PHI = cos(PHI);
-      33           0 : }
-      34             : 
-      35           0 : void PT11Field::setUseASS(bool use) {
-      36           0 :         useASS = use;
-      37           0 :         if (not(use))
-      38             :                 return;
-      39             : 
-      40           0 :         if (useBSS) {
-      41             :                 std::cout << "PT11Field: Disk field changed to ASS" << std::endl;
-      42           0 :                 useBSS = false;
-      43             :         }
-      44             : 
-      45           0 :         pitch = -5.0 * M_PI / 180;
-      46           0 :         B0_Hs = 2.0 * muG;
-      47           0 :         SetParams();
-      48             : }
-      49             : 
-      50           0 : void PT11Field::setUseBSS(bool use) {
-      51           0 :         useBSS = use;
-      52           0 :         if (not(use))
-      53             :                 return;
-      54             : 
-      55           0 :         if (useASS) {
-      56             :                 std::cout << "PT11Field: Disk field changed to BSS" << std::endl;
-      57           0 :                 useASS = false;
-      58             :         }
-      59             : 
-      60           0 :         pitch = -6.0 * M_PI / 180;
-      61           0 :         B0_Hs = 4.0 * muG;
-      62           0 :         SetParams();
-      63             : }
-      64             : 
-      65           0 : void PT11Field::setUseHalo(bool use) {
-      66           0 :         useHalo = use;
-      67           0 : }
-      68             : 
-      69           0 : bool PT11Field::isUsingASS() {
-      70           0 :         return useASS;
-      71             : }
-      72             : 
-      73           0 : bool PT11Field::isUsingBSS() {
-      74           0 :         return useBSS;
-      75             : }
-      76             : 
-      77           0 : bool PT11Field::isUsingHalo() {
-      78           0 :         return useHalo;
-      79             : }
-      80             : 
-      81           0 : Vector3d PT11Field::getField(const Vector3d& pos) const {
-      82           0 :         double r = sqrt(pos.x * pos.x + pos.y * pos.y);  // in-plane radius
-      83             : 
-      84             :         Vector3d b(0.);
-      85             : 
-      86             :         // disk field
-      87           0 :         if ((useASS) or (useBSS)) {
-      88             :                 // PT11 paper has B_theta = B * cos(p) but this seems because they define azimuth clockwise, while we have anticlockwise.
-      89             :                 // see Tinyakov 2002 APh 18,165: "local field points to l=90+p" so p=-5 deg gives l=85 and hence clockwise from above.
-      90             :                 // so to get local B clockwise in our system, need minus (like Sun etal).
-      91             :                 // Ps base their system on Han and Qiao 1994 A&A 288,759 which has a diagram with azimuth clockwise, hence confirmed.
-      92             : 
-      93             :                 // PT11 paper define Earth position at (+8.5, 0, 0) kpc; but usual convention is (-8.5, 0, 0)
-      94             :                 // thus we have to rotate our position by 180 degree in azimuth
-      95           0 :                 double theta = M_PI - pos.getPhi();  // azimuth angle theta: PT11 paper uses opposite convention for azimuth
-      96             :                 // the following is equivalent to sin(pi - phi) and cos(pi - phi) which is computationally slower
-      97           0 :                 double cos_theta = - pos.x / r;
-      98           0 :                 double sin_theta = pos.y / r;
-      99             : 
-     100             :                 // After some geometry calculations (on whiteboard) one finds:
-     101             :                 // Bx = +cos(theta) * B_r - sin(theta) * B_{theta}
-     102             :                 // By = -sin(theta) * B_r - cos(theta) * B_{theta}
-     103             :                 // Use from paper: B_theta = B * cos(pitch)     and B_r = B * sin(pitch)
-     104           0 :                 b.x = sin_pitch * cos_theta - cos_pitch * sin_theta;
-     105           0 :                 b.y = - sin_pitch * sin_theta - cos_pitch * cos_theta;
-     106             :                 b *= -1;        // flip magnetic field direction, as B_{theta} and B_{phi} refering to 180 degree rotated field
-     107             : 
-     108           0 :                 double bMag = cos(theta - cos_pitch / sin_pitch * log(r / R_sun) + PHI);
-     109           0 :                 if (useASS)
-     110           0 :                         bMag = fabs(bMag);
-     111           0 :                 bMag *= B0_D * R_sun / std::max(r, R_c) / cos_PHI * exp(-fabs(pos.z) / z0_D);
-     112             :                 b *= bMag;
-     113             :         }
-     114             : 
-     115             :         // halo field
-     116           0 :         if (useHalo) {
-     117           0 :                 double bMag = (pos.z > 0 ? B0_Hn : - B0_Hs);
-     118           0 :                 double z1 = (fabs(pos.z) < z0_H ? z11_H : z12_H);
-     119           0 :                 bMag *= r / R0_H * exp(1 - r / R0_H) / (1 + pow((fabs(pos.z) - z0_H) / z1, 2.));
-     120             :                 // equation (8) in paper: theta uses now the conventional azimuth definition in contrast to equation (3)
-     121             :                 // cos(phi) = pos.x / r (phi going counter-clockwise)
-     122             :                 // sin(phi) = pos.y / r
-     123             :                 // unitvector of phi in polar coordinates: (-sin(phi), cos(phi), 0)
-     124           0 :                 b += bMag * Vector3d(-pos.y / r, pos.x / r, 0);
-     125             :         }
-     126             : 
-     127           0 :         return b;
-     128             : }
-     129             : 
-     130             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html deleted file mode 100644 index aa48a3251..000000000 --- a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/PolarizedSingleModeMagneticField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - PolarizedSingleModeMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:153246.9 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa32PolarizedSingleModeMagneticFieldC2ERKdS2_S2_RKNS_7Vector3IdEES6_S6_NSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESC_SC_1
_ZNK7crpropa32PolarizedSingleModeMagneticField8getFieldERKNS_7Vector3IdEE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html deleted file mode 100644 index 85b986750..000000000 --- a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/PolarizedSingleModeMagneticField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - PolarizedSingleModeMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:153246.9 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa32PolarizedSingleModeMagneticFieldC2ERKdS2_S2_RKNS_7Vector3IdEES6_S6_NSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEESC_SC_1
_ZNK7crpropa32PolarizedSingleModeMagneticField8getFieldERKNS_7Vector3IdEE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html b/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html deleted file mode 100644 index 9ac25d10b..000000000 --- a/doc/coverageReport/src/magneticField/PolarizedSingleModeMagneticField.cpp.gcov.html +++ /dev/null @@ -1,142 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/PolarizedSingleModeMagneticField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - PolarizedSingleModeMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:153246.9 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/PolarizedSingleModeMagneticField.h"
-       2             : 
-       3             : namespace crpropa {
-       4             : 
-       5           1 : PolarizedSingleModeMagneticField::PolarizedSingleModeMagneticField( const double &B_0, const double &wavelength, const double &sigma, const Vector3d &r_0, const Vector3d &e_1, const Vector3d &e_2, std::string flagAmplitudeRms, std::string flagPolarizationHelicity, std::string flagMode ) {
-       6           1 :         if (flagMode == "elliptical") {
-       7           1 :                 if (abs(sigma) > 1)
-       8           0 :                         throw std::runtime_error("PolarizedSingleModeMagneticField: The value of the  polarization parameter has to lie in the range [-1;+1].");
-       9             :         }
-      10           0 :         else if (flagMode == "circular") {
-      11           0 :                 if (abs(sigma) != 1)
-      12           0 :                         throw std::runtime_error("PolarizedSingleModeMagneticField: For circular polarization the value of the polarization parameter has to be equal to -1 or +1.");
-      13             :         }
-      14           0 :         else if (flagMode == "linear") {
-      15           0 :                 if (abs(sigma) != 0)
-      16           0 :                         throw std::runtime_error("PolarizedSingleModeMagneticField: For linear polarization the value of the polarization parameter has to be equal to 0.");
-      17             :         }
-      18             :         else
-      19           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Wrong value for flagMode. Please choose \"elliptical\" or \"circular\" or \"linear\".");
-      20             : 
-      21           1 :         if (e_1.dot(e_2) != 0)
-      22           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: e_1 and e_2 have to be orthogonal to each other.");
-      23             : 
-      24           1 :         if (e_1.getR() == 0)
-      25           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Vector e_1 cannot be zero.");
-      26             :         unitVector_1 = e_1 / e_1.getR();
-      27             : 
-      28           1 :         if (e_2.getR() == 0)
-      29           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Vector e_2 cannot be zero.");
-      30             :         unitVector_2 = e_2 / e_2.getR();
-      31             : 
-      32             :         wavevector = e_2.cross(e_1);
-      33             : 
-      34             :         //This check is necessary if a polarization with non-orthogonal spanning vectors is desired. This is not implemented in this version, so any corresponding modifications should be made with caution.
-      35             :         //if (wavevector.getR() == 0)
-      36             :         //        throw std::runtime_error("PolarizedSingleModeMagneticField: e_1 cannot be parallel to e_2.");
-      37             : 
-      38             :         wavevector = wavevector / wavevector.getR();
-      39             : 
-      40           1 :         if (wavelength == 0)
-      41           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: The correlation length cannot be zero.");
-      42             :         wavevector = wavevector * 2 * M_PI / wavelength;
-      43             : 
-      44           2 :         if (!((flagPolarizationHelicity == "helicity") || (flagPolarizationHelicity == "polarization")))
-      45           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Wrong value for flagPolarizationHelicity. Please choose \"polarization\" or \"helicity\".");
-      46           1 :         if (flagPolarizationHelicity == "helicity" && abs(sigma) != 1)
-      47           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: In helicity mode only the maximum helicity case (sigma = +1 or sigma = -1) may be chosen.");
-      48             : 
-      49           1 :         if (flagAmplitudeRms == "amplitude")
-      50           1 :                 B_max = B_0;
-      51           0 :         else if (flagAmplitudeRms == "rms")
-      52           0 :                 B_max = sqrt(2 / (1 + sigma * sigma)) * B_0;
-      53             :         else
-      54           0 :                 throw std::runtime_error("PolarizedSingleModeMagneticField: Wrong value for flagAmplitudeRms. Please choose \"amplitude\" or \"rms\".");
-      55             : 
-      56             :         this->r_0 = r_0;
-      57           1 :         this->sigma = sigma;
-      58           1 : }
-      59             : 
-      60           1 : Vector3d PolarizedSingleModeMagneticField::getField(const Vector3d &position) const {
-      61             :         Vector3d delta_r = position - r_0;
-      62             : 
-      63           1 :         return B_max * (unitVector_1 * cos(wavevector.dot(delta_r)) + unitVector_2 * sigma * sin(wavevector.dot(delta_r)));
-      64             : }
-      65             : 
-      66             : } //end namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html deleted file mode 100644 index dbd5a2431..000000000 --- a/doc/coverageReport/src/magneticField/TF17Field.cpp.func-sort-c.html +++ /dev/null @@ -1,188 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/TF17Field.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - TF17Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01960.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9TF17Field10set_H_diskEd0
_ZN7crpropa9TF17Field10set_L_diskEd0
_ZN7crpropa9TF17Field10set_L_haloEd0
_ZN7crpropa9TF17Field10set_a_diskEd0
_ZN7crpropa9TF17Field10set_a_haloEd0
_ZN7crpropa9TF17Field11set_B1_diskEd0
_ZN7crpropa9TF17Field11set_B1_haloEd0
_ZN7crpropa9TF17Field11set_r1_diskEd0
_ZN7crpropa9TF17Field11set_z1_diskEd0
_ZN7crpropa9TF17Field11set_z1_haloEd0
_ZN7crpropa9TF17Field15setUseDiskFieldEb0
_ZN7crpropa9TF17Field15setUseHaloFieldEb0
_ZN7crpropa9TF17Field16isUsingDiskFieldEv0
_ZN7crpropa9TF17Field16isUsingHaloFieldEv0
_ZN7crpropa9TF17Field17set_phi_star_diskEd0
_ZN7crpropa9TF17Field17set_phi_star_haloEd0
_ZN7crpropa9TF17Field6set_HpEd0
_ZN7crpropa9TF17Field6set_LpEd0
_ZN7crpropa9TF17Field6set_p0Ed0
_ZN7crpropa9TF17FieldC2ENS_13TF17DiskModelENS_13TF17HaloModelE0
_ZNK7crpropa9TF17Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getDiskModelB5cxx11Ev0
_ZNK7crpropa9TF17Field12getHaloFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getHaloModelB5cxx11Ev0
_ZNK7crpropa9TF17Field16radialFieldScaleERKdS2_S2_S2_S2_S2_0
_ZNK7crpropa9TF17Field22shiftedWindingFunctionERKdS2_0
_ZNK7crpropa9TF17Field23azimuthalFieldComponentERKdS2_S2_S2_0
_ZNK7crpropa9TF17Field6zscaleERKd0
_ZNK7crpropa9TF17Field8getFieldERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/TF17Field.cpp.func.html b/doc/coverageReport/src/magneticField/TF17Field.cpp.func.html deleted file mode 100644 index 4c39636c6..000000000 --- a/doc/coverageReport/src/magneticField/TF17Field.cpp.func.html +++ /dev/null @@ -1,188 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/TF17Field.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - TF17Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01960.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9TF17Field10set_H_diskEd0
_ZN7crpropa9TF17Field10set_L_diskEd0
_ZN7crpropa9TF17Field10set_L_haloEd0
_ZN7crpropa9TF17Field10set_a_diskEd0
_ZN7crpropa9TF17Field10set_a_haloEd0
_ZN7crpropa9TF17Field11set_B1_diskEd0
_ZN7crpropa9TF17Field11set_B1_haloEd0
_ZN7crpropa9TF17Field11set_r1_diskEd0
_ZN7crpropa9TF17Field11set_z1_diskEd0
_ZN7crpropa9TF17Field11set_z1_haloEd0
_ZN7crpropa9TF17Field15setUseDiskFieldEb0
_ZN7crpropa9TF17Field15setUseHaloFieldEb0
_ZN7crpropa9TF17Field16isUsingDiskFieldEv0
_ZN7crpropa9TF17Field16isUsingHaloFieldEv0
_ZN7crpropa9TF17Field17set_phi_star_diskEd0
_ZN7crpropa9TF17Field17set_phi_star_haloEd0
_ZN7crpropa9TF17Field6set_HpEd0
_ZN7crpropa9TF17Field6set_LpEd0
_ZN7crpropa9TF17Field6set_p0Ed0
_ZN7crpropa9TF17FieldC2ENS_13TF17DiskModelENS_13TF17HaloModelE0
_ZNK7crpropa9TF17Field12getDiskFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getDiskModelB5cxx11Ev0
_ZNK7crpropa9TF17Field12getHaloFieldERKdS2_S2_S2_S2_0
_ZNK7crpropa9TF17Field12getHaloModelB5cxx11Ev0
_ZNK7crpropa9TF17Field16radialFieldScaleERKdS2_S2_S2_S2_S2_0
_ZNK7crpropa9TF17Field22shiftedWindingFunctionERKdS2_0
_ZNK7crpropa9TF17Field23azimuthalFieldComponentERKdS2_S2_S2_0
_ZNK7crpropa9TF17Field6zscaleERKd0
_ZNK7crpropa9TF17Field8getFieldERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html b/doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html deleted file mode 100644 index b277961c9..000000000 --- a/doc/coverageReport/src/magneticField/TF17Field.cpp.gcov.html +++ /dev/null @@ -1,383 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/TF17Field.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField - TF17Field.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:01960.0 %
Date:2024-04-08 14:58:22Functions:0290.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/TF17Field.h"
-       2             : #include "crpropa/Units.h"
-       3             : 
-       4             : #include <algorithm>
-       5             : #include <string>
-       6             : 
-       7             : namespace crpropa {
-       8             : using namespace std;
-       9             : 
-      10           0 : TF17Field::TF17Field(TF17DiskModel disk_model_, TF17HaloModel halo_model_) {
-      11           0 :     disk_model = disk_model_; 
-      12           0 :     halo_model = halo_model_;
-      13             : 
-      14           0 :     useHaloField = true;
-      15           0 :     useDiskField = true;
-      16             : 
-      17           0 :     if ((halo_model == TF17HaloModel::C0) && (disk_model == TF17DiskModel::Ad1)) {
-      18             :         // disk parameters
-      19           0 :         set_r1_disk(3 * kpc);
-      20           0 :         set_B1_disk(19.0 * muG);
-      21           0 :         set_H_disk(0.055 * kpc);
-      22           0 :         set_phi_star_disk(-54 * M_PI / 180);
-      23           0 :         set_a_disk(0.9 / kpc / kpc);
-      24             :         // halo parameters
-      25           0 :         set_z1_halo(0);
-      26           0 :         set_B1_halo(0.36 * muG);
-      27           0 :         set_L_halo(3.0 * kpc);
-      28           0 :         set_a_halo(1.17 / kpc / kpc);
-      29             :         // shared parameters
-      30           0 :         set_p0(-7.9 * M_PI / 180);
-      31           0 :         set_Hp(5 * kpc);
-      32           0 :         set_Lp(50 * kpc); // > 18 kpc
-      33             :             
-      34           0 :     } else if ((halo_model == TF17HaloModel::C0) && (disk_model == TF17DiskModel::Bd1)) {
-      35             :         // disk parameters
-      36           0 :         set_r1_disk(3 * kpc);
-      37           0 :         set_B1_disk(2.0 * muG);
-      38           0 :         set_H_disk(0.32 * kpc);
-      39           0 :         set_phi_star_disk(153 * M_PI / 180);
-      40             :         // halo parameters
-      41           0 :         set_z1_halo(0);
-      42           0 :         set_B1_halo(0.29 * muG);
-      43           0 :         set_L_halo(3.4 * kpc);
-      44           0 :         set_a_halo(0.88 / kpc / kpc);
-      45             :         // shared parameters
-      46           0 :         set_p0(-7.2 * M_PI / 180);
-      47           0 :         set_Hp(9 * kpc);
-      48           0 :         set_Lp(50 * kpc); // > 16 kpc
-      49             : 
-      50           0 :     } else if ((halo_model == TF17HaloModel::C0) && (disk_model == TF17DiskModel::Dd1)) {
-      51             :         // disk parameters
-      52           0 :         set_z1_disk(1.5 * kpc);
-      53           0 :         set_B1_disk(0.065 * muG);
-      54           0 :         set_L_disk(9.8 * kpc);
-      55           0 :         set_phi_star_disk(14 * M_PI / 180);
-      56             :         // halo parameters
-      57           0 :         set_z1_halo(0);
-      58           0 :         set_B1_halo(0.18 * muG);
-      59           0 :         set_L_halo(4.8 * kpc);
-      60           0 :         set_a_halo(0.61 / kpc / kpc);
-      61             :         // shared parameters
-      62           0 :         set_p0(-7.4 * M_PI / 180);
-      63           0 :         set_Hp(4.2 * kpc);
-      64           0 :         set_Lp(50 * kpc); // > 22 kpc
-      65             : 
-      66           0 :     } else if ((halo_model == TF17HaloModel::C1) && (disk_model == TF17DiskModel::Ad1)) {
-      67             :         // disk parameters
-      68           0 :         set_r1_disk(3 * kpc);
-      69           0 :         set_B1_disk(32.0 * muG);
-      70           0 :         set_H_disk(0.054 * kpc);
-      71           0 :         set_phi_star_disk(-31 * M_PI / 180);
-      72           0 :         set_a_disk(0.031 / kpc / kpc);
-      73             :         // halo parameters
-      74           0 :         set_z1_halo(0);
-      75           0 :         set_B1_halo(9.0 * muG);
-      76           0 :         set_L_halo(2.1 * kpc);
-      77           0 :         set_phi_star_halo(198 * M_PI / 180);
-      78           0 :         set_a_halo(0.33 / kpc / kpc);
-      79             :         // shared parameters
-      80           0 :         set_p0(-9.1 * M_PI / 180);
-      81           0 :         set_Hp(1.2 * kpc);
-      82           0 :         set_Lp(50 * kpc); // > 38 kpc
-      83             : 
-      84           0 :     } else if ((halo_model == TF17HaloModel::C1) && (disk_model == TF17DiskModel::Bd1)) {
-      85             :         // disk parameters
-      86           0 :         set_r1_disk(3 * kpc);
-      87           0 :         set_B1_disk(24 * muG);
-      88           0 :         set_H_disk(0.090 * kpc);
-      89           0 :         set_phi_star_disk(-34 * M_PI / 180);
-      90             :         // halo parameters
-      91           0 :         set_z1_halo(0);
-      92           0 :         set_B1_halo(8.2 * muG);
-      93           0 :         set_L_halo(2.2 * kpc);
-      94           0 :         set_phi_star_halo(197 * M_PI / 180);
-      95           0 :         set_a_halo(0.38 / kpc / kpc);
-      96             :         // shared parameters
-      97           0 :         set_p0(-9.0 * M_PI / 180);
-      98           0 :         set_Hp(1.2 * kpc);
-      99           0 :         set_Lp(50 * kpc); // > 38 kpc
-     100             : 
-     101           0 :     } else if ((halo_model == TF17HaloModel::C1) && (disk_model == TF17DiskModel::Dd1)) {
-     102             :         // disk parameters
-     103           0 :         set_z1_disk(1.5 * kpc);
-     104           0 :         set_B1_disk(0.40 * muG);
-     105           0 :         set_L_disk(2.9 * kpc);
-     106           0 :         set_phi_star_disk(120 * M_PI / 180);
-     107             :         // halo parameters
-     108           0 :         set_z1_halo(0);
-     109           0 :         set_B1_halo(9.5 * muG);
-     110           0 :         set_L_halo(2.1 * kpc);
-     111           0 :         set_phi_star_halo(179 * M_PI / 180);
-     112           0 :         set_a_halo(0.45 / kpc / kpc);
-     113             :         // shared parameters
-     114           0 :         set_p0(-8.4 * M_PI / 180);
-     115           0 :         set_Hp(1.2 * kpc);
-     116           0 :         set_Lp(50 * kpc); // > 30 kpc
-     117             :     }
-     118             : 
-     119           0 :     epsilon = std::numeric_limits<double>::epsilon();
-     120           0 : }
-     121             : 
-     122           0 : void TF17Field::setUseDiskField(bool use) {     useDiskField = use; }
-     123           0 : void TF17Field::setUseHaloField(bool use) { useHaloField = use; }
-     124             : 
-     125           0 : bool TF17Field::isUsingDiskField() { return useDiskField; }
-     126           0 : bool TF17Field::isUsingHaloField() { return useHaloField; }
-     127             : 
-     128           0 : void TF17Field::set_B1_disk(const double B1){ B1_disk = B1; }
-     129           0 : void TF17Field::set_z1_disk(const double z1){ z1_disk = z1; }
-     130           0 : void TF17Field::set_r1_disk(const double r1){ r1_disk = r1; }
-     131           0 : void TF17Field::set_H_disk(const double H){ H_disk = H; }
-     132           0 : void TF17Field::set_L_disk(const double L){ L_disk = L; }
-     133           0 : void TF17Field::set_a_disk(const double a){ a_disk = a; }
-     134           0 : void TF17Field::set_phi_star_disk(const double phi){ phi_star_disk = phi; }
-     135             : 
-     136           0 : void TF17Field::set_B1_halo(const double B1){ B1_halo = B1; }
-     137           0 : void TF17Field::set_z1_halo(const double z1){ z1_halo = z1; }
-     138           0 : void TF17Field::set_L_halo(const double L){ L_halo = L; }
-     139           0 : void TF17Field::set_a_halo(const double a){ a_halo = a; }
-     140           0 : void TF17Field::set_phi_star_halo(const double phi){ phi_star_halo = phi; }
-     141             : 
-     142           0 : void TF17Field::set_Hp(const double H){ H_p = H; }
-     143           0 : void TF17Field::set_Lp(const double L){ L_p = L; }
-     144           0 : void TF17Field::set_p0(const double p0){ 
-     145           0 :     p_0 = p0; 
-     146           0 :     cot_p0 = cos(p_0) / sin(p_0);
-     147           0 : }
-     148             : 
-     149           0 : string TF17Field::getDiskModel() const {
-     150             :     string model_name;
-     151           0 :     switch (disk_model) {
-     152             :         case TF17DiskModel::Ad1 : model_name = "Ad1"; break;
-     153             :         case TF17DiskModel::Bd1 : model_name = "Bd1"; break;
-     154             :         case TF17DiskModel::Dd1 : model_name = "Dd1"; break;
-     155             :     }
-     156           0 :     return model_name;
-     157             : }
-     158           0 : string TF17Field::getHaloModel() const {
-     159             :     string model_name;
-     160           0 :     switch (halo_model) {
-     161             :         case TF17HaloModel::C0 : model_name = "C0"; break;
-     162             :         case TF17HaloModel::C1 : model_name = "C1"; break;
-     163             :     }
-     164           0 :     return model_name;
-     165             : }
-     166             : 
-     167             : 
-     168           0 : Vector3d TF17Field::getField(const Vector3d& pos) const {
-     169           0 :         double r = sqrt(pos.x * pos.x + pos.y * pos.y);  // in-plane radius
-     170           0 :         double phi = M_PI - pos.getPhi(); // azimuth in our convention
-     171             :         // double cosPhi = pos.x / r;
-     172           0 :         double cosPhi = cos(phi);
-     173             :         // double sinPhi = pos.y / r;
-     174           0 :         double sinPhi = sin(phi);
-     175             : 
-     176             :         Vector3d b(0.);
-     177           0 :         if (useDiskField)
-     178           0 :                 b += getDiskField(r, pos.z, phi, sinPhi, cosPhi);       // disk field
-     179           0 :         if (useHaloField)
-     180           0 :                 b += getHaloField(r, pos.z, phi, sinPhi, cosPhi);       // halo field
-     181           0 :         return b;
-     182             : }
-     183             : 
-     184           0 : Vector3d TF17Field::getDiskField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
-     185             :         Vector3d b(0.);
-     186           0 :     double B_r = 0;
-     187             :     double B_phi = 0;
-     188           0 :     double B_z = 0;
-     189             : 
-     190           0 :     if (disk_model == TF17DiskModel::Ad1) { // ==========================================================
-     191           0 :         if (r > r1_disk) {
-     192           0 :             double z1_disk_z = (1. + a_disk * r1_disk * r1_disk) / (1. + a_disk * r * r); // z1_disk / z
-     193             :             // B components in (r, phi, z)
-     194           0 :             double B_r0 = radialFieldScale(B1_disk, phi_star_disk, z1_disk_z*z, phi, r, z);
-     195           0 :             B_r = (r1_disk / r) * z1_disk_z * B_r0;
-     196           0 :             B_z = 2 * a_disk * r1_disk * z1_disk_z*z / (1+ a_disk * r * r) * B_r0;
-     197           0 :             B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
-     198             :         } else {
-     199             :             // within r = r1_disk, the field lines are straight in direction g_phi + phi_star_disk
-     200             :             // and thus z = z1
-     201           0 :             double phi1_disk = shiftedWindingFunction(r1_disk, z) + phi_star_disk;
-     202           0 :             double B_amp = B1_disk * exp(-fabs(z) / H_disk);
-     203           0 :             B_r = cos(phi1_disk - phi) * B_amp;
-     204           0 :             B_phi = sin(phi1_disk - phi) * B_amp;
-     205             :         }
-     206             : 
-     207           0 :     } else if (disk_model == TF17DiskModel::Bd1) { // ===================================================
-     208             :         // for model Bd1, best fit for n = 2 
-     209           0 :         if ( r > epsilon ) {
-     210           0 :             double r1_disk_r = r1_disk / r;     
-     211           0 :             double z1_disk_z = 5. / (r1_disk_r*r1_disk_r + 4./sqrt(r1_disk_r)); // z1_disk / z -> remove z dependancy 
-     212           0 :             double B_r0 = radialFieldScale(B1_disk, phi_star_disk, z1_disk_z*z, phi, r, z);
-     213           0 :             B_r = r1_disk_r * z1_disk_z * B_r0;
-     214           0 :             B_z = -0.4 * r1_disk_r / r * z1_disk_z* z1_disk_z * z * (r1_disk_r*r1_disk_r - 1./sqrt(r1_disk_r)) * B_r0;
-     215             :         } else {
-     216           0 :             double z1_disk_z = 5. * r*r / (r1_disk*r1_disk); // z1_disk / z -> remove z dependancy 
-     217           0 :             double B_r0 = radialFieldScale(B1_disk, phi_star_disk, z1_disk_z*z, phi, r, z);
-     218           0 :             B_r = 5. * r / r1_disk * B_r0;
-     219           0 :             B_z = -10. * z / r1_disk * B_r0;
-     220             :         }
-     221           0 :         B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
-     222             : 
-     223           0 :     } else if (disk_model == TF17DiskModel::Dd1) { // ===================================================
-     224             :         // for model Dd1, best fit for n = 0.5 
-     225           0 :         double z_sign = z >= 0 ? 1. : -1.; 
-     226           0 :         double z_abs = fabs(z); 
-     227           0 :         if ( z_abs > epsilon ) {
-     228           0 :             double z1_disk_z = z1_disk / z_abs; 
-     229           0 :             double r1_disk_r = 1.5 / (sqrt(z1_disk_z) + 0.5/z1_disk_z); // r1_disk / r
-     230           0 :             double F_r = r1_disk_r*r  <= L_disk ? 1. : exp(1. - r1_disk_r*r/L_disk);
-     231             :         // simplication of the equation in the cosinus
-     232           0 :             double B_z0 = z_sign * B1_disk * F_r * cos(phi - shiftedWindingFunction(r, z) - phi_star_disk);
-     233           0 :             B_r = -0.5/1.5 * r1_disk_r * r1_disk_r * r1_disk_r * r / z_abs * (sqrt(z1_disk_z) - 1/z1_disk_z) * B_z0;
-     234           0 :             B_z = z_sign * r1_disk_r * r1_disk_r * B_z0;
-     235             :         } else {
-     236           0 :             double z_z1_disk = z_abs / z1_disk; 
-     237           0 :             double r1_disk_r = 1.5 * sqrt(z_abs / z1_disk); // r1_disk / r
-     238           0 :             double F_r = r1_disk_r*r  <= L_disk ? 1. : exp(1. - r1_disk_r*r/L_disk);
-     239           0 :             double B_z0 = z_sign * B1_disk * F_r * cos(phi - shiftedWindingFunction(r, z) - phi_star_disk);
-     240           0 :             B_r = -1.125 * r / z1_disk * (1 - 2.5 * z_z1_disk * sqrt(z_z1_disk)) * B_z0;
-     241           0 :             B_z = z_sign * r1_disk_r * r1_disk_r * B_z0;
-     242             :         }
-     243           0 :         B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
-     244             :     }
-     245             : 
-     246             :     // Convert to (x, y, z) components
-     247           0 :     b.x = - (B_r * cosPhi - B_phi * sinPhi); // flip x-component at the end
-     248           0 :     b.y = B_r * sinPhi + B_phi * cosPhi;
-     249           0 :     b.z = B_z;
-     250           0 :         return b;
-     251             : }
-     252             : 
-     253           0 : Vector3d TF17Field::getHaloField(const double& r, const double& z, const double& phi, const double& sinPhi, const double& cosPhi) const {
-     254             :     int m;
-     255             : 
-     256             :         Vector3d b(0.);
-     257           0 :         double r1_halo_r =  (1. + a_halo * z1_halo * z1_halo) / (1. + a_halo * z * z);
-     258             :         // B components in (r, phi, z)
-     259             :     double B_z0;
-     260             : 
-     261           0 :     if (halo_model == TF17HaloModel::C0) { // m = 0
-     262           0 :         B_z0 = B1_halo * exp(-r1_halo_r*r / L_halo); 
-     263           0 :     } else if (halo_model == TF17HaloModel::C1) { // m = 1
-     264             :         // simplication of the equation in the cosinus
-     265           0 :         double phi_prime = phi - shiftedWindingFunction(r, z) - phi_star_halo;
-     266           0 :         B_z0 = B1_halo * exp(-r1_halo_r*r / L_halo) * cos(phi_prime); 
-     267             :     }
-     268             : 
-     269             :     // Contrary to article, Br has been rewriten to a little bit by replacing
-     270             :     // (2 * a * r1**3 * z) / (r**2) by (2 * a * r1**2 * z) / (r * (1+a*z**2))
-     271             :     // but that is strictly equivalent except we can reintroduce the z1 in the expression via r1
-     272           0 :         double B_r = 2 * a_halo * r1_halo_r * r1_halo_r * r * z / (1. + a_halo * z * z) * B_z0;
-     273           0 :         double B_z = r1_halo_r * r1_halo_r * B_z0; 
-     274           0 :         double B_phi = azimuthalFieldComponent(r, z, B_r, B_z);
-     275             : 
-     276             :         // Convert to (x, y, z) components
-     277           0 :         b.x = - (B_r * cosPhi - B_phi * sinPhi);        // flip x-component at the end
-     278           0 :         b.y = B_r * sinPhi + B_phi * cosPhi;
-     279           0 :         b.z = B_z;
-     280             : 
-     281           0 :         return b;
-     282             : }
-     283             : 
-     284           0 : double TF17Field::azimuthalFieldComponent(const double& r, const double& z, const double& B_r, const double& B_z) const {
-     285           0 :         double r_ = r / L_p;
-     286           0 :     double rscale = r > epsilon ? r_ * exp(-r_) / (1 - exp(-r_)) : 1 - r_/2. - r_*r_/12. ;
-     287           0 :         double B_phi = cot_p0 / zscale(z) * rscale * B_r;
-     288           0 :     B_phi = B_phi - 2 * z * r / (H_p * H_p) / zscale(z) * shiftedWindingFunction(r, z) * B_z;
-     289           0 :         return B_phi;
-     290             : }
-     291             : 
-     292           0 : double TF17Field::radialFieldScale(const double& B1, const double& phi_star, const double& z1, const double& phi, const double& r, const double& z) const {
-     293             :     // simplication of the equation in the cosinus
-     294           0 :     double phi_prime = phi - shiftedWindingFunction(r, z) - phi_star;
-     295             :         // This term occures is parameterizations of models A and B always bisymmetric (m = 1)
-     296           0 :         return B1 * exp(-fabs(z1) / H_disk) * cos(phi_prime);
-     297             : }
-     298             : 
-     299           0 : double TF17Field::shiftedWindingFunction(const double& r, const double& z) const {
-     300           0 :     return cot_p0 * log(1 - exp(-r / L_p) + epsilon) / zscale(z);
-     301             : }
-     302             : 
-     303           0 : double TF17Field::zscale(const double& z) const {
-     304           0 :         return 1 + z * z / H_p / H_p;
-     305             : }
-     306             : 
-     307             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/index-sort-f.html b/doc/coverageReport/src/magneticField/index-sort-f.html deleted file mode 100644 index e6f4aee3b..000000000 --- a/doc/coverageReport/src/magneticField/index-sort-f.html +++ /dev/null @@ -1,173 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:16691018.2 %
Date:2024-04-08 14:58:22Functions:2913821.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
PT11Field.cpp -
0.0%
-
0.0 %0 / 630.0 %0 / 9
ArchimedeanSpiralField.cpp -
0.0%
-
0.0 %0 / 420.0 %0 / 10
MagneticFieldGrid.cpp -
0.0%
-
0.0 %0 / 310.0 %0 / 11
JF12FieldSolenoidal.cpp -
0.0%
-
0.0 %0 / 1420.0 %0 / 14
TF17Field.cpp -
0.0%
-
0.0 %0 / 1960.0 %0 / 29
JF12Field.cpp -
0.0%
-
0.0 %0 / 2310.0 %0 / 29
MagneticField.cpp -
72.7%72.7%
-
72.7 %48 / 6656.2 %9 / 16
PolarizedSingleModeMagneticField.cpp -
46.9%46.9%
-
46.9 %15 / 32100.0 %2 / 2
CMZField.cpp -
96.3%96.3%
-
96.3 %103 / 107100.0 %18 / 18
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/index-sort-l.html b/doc/coverageReport/src/magneticField/index-sort-l.html deleted file mode 100644 index 2650220e6..000000000 --- a/doc/coverageReport/src/magneticField/index-sort-l.html +++ /dev/null @@ -1,173 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:16691018.2 %
Date:2024-04-08 14:58:22Functions:2913821.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticFieldGrid.cpp -
0.0%
-
0.0 %0 / 310.0 %0 / 11
ArchimedeanSpiralField.cpp -
0.0%
-
0.0 %0 / 420.0 %0 / 10
PT11Field.cpp -
0.0%
-
0.0 %0 / 630.0 %0 / 9
JF12FieldSolenoidal.cpp -
0.0%
-
0.0 %0 / 1420.0 %0 / 14
TF17Field.cpp -
0.0%
-
0.0 %0 / 1960.0 %0 / 29
JF12Field.cpp -
0.0%
-
0.0 %0 / 2310.0 %0 / 29
PolarizedSingleModeMagneticField.cpp -
46.9%46.9%
-
46.9 %15 / 32100.0 %2 / 2
MagneticField.cpp -
72.7%72.7%
-
72.7 %48 / 6656.2 %9 / 16
CMZField.cpp -
96.3%96.3%
-
96.3 %103 / 107100.0 %18 / 18
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/index.html b/doc/coverageReport/src/magneticField/index.html deleted file mode 100644 index e4d6a01d2..000000000 --- a/doc/coverageReport/src/magneticField/index.html +++ /dev/null @@ -1,173 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticFieldHitTotalCoverage
Test:coverage.info.cleanedLines:16691018.2 %
Date:2024-04-08 14:58:22Functions:2913821.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ArchimedeanSpiralField.cpp -
0.0%
-
0.0 %0 / 420.0 %0 / 10
CMZField.cpp -
96.3%96.3%
-
96.3 %103 / 107100.0 %18 / 18
JF12Field.cpp -
0.0%
-
0.0 %0 / 2310.0 %0 / 29
JF12FieldSolenoidal.cpp -
0.0%
-
0.0 %0 / 1420.0 %0 / 14
MagneticField.cpp -
72.7%72.7%
-
72.7 %48 / 6656.2 %9 / 16
MagneticFieldGrid.cpp -
0.0%
-
0.0 %0 / 310.0 %0 / 11
PT11Field.cpp -
0.0%
-
0.0 %0 / 630.0 %0 / 9
PolarizedSingleModeMagneticField.cpp -
46.9%46.9%
-
46.9 %15 / 32100.0 %2 / 2
TF17Field.cpp -
0.0%
-
0.0 %0 / 1960.0 %0 / 29
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html deleted file mode 100644 index 166f69ed4..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/GridTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - GridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8910485.6 %
Date:2024-04-08 14:58:22Functions:71353.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa14GridTurbulence10dumpToFileENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa14GridTurbulence16getPowerSpectrumEv0
_ZNK7crpropa14GridTurbulence18getMeanFieldVectorEv0
_ZNK7crpropa14GridTurbulence19getRmsFieldStrengthEv0
_ZNK7crpropa14GridTurbulence20getMeanFieldStrengthEv0
_ZNK7crpropa14GridTurbulence26getRmsFieldStrengthPerAxisEv0
_ZNK7crpropa14GridTurbulence7getGridEv1
_ZNK7crpropa14GridTurbulence8getFieldERKNS_7Vector3IdEE4
_ZN7crpropa14GridTurbulence14initTurbulenceEv6
_ZN7crpropa14GridTurbulence8initGridERKNS_14GridPropertiesE6
_ZN7crpropa14GridTurbulenceC2ERKNS_18TurbulenceSpectrumERKNS_14GridPropertiesEj6
_ZN7crpropa14GridTurbulence24executeInverseFFTInplaceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEPA2_fS8_S8_10
_ZN7crpropa14GridTurbulence21checkGridRequirementsENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEdd13
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html deleted file mode 100644 index 59602c105..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/GridTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - GridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8910485.6 %
Date:2024-04-08 14:58:22Functions:71353.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14GridTurbulence14initTurbulenceEv6
_ZN7crpropa14GridTurbulence21checkGridRequirementsENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEdd13
_ZN7crpropa14GridTurbulence24executeInverseFFTInplaceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEPA2_fS8_S8_10
_ZN7crpropa14GridTurbulence8initGridERKNS_14GridPropertiesE6
_ZN7crpropa14GridTurbulenceC2ERKNS_18TurbulenceSpectrumERKNS_14GridPropertiesEj6
_ZNK7crpropa14GridTurbulence10dumpToFileENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa14GridTurbulence16getPowerSpectrumEv0
_ZNK7crpropa14GridTurbulence18getMeanFieldVectorEv0
_ZNK7crpropa14GridTurbulence19getRmsFieldStrengthEv0
_ZNK7crpropa14GridTurbulence20getMeanFieldStrengthEv0
_ZNK7crpropa14GridTurbulence26getRmsFieldStrengthPerAxisEv0
_ZNK7crpropa14GridTurbulence7getGridEv1
_ZNK7crpropa14GridTurbulence8getFieldERKNS_7Vector3IdEE4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html deleted file mode 100644 index fb8a58ac8..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/GridTurbulence.cpp.gcov.html +++ /dev/null @@ -1,289 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/GridTurbulence.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - GridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8910485.6 %
Date:2024-04-08 14:58:22Functions:71353.8 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/turbulentField/GridTurbulence.h"
-       2             : #include "crpropa/GridTools.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #ifdef CRPROPA_HAVE_FFTW3F
-       6             : 
-       7             : namespace crpropa {
-       8             : 
-       9             : 
-      10           6 : GridTurbulence::GridTurbulence(const TurbulenceSpectrum &spectrum,
-      11             :                                const GridProperties &gridProp,
-      12           6 :                                unsigned int seed)
-      13           6 :     : TurbulentField(spectrum), seed(seed) {
-      14           6 :         initGrid(gridProp);
-      15           6 :         checkGridRequirements(gridPtr, spectrum.getLmin(), spectrum.getLmax());
-      16           6 :         initTurbulence();
-      17           6 : }
-      18             : 
-      19           6 : void GridTurbulence::initGrid(const GridProperties &p) {
-      20           6 :         gridPtr = new Grid3f(p);
-      21           6 : }
-      22             : 
-      23           4 : Vector3d GridTurbulence::getField(const Vector3d &pos) const {
-      24           4 :         return gridPtr->interpolate(pos);
-      25             : }
-      26             : 
-      27           1 : const ref_ptr<Grid3f> &GridTurbulence::getGrid() const { return gridPtr; }
-      28             : 
-      29           6 : void GridTurbulence::initTurbulence() {
-      30             : 
-      31             :         Vector3d spacing = gridPtr->getSpacing();
-      32             :         size_t n = gridPtr->getNx(); // size of array
-      33           6 :         size_t n2 = (size_t)floor(n / 2) +
-      34             :                     1; // size array in z-direction in configuration space
-      35             : 
-      36             :         // arrays to hold the complex vector components of the B(k)-field
-      37             :         fftwf_complex *Bkx, *Bky, *Bkz;
-      38           6 :         Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      39           6 :         Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      40           6 :         Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      41             : 
-      42           6 :         Random random;
-      43           6 :         if (seed != 0)
-      44           4 :                 random.seed(seed); // use given seed
-      45             : 
-      46             :         // calculate the n possible discrete wave numbers
-      47           6 :         double K[n];
-      48         390 :         for (size_t i = 0; i < n; i++)
-      49         384 :                 K[i] = ((double)i / n - i / (n / 2));
-      50             : 
-      51             :         // double kMin = 2*M_PI / lMax; // * 2 * spacing.x; // spacing.x / lMax;
-      52             :         // double kMax = 2*M_PI / lMin; // * 2 * spacing.x; // spacing.x / lMin;
-      53           6 :         double kMin = spacing.x / spectrum.getLmax();
-      54           6 :         double kMax = spacing.x / spectrum.getLmin();
-      55           6 :         auto lambda = 1 / spacing.x * 2 * M_PI;
-      56             : 
-      57             :         Vector3f n0(1, 1, 1); // arbitrary vector to construct orthogonal base
-      58             : 
-      59         390 :         for (size_t ix = 0; ix < n; ix++) {
-      60       24960 :                 for (size_t iy = 0; iy < n; iy++) {
-      61      835584 :                         for (size_t iz = 0; iz < n2; iz++) {
-      62             :         
-      63             :                                 Vector3f ek, e1, e2;  // orthogonal base
-      64             : 
-      65      811008 :                                 size_t i = ix * n * n2 + iy * n2 + iz;
-      66      811008 :                                 ek.setXYZ(K[ix], K[iy], K[iz]);
-      67      811008 :                                 double k = ek.getR();
-      68             : 
-      69             :                                 // wave outside of turbulent range -> B(k) = 0
-      70      811008 :                                 if ((k < kMin) || (k > kMax)) {
-      71      395939 :                                         Bkx[i][0] = 0;
-      72      395939 :                                         Bkx[i][1] = 0;
-      73      395939 :                                         Bky[i][0] = 0;
-      74      395939 :                                         Bky[i][1] = 0;
-      75      395939 :                                         Bkz[i][0] = 0;
-      76      395939 :                                         Bkz[i][1] = 0;
-      77             :                                         continue;
-      78             :                                 }
-      79             : 
-      80             :                                 // construct an orthogonal base ek, e1, e2
-      81      415069 :                                 if (ek.isParallelTo(n0, float(1e-3))) {
-      82             :                                         // ek parallel to (1,1,1)
-      83             :                                         e1.setXYZ(-1., 1., 0);
-      84             :                                         e2.setXYZ(1., 1., -2.);
-      85             :                                 } else {
-      86             :                                         // ek not parallel to (1,1,1)
-      87             :                                         e1 = n0.cross(ek);
-      88             :                                         e2 = ek.cross(e1);
-      89             :                                 }
-      90             :                                 e1 /= e1.getR();
-      91             :                                 e2 /= e2.getR();
-      92             : 
-      93             :                                 // random orientation perpendicular to k
-      94      415069 :                                 double theta = 2 * M_PI * random.rand();
-      95      415069 :                                 Vector3f b = e1 * std::cos(theta) + e2 * std::sin(theta); // real b-field vector
-      96             : 
-      97             :                                 // normal distributed amplitude with mean = 0
-      98      415069 :                                 b *= std::sqrt(spectrum.energySpectrum(k*lambda));
-      99             :                                 
-     100             :                                 // uniform random phase
-     101      415069 :                                 double phase = 2 * M_PI * random.rand();
-     102      415069 :                                 double cosPhase = std::cos(phase); // real part
-     103      415069 :                                 double sinPhase = std::sin(phase); // imaginary part
-     104             : 
-     105      415069 :                                 Bkx[i][0] = b.x * cosPhase;
-     106      415069 :                                 Bkx[i][1] = b.x * sinPhase;
-     107      415069 :                                 Bky[i][0] = b.y * cosPhase;
-     108      415069 :                                 Bky[i][1] = b.y * sinPhase;
-     109      415069 :                                 Bkz[i][0] = b.z * cosPhase;
-     110      415069 :                                 Bkz[i][1] = b.z * sinPhase;
-     111             :                         } // for iz
-     112             :                 }     // for iy
-     113             :         }         // for ix
-     114             : 
-     115           6 :         executeInverseFFTInplace(gridPtr, Bkx, Bky, Bkz);
-     116             : 
-     117           6 :         fftwf_free(Bkx);
-     118           6 :         fftwf_free(Bky);
-     119           6 :         fftwf_free(Bkz);
-     120             : 
-     121          24 :         scaleGrid(gridPtr, spectrum.getBrms() /
-     122          12 :                                rmsFieldStrength(gridPtr)); // normalize to Brms
-     123          12 : }
-     124             : 
-     125             : // Check the grid properties before the FFT procedure
-     126          13 : void GridTurbulence::checkGridRequirements(ref_ptr<Grid3f> grid, double lMin,
-     127             :                                            double lMax) {
-     128             :         size_t Nx = grid->getNx();
-     129             :         size_t Ny = grid->getNy();
-     130             :         size_t Nz = grid->getNz();
-     131             :         Vector3d spacing = grid->getSpacing();
-     132             : 
-     133          13 :         if ((Nx != Ny) or (Ny != Nz))
-     134           0 :                 throw std::runtime_error("turbulentField: only cubic grid supported");
-     135          13 :         if ((spacing.x != spacing.y) or (spacing.y != spacing.z))
-     136           0 :                 throw std::runtime_error("turbulentField: only equal spacing suported");
-     137          13 :         if (lMin < 2 * spacing.x)
-     138           1 :                 throw std::runtime_error("turbulentField: lMin < 2 * spacing");
-     139          12 :         if (lMax > Nx * spacing.x) // before was (lMax > Nx * spacing.x / 2), why?
-     140           1 :                 throw std::runtime_error("turbulentField: lMax > size");
-     141          11 :         if (lMax < lMin) 
-     142           1 :                 throw std::runtime_error("lMax < lMin");
-     143          10 : }
-     144             : 
-     145             : // Execute inverse discrete FFT in-place for a 3D grid, from complex to real
-     146             : // space
-     147          10 : void GridTurbulence::executeInverseFFTInplace(ref_ptr<Grid3f> grid,
-     148             :                                               fftwf_complex *Bkx,
-     149             :                                               fftwf_complex *Bky,
-     150             :                                               fftwf_complex *Bkz) {
-     151             : 
-     152             :         size_t n = grid->getNx(); // size of array
-     153          10 :         size_t n2 = (size_t)floor(n / 2) +
-     154             :                     1; // size array in z-direction in configuration space
-     155             : 
-     156             :         // in-place, complex to real, inverse Fourier transformation on each
-     157             :         // component note that the last elements of B(x) are unused now
-     158             :         float *Bx = (float *)Bkx;
-     159          10 :         fftwf_plan plan_x = fftwf_plan_dft_c2r_3d(n, n, n, Bkx, Bx, FFTW_ESTIMATE);
-     160          10 :         fftwf_execute(plan_x);
-     161          10 :         fftwf_destroy_plan(plan_x);
-     162             : 
-     163             :         float *By = (float *)Bky;
-     164          10 :         fftwf_plan plan_y = fftwf_plan_dft_c2r_3d(n, n, n, Bky, By, FFTW_ESTIMATE);
-     165          10 :         fftwf_execute(plan_y);
-     166          10 :         fftwf_destroy_plan(plan_y);
-     167             : 
-     168             :         float *Bz = (float *)Bkz;
-     169          10 :         fftwf_plan plan_z = fftwf_plan_dft_c2r_3d(n, n, n, Bkz, Bz, FFTW_ESTIMATE);
-     170          10 :         fftwf_execute(plan_z);
-     171          10 :         fftwf_destroy_plan(plan_z);
-     172             : 
-     173             :         // save to grid
-     174         650 :         for (size_t ix = 0; ix < n; ix++) {
-     175       41600 :                 for (size_t iy = 0; iy < n; iy++) {
-     176     2662400 :                         for (size_t iz = 0; iz < n; iz++) {
-     177     2621440 :                                 size_t i = ix * n * 2 * n2 + iy * 2 * n2 + iz;
-     178             :                                 Vector3f &b = grid->get(ix, iy, iz);
-     179     2621440 :                                 b.x = Bx[i];
-     180     2621440 :                                 b.y = By[i];
-     181     2621440 :                                 b.z = Bz[i];
-     182             :                         }
-     183             :                 }
-     184             :         }
-     185          10 : }
-     186             : 
-     187           0 : Vector3f GridTurbulence::getMeanFieldVector() const {
-     188           0 :         return meanFieldVector(gridPtr);
-     189             : }
-     190             : 
-     191           0 : double GridTurbulence::getMeanFieldStrength() const {
-     192           0 :         return meanFieldStrength(gridPtr);
-     193             : }
-     194             : 
-     195           0 : double GridTurbulence::getRmsFieldStrength() const {
-     196           0 :         return rmsFieldStrength(gridPtr);
-     197             : }
-     198             : 
-     199           0 : std::array<float, 3> GridTurbulence::getRmsFieldStrengthPerAxis() const {
-     200           0 :         return rmsFieldStrengthPerAxis(gridPtr);
-     201             : }
-     202             :         
-     203           0 : std::vector<std::pair<int, float>> GridTurbulence::getPowerSpectrum() const {
-     204           0 :         return gridPowerSpectrum(gridPtr);
-     205             : }
-     206             : 
-     207           0 : void GridTurbulence::dumpToFile(std::string filename) const {
-     208           0 :         dumpGrid(gridPtr, filename);
-     209           0 : }
-     210             : 
-     211             : } // namespace crpropa
-     212             : 
-     213             : #endif // CRPROPA_HAVE_FFTW3F
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html deleted file mode 100644 index ce798a6be..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/HelicalGridTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - HelicalGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0590.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21HelicalGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
_ZN7crpropa21HelicalGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEdj0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html deleted file mode 100644 index 3a300bc05..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/HelicalGridTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - HelicalGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0590.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21HelicalGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddid0
_ZN7crpropa21HelicalGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEdj0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html deleted file mode 100644 index 4a3415bc2..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/HelicalGridTurbulence.cpp.gcov.html +++ /dev/null @@ -1,206 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/HelicalGridTurbulence.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - HelicalGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0590.0 %
Date:2024-04-08 14:58:22Functions:020.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/turbulentField/HelicalGridTurbulence.h"
-       2             : #include "crpropa/GridTools.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #ifdef CRPROPA_HAVE_FFTW3F
-       6             : #include "fftw3.h"
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10           0 : HelicalGridTurbulence::HelicalGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
-      11             :                                              const GridProperties &gridProp,
-      12           0 :                                              double H, unsigned int seed)
-      13           0 :     : SimpleGridTurbulence(spectrum, gridProp, seed), H(H) {
-      14           0 :         initTurbulence(gridPtr, spectrum.getBrms(), spectrum.getLmin(),
-      15           0 :                        spectrum.getLmax(), -spectrum.getSindex() - 2, seed, H);
-      16           0 : }
-      17             : 
-      18           0 : void HelicalGridTurbulence::initTurbulence(ref_ptr<Grid3f> grid, double Brms,
-      19             :                                            double lMin, double lMax,
-      20             :                                            double alpha, int seed, double H) {
-      21             : 
-      22           0 :         checkGridRequirements(grid, lMin, lMax);
-      23             : 
-      24             :         Vector3d spacing = grid->getSpacing();
-      25             :         size_t n = grid->getNx(); // size of array
-      26           0 :         size_t n2 = (size_t)floor(n / 2) +
-      27             :                     1; // size array in z-direction in configuration space
-      28             : 
-      29             :         // arrays to hold the complex vector components of the B(k)-field
-      30             :         fftwf_complex *Bkx, *Bky, *Bkz;
-      31           0 :         Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      32           0 :         Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      33           0 :         Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      34             : 
-      35           0 :         Random random;
-      36           0 :         if (seed != 0)
-      37           0 :                 random.seed(seed); // use given seed
-      38             : 
-      39             :         // calculate the n possible discrete wave numbers
-      40           0 :         double K[n];
-      41           0 :         for (size_t i = 0; i < n; i++)
-      42           0 :                 K[i] = (double)i / n - i / (n / 2);
-      43             : 
-      44             :         // only used if there is a helicity
-      45             :         double Bktot, Bkplus, Bkminus, thetaplus, thetaminus;
-      46             : 
-      47           0 :         double kMin = spacing.x / lMax;
-      48           0 :         double kMax = spacing.x / lMin;
-      49             :         Vector3f b;           // real b-field vector
-      50             :         Vector3f ek, e1, e2;  // orthogonal base
-      51             :         Vector3f n0(1, 1, 1); // arbitrary vector to construct orthogonal base
-      52             : 
-      53           0 :         for (size_t ix = 0; ix < n; ix++) {
-      54           0 :                 for (size_t iy = 0; iy < n; iy++) {
-      55           0 :                         for (size_t iz = 0; iz < n2; iz++) {
-      56             : 
-      57           0 :                                 size_t i = ix * n * n2 + iy * n2 + iz;
-      58           0 :                                 ek.setXYZ(K[ix], K[iy], K[iz]);
-      59           0 :                                 double k = ek.getR();
-      60             : 
-      61             :                                 // wave outside of turbulent range -> B(k) = 0
-      62           0 :                                 if ((k < kMin) || (k > kMax)) {
-      63           0 :                                         Bkx[i][0] = 0;
-      64           0 :                                         Bkx[i][1] = 0;
-      65           0 :                                         Bky[i][0] = 0;
-      66           0 :                                         Bky[i][1] = 0;
-      67           0 :                                         Bkz[i][0] = 0;
-      68           0 :                                         Bkz[i][1] = 0;
-      69             :                                         continue;
-      70             :                                 }
-      71             : 
-      72             :                                 // construct an orthogonal base ek, e1, e2
-      73             :                                 // (for helical fields together with the real transform the
-      74             :                                 // following convention must be used: e1(-k) = e1(k), e2(-k) = -
-      75             :                                 // e2(k)
-      76           0 :                                 if (ek.getAngleTo(n0) < 1e-3) { // ek parallel to (1,1,1)
-      77             :                                         e1.setXYZ(-1, 1, 0);
-      78             :                                         e2.setXYZ(1, 1, -2);
-      79             :                                 } else { // ek not parallel to (1,1,1)
-      80             :                                         e1 = n0.cross(ek);
-      81             :                                         e2 = ek.cross(e1);
-      82             :                                 }
-      83             :                                 e1 /= e1.getR();
-      84             :                                 e2 /= e2.getR();
-      85             : 
-      86             : 
-      87           0 :                                 double Bkprefactor = mu0 / (4 * M_PI * pow(k, 3));
-      88           0 :                                 Bktot = fabs(random.randNorm() * pow(k, alpha / 2));
-      89           0 :                                 Bkplus = Bkprefactor * sqrt((1 + H) / 2) * Bktot;
-      90           0 :                                 Bkminus = Bkprefactor * sqrt((1 - H) / 2) * Bktot;
-      91           0 :                                 thetaplus = 2 * M_PI * random.rand();
-      92           0 :                                 thetaminus = 2 * M_PI * random.rand();
-      93           0 :                                 double ctp = cos(thetaplus);
-      94           0 :                                 double stp = sin(thetaplus);
-      95           0 :                                 double ctm = cos(thetaminus);
-      96           0 :                                 double stm = sin(thetaminus);
-      97             : 
-      98           0 :                                 Bkx[i][0] = ((Bkplus * ctp + Bkminus * ctm) * e1.x +
-      99           0 :                                              (-Bkplus * stp + Bkminus * stm) * e2.x) /
-     100             :                                             sqrt(2);
-     101           0 :                                 Bkx[i][1] = ((Bkplus * stp + Bkminus * stm) * e1.x +
-     102           0 :                                              (Bkplus * ctp - Bkminus * ctm) * e2.x) /
-     103             :                                             sqrt(2);
-     104           0 :                                 Bky[i][0] = ((Bkplus * ctp + Bkminus * ctm) * e1.y +
-     105           0 :                                              (-Bkplus * stp + Bkminus * stm) * e2.y) /
-     106             :                                             sqrt(2);
-     107           0 :                                 Bky[i][1] = ((Bkplus * stp + Bkminus * stm) * e1.y +
-     108           0 :                                              (Bkplus * ctp - Bkminus * ctm) * e2.y) /
-     109             :                                             sqrt(2);
-     110           0 :                                 Bkz[i][0] = ((Bkplus * ctp + Bkminus * ctm) * e1.z +
-     111           0 :                                              (-Bkplus * stp + Bkminus * stm) * e2.z) /
-     112             :                                             sqrt(2);
-     113           0 :                                 Bkz[i][1] = ((Bkplus * stp + Bkminus * stm) * e1.z +
-     114           0 :                                              (Bkplus * ctp - Bkminus * ctm) * e2.z) /
-     115             :                                             sqrt(2);
-     116             : 
-     117             :                                 Vector3f BkRe(Bkx[i][0], Bky[i][0], Bkz[i][0]);
-     118             :                                 Vector3f BkIm(Bkx[i][1], Bky[i][1], Bkz[i][1]);
-     119             :                         } // for iz
-     120             :                 }     // for iy
-     121             :         }         // for ix
-     122             : 
-     123           0 :         executeInverseFFTInplace(grid, Bkx, Bky, Bkz);
-     124             : 
-     125           0 :         scaleGrid(grid, Brms / rmsFieldStrength(grid)); // normalize to Brms
-     126           0 : }
-     127             : 
-     128             : } // namespace crpropa
-     129             : 
-     130             : #endif // CRPROPA_HAVE_FFTW3F
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html deleted file mode 100644 index ecbe74169..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/PlaneWaveTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - PlaneWaveTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:464895.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PlaneWaveTurbulenceC2ERKNS_18TurbulenceSpectrumEii2
_ZNK7crpropa19PlaneWaveTurbulence8getFieldERKNS_7Vector3IdEE45
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html deleted file mode 100644 index 3a3efe0af..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/PlaneWaveTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - PlaneWaveTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:464895.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PlaneWaveTurbulenceC2ERKNS_18TurbulenceSpectrumEii2
_ZNK7crpropa19PlaneWaveTurbulence8getFieldERKNS_7Vector3IdEE45
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html deleted file mode 100644 index 0344bde9e..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp.gcov.html +++ /dev/null @@ -1,517 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/PlaneWaveTurbulence.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - PlaneWaveTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:464895.8 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : // This file contains an implementation of a vectorized cosine, which
-       2             : // is based in part on the implementations in the library "SLEEF" by
-       3             : // Naoki Shibata. SLEEF was used under the Boost Software License,
-       4             : // Version 1.0. The original source file contained the following
-       5             : // copyright notice:
-       6             : //
-       7             : //   //          Copyright Naoki Shibata 2010 - 2018.
-       8             : //   // Distributed under the Boost Software License, Version 1.0.
-       9             : //   //    (See accompanying file LICENSE.txt or copy at
-      10             : //   //          http://www.boost.org/LICENSE_1_0.txt)
-      11             : //
-      12             : // SLEEF was used under the following license, which is not necessarily the
-      13             : // license that applies to this file:
-      14             : //
-      15             : //         Boost Software License - Version 1.0 - August 17th, 2003
-      16             : //
-      17             : //         Permission is hereby granted, free of charge, to any person or
-      18             : //         organization obtaining a copy of the software and accompanying
-      19             : //         documentation covered by this license (the "Software") to use,
-      20             : //         reproduce, display, distribute, execute, and transmit the Software,
-      21             : //         and to prepare derivative works of the Software, and to permit
-      22             : //         third-parties to whom the Software is furnished to do so, all subject
-      23             : //         to the following:
-      24             : //
-      25             : //         The copyright notices in the Software and this entire statement,
-      26             : //         including the above license grant, this restriction and the following
-      27             : //         disclaimer, must be included in all copies of the Software, in whole
-      28             : //         or in part, and all derivative works of the Software, unless such
-      29             : //         copies or derivative works are solely in the form of
-      30             : //         machine-executable object code generated by a source language
-      31             : //         processor.
-      32             : //
-      33             : //         THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
-      34             : //         EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
-      35             : //         MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, TITLE AND
-      36             : //         NON-INFRINGEMENT. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR ANYONE
-      37             : //         DISTRIBUTING THE SOFTWARE BE LIABLE FOR ANY DAMAGES OR OTHER
-      38             : //         LIABILITY, WHETHER IN CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT
-      39             : //         OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
-      40             : //         THE SOFTWARE.
-      41             : 
-      42             : #include "crpropa/magneticField/turbulentField/PlaneWaveTurbulence.h"
-      43             : #include "crpropa/GridTools.h"
-      44             : #include "crpropa/Random.h"
-      45             : #include "crpropa/Units.h"
-      46             : 
-      47             : #include "kiss/logger.h"
-      48             : 
-      49             : #include <iostream>
-      50             : 
-      51             : #if defined(FAST_WAVES)
-      52             : #if defined(__SSE__) && defined(__SSE2__) && defined(__SSE3__) && defined(__SSE4_1__) && defined(__SSE4_2__) && defined(__AVX__)
-      53             : #define ENABLE_FAST_WAVES
-      54             : #else
-      55             : #error "FAST_WAVES is enabled, but it appears that not all required SIMD extensions are enabled in the compiler. Without these extensions, the FAST_WAVES optimization cannot be used. Please make sure that the SIMD_EXTENSIONS option in cmake matches the capabilities of your target CPU, or (if your target CPU does not support the required extensions), disable the FAST_WAVES flag in cmake."
-      56             : #endif
-      57             : #endif
-      58             : 
-      59             : 
-      60             : #ifdef ENABLE_FAST_WAVES
-      61             : #include <immintrin.h>
-      62             : #endif
-      63             : 
-      64             : namespace crpropa {
-      65             : #ifdef ENABLE_FAST_WAVES
-      66             : // see
-      67             : // https://stackoverflow.com/questions/49941645/get-sum-of-values-stored-in-m256d-with-sse-avx
-      68             : double hsum_double_avx(__m256d v) {
-      69             :         __m128d vlow = _mm256_castpd256_pd128(v);
-      70             :         __m128d vhigh = _mm256_extractf128_pd(v, 1); // high 128
-      71             :         vlow = _mm_add_pd(vlow, vhigh);              // reduce down to 128
-      72             : 
-      73             :         __m128d high64 = _mm_unpackhi_pd(vlow, vlow);
-      74             :         return _mm_cvtsd_f64(_mm_add_sd(vlow, high64)); // reduce to scalar
-      75             : }
-      76             : #endif // defined(ENABLE_FAST_WAVES)
-      77             : 
-      78           2 : PlaneWaveTurbulence::PlaneWaveTurbulence(const TurbulenceSpectrum &spectrum,
-      79           2 :                                          int Nm, int seed)
-      80           2 :     : TurbulentField(spectrum), Nm(Nm) {
-      81             : 
-      82             : #ifdef ENABLE_FAST_WAVES
-      83             :         KISS_LOG_INFO << "PlaneWaveTurbulence: Using SIMD TD13 implementation"
-      84             :                       << std::endl;
-      85             : 
-      86             :         // There used to be a cpuid check here, to see if the cpu running
-      87             :         // this code would support SIMD (SSE + AVX). However, the library providing
-      88             :         // the relevant function is no longer being used, and doing this manually
-      89             :         // might be a bit too much work.
-      90             : #endif
-      91             : 
-      92           2 :         if (Nm <= 1) {
-      93           0 :                 throw std::runtime_error(
-      94             :                     "PlaneWaveTurbulence: Nm <= 1. Specify at least two wavemodes in "
-      95           0 :                     "order to generate the k distribution properly.");
-      96             :         }
-      97             : 
-      98           2 :         Random random;
-      99           2 :         if (seed != 0)
-     100           2 :                 random.seed(seed);
-     101             : 
-     102           2 :         double kmax = 2 * M_PI / spectrum.getLmin();
-     103           2 :         double kmin = 2 * M_PI / spectrum.getLmax();
-     104             : 
-     105           4 :         xi = std::vector<Vector3d>(Nm, Vector3d(0.));
-     106           4 :         kappa = std::vector<Vector3d>(Nm, Vector3d(0.));
-     107           2 :         phi = std::vector<double>(Nm, 0.);
-     108           2 :         costheta = std::vector<double>(Nm, 0.);
-     109           2 :         beta = std::vector<double>(Nm, 0.);
-     110           2 :         Ak = std::vector<double>(Nm, 0.);
-     111           2 :         k = std::vector<double>(Nm, 0.);
-     112             : 
-     113           2 :         double delta = log10(kmax / kmin);
-     114          22 :         for (int i = 0; i < Nm; i++) {
-     115          20 :                 k[i] = pow(10, log10(kmin) + ((double)i) / ((double)(Nm - 1)) * delta);
-     116             :         }
-     117             : 
-     118             :         // * compute Ak *
-     119             : 
-     120             :         double delta_k0 =
-     121           2 :             (k[1] - k[0]) / k[1]; // multiply this by k[i] to get delta_k[i]
-     122             :         // Note: this is probably unnecessary since it's just a factor
-     123             :         // and will get normalized out anyways. It's not like this is
-     124             :         // performance-sensitive code though, and I don't want to change
-     125             :         // anything numerical now.
-     126             : 
-     127             :         // For this loop, the Ak array actually contains Gk*delta_k (ie
-     128             :         // non-normalized Ak^2). Normalization happens in a second loop,
-     129             :         // once the total is known.
-     130             :         double Ak2_sum = 0; // sum of Ak^2 over all k
-     131          22 :         for (int i = 0; i < Nm; i++) {
-     132          20 :                 double k = this->k[i];
-     133          20 :                 double kHat = k * spectrum.getLbendover();
-     134          20 :                 double Gk = spectrum.energySpectrum(k) * (1 + kHat * kHat);     // correct different implementation in TD 13 (eq. 5, missing + 1 in the denuminators exponent)
-     135          20 :                 Ak[i] = Gk * delta_k0 * k;
-     136          20 :                 Ak2_sum += Ak[i];
-     137             : 
-     138             :                 // phi, costheta, and sintheta are for drawing vectors with
-     139             :                 // uniform distribution on the unit sphere.
-     140             :                 // This is similar to Random::randVector(): their t is our phi,
-     141             :                 // z is costheta, and r is sintheta. Our kappa is equivalent to
-     142             :                 // the return value of randVector(); however, TD13 then reuse
-     143             :                 // these values to generate a random vector perpendicular to kappa.
-     144          20 :                 double phi = random.randUniform(-M_PI, M_PI);
-     145          20 :                 double costheta = random.randUniform(-1., 1.);
-     146          20 :                 double sintheta = sqrt(1 - costheta * costheta);
-     147             : 
-     148          20 :                 double alpha = random.randUniform(0, 2 * M_PI);
-     149          20 :                 double beta = random.randUniform(0, 2 * M_PI);
-     150             : 
-     151             :                 Vector3d kappa =
-     152          20 :                     Vector3d(sintheta * cos(phi), sintheta * sin(phi), costheta);
-     153             : 
-     154             :                 // NOTE: all other variable names match the ones from the TD13 paper.
-     155             :                 // However, our xi is actually their psi, and their xi isn't used at
-     156             :                 // all. (Though both can be used for the polarization vector, according
-     157             :                 // to the paper.) The reason for this discrepancy is that this code
-     158             :                 // used to be based on the original GJ99 paper, which provided only a
-     159             :                 // xi vector, and this xi happens to be almost the same as TD13's psi.
-     160             :                 Vector3d xi =
-     161          20 :                     Vector3d(costheta * cos(phi) * cos(alpha) + sin(phi) * sin(alpha),
-     162          20 :                              costheta * sin(phi) * cos(alpha) - cos(phi) * sin(alpha),
-     163          20 :                              -sintheta * cos(alpha));
-     164             : 
-     165             :                 this->xi[i] = xi;
-     166             :                 this->kappa[i] = kappa;
-     167          20 :                 this->phi[i] = phi;
-     168          20 :                 this->costheta[i] = costheta;
-     169          20 :                 this->beta[i] = beta;
-     170             :         }
-     171             : 
-     172             :         // Only in this loop are the actual Ak computed and stored.
-     173             :         // This two-step process is necessary in order to normalize the values
-     174             :         // properly.
-     175          22 :         for (int i = 0; i < Nm; i++) {
-     176          20 :                 Ak[i] = sqrt(2 * Ak[i] / Ak2_sum) * spectrum.getBrms();
-     177             :         }
-     178             : 
-     179             : #ifdef ENABLE_FAST_WAVES
-     180             :         // * copy data into AVX-compatible arrays *
-     181             :         //
-     182             :         // AVX requires all data to be aligned to 256 bit, or 32 bytes, which is the
-     183             :         // same as 4 double precision floating point numbers. Since support for
-     184             :         // alignments this big seems to be somewhat tentative in C++ allocators,
-     185             :         // we're aligning them manually by allocating a normal double array, and
-     186             :         // then computing the offset to the first value with the correct alignment.
-     187             :         // This is a little bit of work, so instead of doing it separately for each
-     188             :         // of the individual data arrays, we're doing it once for one big array that
-     189             :         // all of the component arrays get packed into.
-     190             :         //
-     191             :         // The other thing to keep in mind is that AVX always reads in units of 256
-     192             :         // bits, or 4 doubles. This means that our number of wavemodes must be
-     193             :         // divisible by 4. If it isn't, we simply pad it out with zeros. Since the
-     194             :         // final step of the computation of each wavemode is multiplication by the
-     195             :         // amplitude, which will be set to 0, these padding wavemodes won't affect
-     196             :         // the result.
-     197             : 
-     198             :         avx_Nm = ((Nm + 4 - 1) / 4) * 4; // round up to next larger multiple of 4:
-     199             :                                          // align is 256 = 4 * sizeof(double) bit
-     200             :         avx_data = std::vector<double>(itotal * avx_Nm + 3, 0.);
-     201             : 
-     202             :         // get the first 256-bit aligned element
-     203             :         size_t size = avx_data.size() * sizeof(double);
-     204             :         void *pointer = avx_data.data();
-     205             :         align_offset =
-     206             :             (double *)std::align(32, 32, pointer, size) - avx_data.data();
-     207             : 
-     208             :         // copy into the AVX arrays
-     209             :         for (int i = 0; i < Nm; i++) {
-     210             :                 avx_data[i + align_offset + avx_Nm * iAxi0] = Ak[i] * xi[i].x;
-     211             :                 avx_data[i + align_offset + avx_Nm * iAxi1] = Ak[i] * xi[i].y;
-     212             :                 avx_data[i + align_offset + avx_Nm * iAxi2] = Ak[i] * xi[i].z;
-     213             : 
-     214             :                 // The cosine implementation computes cos(pi*x), so we'll divide out the
-     215             :                 // pi here.
-     216             :                 avx_data[i + align_offset + avx_Nm * ikkappa0] =
-     217             :                     k[i] / M_PI * kappa[i].x;
-     218             :                 avx_data[i + align_offset + avx_Nm * ikkappa1] =
-     219             :                     k[i] / M_PI * kappa[i].y;
-     220             :                 avx_data[i + align_offset + avx_Nm * ikkappa2] =
-     221             :                     k[i] / M_PI * kappa[i].z;
-     222             : 
-     223             :                 // We also need to divide beta by pi, since that goes into the argument
-     224             :                 // of the cosine as well.
-     225             :                 avx_data[i + align_offset + avx_Nm * ibeta] = beta[i] / M_PI;
-     226             :         }
-     227             : #endif // ENABLE_FAST_WAVES
-     228           2 : }
-     229             : 
-     230          45 : Vector3d PlaneWaveTurbulence::getField(const Vector3d &pos) const {
-     231             : 
-     232             : #ifndef ENABLE_FAST_WAVES
-     233             :         Vector3d B(0.);
-     234         495 :         for (int i = 0; i < Nm; i++) {
-     235         450 :                 double z_ = pos.dot(kappa[i]);
-     236         450 :                 B += xi[i] * Ak[i] * cos(k[i] * z_ + beta[i]);
-     237             :         }
-     238          45 :         return B;
-     239             : 
-     240             : #else  // ENABLE_FAST_WAVES
-     241             : 
-     242             :         // Initialize accumulators
-     243             :         //
-     244             :         // There is one accumulator per component of the result vector.
-     245             :         // Note that each accumulator contains four numbers. At the end of
-     246             :         // the loop, each of these numbers will contain the sum of every
-     247             :         // fourth wavemode, starting at a different offset. In the end, each
-     248             :         // of the accumulator's numbers are added together (using
-     249             :         // hsum_double_avx), resulting in the total sum for that component.
-     250             : 
-     251             :         __m256d acc0 = _mm256_setzero_pd();
-     252             :         __m256d acc1 = _mm256_setzero_pd();
-     253             :         __m256d acc2 = _mm256_setzero_pd();
-     254             : 
-     255             :         // broadcast position into AVX registers
-     256             :         __m256d pos0 = _mm256_set1_pd(pos.x);
-     257             :         __m256d pos1 = _mm256_set1_pd(pos.y);
-     258             :         __m256d pos2 = _mm256_set1_pd(pos.z);
-     259             : 
-     260             :         for (int i = 0; i < avx_Nm; i += 4) {
-     261             : 
-     262             :                 // Load data from memory into AVX registers:
-     263             :                 //  - the three components of the vector A * xi
-     264             :                 __m256d Axi0 =
-     265             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * iAxi0);
-     266             :                 __m256d Axi1 =
-     267             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * iAxi1);
-     268             :                 __m256d Axi2 =
-     269             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * iAxi2);
-     270             : 
-     271             :                 //  - the three components of the vector k * kappa
-     272             :                 __m256d kkappa0 = _mm256_load_pd(avx_data.data() + i + align_offset +
-     273             :                                                  avx_Nm * ikkappa0);
-     274             :                 __m256d kkappa1 = _mm256_load_pd(avx_data.data() + i + align_offset +
-     275             :                                                  avx_Nm * ikkappa1);
-     276             :                 __m256d kkappa2 = _mm256_load_pd(avx_data.data() + i + align_offset +
-     277             :                                                  avx_Nm * ikkappa2);
-     278             : 
-     279             :                 //  - the phase beta.
-     280             :                 __m256d beta =
-     281             :                     _mm256_load_pd(avx_data.data() + i + align_offset + avx_Nm * ibeta);
-     282             : 
-     283             :                 // Then, do the computation.
-     284             : 
-     285             :                 // This is the scalar product between k*kappa and pos:
-     286             :                 __m256d z = _mm256_add_pd(_mm256_mul_pd(pos0, kkappa0),
-     287             :                                           _mm256_add_pd(_mm256_mul_pd(pos1, kkappa1),
-     288             :                                                         _mm256_mul_pd(pos2, kkappa2)));
-     289             : 
-     290             :                 // Here, the phase is added on. This is the argument of the cosine.
-     291             :                 __m256d cos_arg = _mm256_add_pd(z, beta);
-     292             : 
-     293             :                 // ********
-     294             :                 // * Computing the cosine
-     295             :                 // * Part 1: Argument reduction
-     296             :                 //
-     297             :                 //  To understand the computation of the cosine, first note that the
-     298             :                 //  cosine is periodic and we thus only need to model its behavior
-     299             :                 //  between 0 and 2*pi to be able compute the function anywhere. In
-     300             :                 //  fact, by mirroring the function along the x and y axes, even the
-     301             :                 //  range between 0 and pi/2 is sufficient for this purpose. In this
-     302             :                 //  range, the cosine can be efficiently evaluated with high precision
-     303             :                 //  by using a polynomial approximation. Thus, to compute the cosine,
-     304             :                 //  the input value is first reduced so that it lies within this range.
-     305             :                 //  Then, the polynomial approximation is evaluated. Finally, if
-     306             :                 //  necessary, the sign of the result is flipped (mirroring the function
-     307             :                 //  along the x axis).
-     308             :                 //
-     309             :                 //  The actual computation is slightly more involved. First, argument
-     310             :                 //  reduction can be simplified drastically by computing cos(pi*x),
-     311             :                 //  such that the values are reduced to the range [0, 0.5) instead of
-     312             :                 //  [0, pi/2). Since the cosine is even (independent of the sign), we
-     313             :                 //  can first reduce values to [-0.5, 0.5) – that is, a simple rounding
-     314             :                 //  operation – and then neutralize the sign. In fact, precisely because
-     315             :                 //  the cosine is even, all terms of the polynomial are powers of x^2,
-     316             :                 //  so the value of x^2 (computed as x*x) forms the basis for the
-     317             :                 //  polynomial approximation. If I understand things correctly, then (in
-     318             :                 //  IEEE-754 floating point) x*x and (-x)*(-x) will always result in the
-     319             :                 //  exact same value, which means that any error bound over [0, 0.5)
-     320             :                 //  automatically applies to (-0.5, 0] as well.
-     321             : 
-     322             :                 // First, compute round(x), and store it in q. If this value is odd,
-     323             :                 // we're looking at the negative half-wave of the cosine, and thus
-     324             :                 // will have to invert the sign of the result.
-     325             :                 __m256d q = _mm256_round_pd(
-     326             :                     cos_arg, (_MM_FROUND_TO_NEAREST_INT | _MM_FROUND_NO_EXC));
-     327             : 
-     328             :                 // Since we're computing cos(pi*x), round(x) always yields the center of
-     329             :                 // a half-wave (where cos(pi*x) achieves an extremum). This point
-     330             :                 // logically corresponds to x=0. Therefore, we subtract this center from
-     331             :                 // the actual input argument to find the corresponding point on the
-     332             :                 // half-wave that is centered around zero.
-     333             :                 __m256d s = _mm256_sub_pd(cos_arg, q);
-     334             : 
-     335             :                 // We now want to check whether q (the index of our half-wave) is even
-     336             :                 // or odd, since all of the odd-numbered half-waves are negative, so
-     337             :                 // we'll have to flip the final result. On an int, this is as simple as
-     338             :                 // checking the 0th bit. Idea: manipulate the double in such a way that
-     339             :                 // we can do this. So, we add 2^52, such that the last digit of the
-     340             :                 // mantissa is actually in the ones' position. Since q may be negative,
-     341             :                 // we'll also add 2^51 to make sure it's positive. Note that 2^51 is
-     342             :                 // even and thus leaves evenness invariant, which is the only thing we
-     343             :                 // care about here.
-     344             :                 //
-     345             :                 // This is based on the int extraction process described here:
-     346             :                 // https://stackoverflow.com/questions/41144668/how-to-efficiently-perform-double-int64-conversions-with-sse-avx/41223013
-     347             :                 //
-     348             :                 // We assume -2^51 <= q < 2^51 for this, which is unproblematic, as
-     349             :                 // double precision has decayed far enough at that point that the
-     350             :                 // usefulness of the cosine becomes limited.
-     351             :                 //
-     352             :                 // Explanation: The mantissa of a double-precision float has 52 bits
-     353             :                 // (excluding the implicit first bit, which is always one). If |q| >
-     354             :                 // 2^51, this implicit first bit has a place value of at least 2^51,
-     355             :                 // while the first stored bit of the mantissa has a place value of at
-     356             :                 // least 2^50. This means that the LSB of the mantissa has a place value
-     357             :                 // of at least 2^(-1), or 0.5. For a cos(pi*x), this corresponds to a
-     358             :                 // quarter of a cycle (pi/2), so at this point the precision of the
-     359             :                 // input argument is so low that going from one representable number to
-     360             :                 // the next causes the result to jump by +/-1.
-     361             : 
-     362             :                 q = _mm256_add_pd(q, _mm256_set1_pd(0x0018000000000000));
-     363             : 
-     364             :                 // Unfortunately, integer comparisons were only introduced in AVX2, so
-     365             :                 // we'll have to make do with a floating point comparison to check
-     366             :                 // whether the last bit is set. However, masking out all but the last
-     367             :                 // bit will result in a denormal float, which may either result in
-     368             :                 // performance problems or just be rounded down to zero, neither of
-     369             :                 // which is what we want here. To fix this, we'll mask in not only bit
-     370             :                 // 0, but also the exponent (and sign, but that doesn't matter) of q.
-     371             :                 // Luckily, the exponent of q is guaranteed to have the fixed value of
-     372             :                 // 1075 (corresponding to 2^52) after our addition.
-     373             : 
-     374             :                 __m256d invert = _mm256_and_pd(
-     375             :                     q, _mm256_castsi256_pd(_mm256_set1_epi64x(0xfff0000000000001)));
-     376             : 
-     377             :                 // If we did have a one in bit 0, our result will be equal to 2^52 + 1.
-     378             :                 invert = _mm256_cmp_pd(
-     379             :                     invert, _mm256_castsi256_pd(_mm256_set1_epi64x(0x4330000000000001)),
-     380             :                     _CMP_EQ_OQ);
-     381             : 
-     382             :                 // Now we know whether to flip the sign of the result. However, remember
-     383             :                 // that we're working on multiple values at a time, so an if statement
-     384             :                 // won't be of much use here (plus it might perform badly). Instead,
-     385             :                 // we'll make use of the fact that the result of the comparison is all
-     386             :                 // ones if the comparison was true (i.e. q is odd and we need to flip
-     387             :                 // the result), and all zeroes otherwise. If we now mask out all bits
-     388             :                 // except the sign bit, we get something that, when xor'ed into our
-     389             :                 // final result, will flip the sign exactly when q is odd.
-     390             :                 invert = _mm256_and_pd(invert, _mm256_set1_pd(-0.0));
-     391             :                 // (Note that the binary representation of -0.0 is all 0 bits, except
-     392             :                 // for the sign bit, which is set to 1.)
-     393             : 
-     394             :                 // TODO: clamp floats between 0 and 1? This would ensure that we never
-     395             :                 // see inf's, but maybe we want that, so that things dont just fail
-     396             :                 // silently...
-     397             : 
-     398             :                 // * end of argument reduction
-     399             :                 // *******
-     400             : 
-     401             :                 // ******
-     402             :                 // * Evaluate the cosine using a polynomial approximation for the zeroth
-     403             :                 // half-wave.
-     404             :                 // * The coefficients for this were generated using sleefs gencoef.c.
-     405             :                 // * These coefficients are probably far from optimal; however, they
-     406             :                 // should be sufficient for this case.
-     407             :                 s = _mm256_mul_pd(s, s);
-     408             : 
-     409             :                 __m256d u = _mm256_set1_pd(+0.2211852080653743946e+0);
-     410             : 
-     411             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s),
-     412             :                                   _mm256_set1_pd(-0.1332560668688523853e+1));
-     413             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s),
-     414             :                                   _mm256_set1_pd(+0.4058509506474178075e+1));
-     415             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s),
-     416             :                                   _mm256_set1_pd(-0.4934797516664651162e+1));
-     417             :                 u = _mm256_add_pd(_mm256_mul_pd(u, s), _mm256_set1_pd(1.));
-     418             : 
-     419             :                 // Then, flip the sign of each double for which invert is not zero.
-     420             :                 // Since invert has only zero bits except for a possible one in bit 63,
-     421             :                 // we can xor it onto our result to selectively invert the 63rd (sign)
-     422             :                 // bit in each double where invert is set.
-     423             :                 u = _mm256_xor_pd(u, invert);
-     424             : 
-     425             :                 // * end computation of cosine
-     426             :                 // **********
-     427             : 
-     428             :                 // Finally, Ak*xi is multiplied on. Since this is a vector, the
-     429             :                 // multiplication needs to be done for each of the three
-     430             :                 // components, so it happens separately.
-     431             :                 acc0 = _mm256_add_pd(_mm256_mul_pd(u, Axi0), acc0);
-     432             :                 acc1 = _mm256_add_pd(_mm256_mul_pd(u, Axi1), acc1);
-     433             :                 acc2 = _mm256_add_pd(_mm256_mul_pd(u, Axi2), acc2);
-     434             :         }
-     435             : 
-     436             :         return Vector3d(hsum_double_avx(acc0), hsum_double_avx(acc1),
-     437             :                         hsum_double_avx(acc2));
-     438             : #endif // ENABLE_FAST_WAVES
-     439             : }
-     440             : 
-     441             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html deleted file mode 100644 index 02289b77c..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/SimpleGridTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - SimpleGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5252100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SimpleGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEj3
_ZN7crpropa20SimpleGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi7
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html deleted file mode 100644 index 55d106e43..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/SimpleGridTurbulence.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - SimpleGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5252100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SimpleGridTurbulence14initTurbulenceENS_7ref_ptrINS_4GridINS_7Vector3IfEEEEEEddddi7
_ZN7crpropa20SimpleGridTurbulenceC2ERKNS_24SimpleTurbulenceSpectrumERKNS_14GridPropertiesEj3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html b/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html deleted file mode 100644 index a0b831617..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/SimpleGridTurbulence.cpp.gcov.html +++ /dev/null @@ -1,193 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField/SimpleGridTurbulence.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentField - SimpleGridTurbulence.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:5252100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
-       2             : #include "crpropa/GridTools.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #ifdef CRPROPA_HAVE_FFTW3F
-       6             : #include "fftw3.h"
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10           3 : SimpleGridTurbulence::SimpleGridTurbulence(const SimpleTurbulenceSpectrum &spectrum,
-      11             :                                            const GridProperties &gridProp,
-      12           3 :                                            unsigned int seed)
-      13           3 :     : GridTurbulence(spectrum, gridProp, seed) {
-      14           6 :         initTurbulence(gridPtr, spectrum.getBrms(), spectrum.getLmin(),
-      15           3 :                        spectrum.getLmax(), -spectrum.getSindex() - 2, seed);
-      16           3 : }
-      17             : 
-      18           7 : void SimpleGridTurbulence::initTurbulence(ref_ptr<Grid3f> grid, double Brms,
-      19             :                                           double lMin, double lMax,
-      20             :                                           double alpha, int seed) {
-      21             :         
-      22             :         Vector3d spacing = grid->getSpacing();
-      23             : 
-      24          11 :         checkGridRequirements(grid, lMin, lMax);
-      25             : 
-      26             :         size_t n = grid->getNx(); // size of array
-      27           4 :         size_t n2 = (size_t)floor(n / 2) +
-      28             :                     1; // size array in z-direction in configuration space
-      29             : 
-      30             :         // arrays to hold the complex vector components of the B(k)-field
-      31             :         fftwf_complex *Bkx, *Bky, *Bkz;
-      32           4 :         Bkx = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      33           4 :         Bky = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      34           4 :         Bkz = (fftwf_complex *)fftwf_malloc(sizeof(fftwf_complex) * n * n * n2);
-      35             : 
-      36           4 :         Random random;
-      37           4 :         if (seed != 0)
-      38           2 :                 random.seed(seed); // use given seed
-      39             : 
-      40             :         // calculate the n possible discrete wave numbers
-      41           4 :         double K[n];
-      42         260 :         for (size_t i = 0; i < n; i++)
-      43         256 :                 K[i] = (double)i / n - i / (n / 2);
-      44             : 
-      45           4 :         double kMin = spacing.x / lMax;
-      46           4 :         double kMax = spacing.x / lMin;
-      47             :         Vector3f n0(1, 1, 1); // arbitrary vector to construct orthogonal base
-      48             : 
-      49         260 :         for (size_t ix = 0; ix < n; ix++) {
-      50       16640 :                 for (size_t iy = 0; iy < n; iy++) {
-      51      557056 :                         for (size_t iz = 0; iz < n2; iz++) {
-      52             :         
-      53             :                                 Vector3f ek, e1, e2;  // orthogonal base
-      54             : 
-      55      540672 :                                 size_t i = ix * n * n2 + iy * n2 + iz;
-      56      540672 :                                 ek.setXYZ(K[ix], K[iy], K[iz]);
-      57      540672 :                                 double k = ek.getR();
-      58             : 
-      59             :                                 // wave outside of turbulent range -> B(k) = 0
-      60      540672 :                                 if ((k < kMin) || (k > kMax)) {
-      61      264724 :                                         Bkx[i][0] = 0;
-      62      264724 :                                         Bkx[i][1] = 0;
-      63      264724 :                                         Bky[i][0] = 0;
-      64      264724 :                                         Bky[i][1] = 0;
-      65      264724 :                                         Bkz[i][0] = 0;
-      66      264724 :                                         Bkz[i][1] = 0;
-      67             :                                         continue;
-      68             :                                 }
-      69             : 
-      70             :                                 // construct an orthogonal base ek, e1, e2
-      71      275948 :                                 if (ek.isParallelTo(n0, float(1e-3))) {
-      72             :                                         // ek parallel to (1,1,1)
-      73             :                                         e1.setXYZ(-1., 1., 0);
-      74             :                                         e2.setXYZ(1., 1., -2.);
-      75             :                                 } else {
-      76             :                                         // ek not parallel to (1,1,1)
-      77             :                                         e1 = n0.cross(ek);
-      78             :                                         e2 = ek.cross(e1);
-      79             :                                 }
-      80             :                                 e1 /= e1.getR();
-      81             :                                 e2 /= e2.getR();
-      82             : 
-      83             :                                 // random orientation perpendicular to k
-      84      275948 :                                 double theta = 2 * M_PI * random.rand();
-      85      275948 :                                 Vector3f b = e1 * cos(theta) + e2 * sin(theta); // real b-field vector
-      86             : 
-      87             :                                 // normal distributed amplitude with mean = 0 and sigma =
-      88             :                                 // k^alpha/2
-      89      275948 :                                 b *= random.randNorm() * pow(k, alpha / 2);
-      90             : 
-      91             :                                 // uniform random phase
-      92      275948 :                                 double phase = 2 * M_PI * random.rand();
-      93      275948 :                                 double cosPhase = cos(phase); // real part
-      94      275948 :                                 double sinPhase = sin(phase); // imaginary part
-      95             : 
-      96      275948 :                                 Bkx[i][0] = b.x * cosPhase;
-      97      275948 :                                 Bkx[i][1] = b.x * sinPhase;
-      98      275948 :                                 Bky[i][0] = b.y * cosPhase;
-      99      275948 :                                 Bky[i][1] = b.y * sinPhase;
-     100      275948 :                                 Bkz[i][0] = b.z * cosPhase;
-     101      275948 :                                 Bkz[i][1] = b.z * sinPhase;
-     102             :                         } // for iz
-     103             :                 }     // for iy
-     104             :         }         // for ix
-     105             : 
-     106           4 :         executeInverseFFTInplace(grid, Bkx, Bky, Bkz);
-     107             : 
-     108           4 :         fftwf_free(Bkx);
-     109           4 :         fftwf_free(Bky);
-     110           4 :         fftwf_free(Bkz);
-     111             : 
-     112          16 :         scaleGrid(grid, Brms / rmsFieldStrength(grid)); // normalize to Brms
-     113          11 : }
-     114             : 
-     115             : } // namespace crpropa
-     116             : 
-     117             : #endif // CRPROPA_HAVE_FFTW3F
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html b/doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html deleted file mode 100644 index 4bb56e51d..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/index-sort-f.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:18726371.1 %
Date:2024-04-08 14:58:22Functions:111957.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.cpp -
0.0%
-
0.0 %0 / 590.0 %0 / 2
GridTurbulence.cpp -
85.6%85.6%
-
85.6 %89 / 10453.8 %7 / 13
SimpleGridTurbulence.cpp -
100.0%
-
100.0 %52 / 52100.0 %2 / 2
PlaneWaveTurbulence.cpp -
95.8%95.8%
-
95.8 %46 / 48100.0 %2 / 2
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html b/doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html deleted file mode 100644 index 1a7102ae5..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/index-sort-l.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:18726371.1 %
Date:2024-04-08 14:58:22Functions:111957.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
HelicalGridTurbulence.cpp -
0.0%
-
0.0 %0 / 590.0 %0 / 2
GridTurbulence.cpp -
85.6%85.6%
-
85.6 %89 / 10453.8 %7 / 13
PlaneWaveTurbulence.cpp -
95.8%95.8%
-
95.8 %46 / 48100.0 %2 / 2
SimpleGridTurbulence.cpp -
100.0%
-
100.0 %52 / 52100.0 %2 / 2
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticField/turbulentField/index.html b/doc/coverageReport/src/magneticField/turbulentField/index.html deleted file mode 100644 index 2bfdfdefa..000000000 --- a/doc/coverageReport/src/magneticField/turbulentField/index.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticField/turbulentField - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticField/turbulentFieldHitTotalCoverage
Test:coverage.info.cleanedLines:18726371.1 %
Date:2024-04-08 14:58:22Functions:111957.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
GridTurbulence.cpp -
85.6%85.6%
-
85.6 %89 / 10453.8 %7 / 13
HelicalGridTurbulence.cpp -
0.0%
-
0.0 %0 / 590.0 %0 / 2
PlaneWaveTurbulence.cpp -
95.8%95.8%
-
95.8 %46 / 48100.0 %2 / 2
SimpleGridTurbulence.cpp -
100.0%
-
100.0 %52 / 52100.0 %2 / 2
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html deleted file mode 100644 index 6962e0d0c..000000000 --- a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/MagneticLens.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - MagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4310441.3 %
Date:2024-04-08 14:58:22Functions:61346.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLens12loadLensPartERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd0
_ZN7crpropa12MagneticLens13normalizeLensEv0
_ZN7crpropa12MagneticLens18normalizeLenspartsEv0
_ZN7crpropa12MagneticLens22normalizeMatrixColumnsEv0
_ZN7crpropa12MagneticLens8loadLensERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa12MagneticLens15rigidityCoveredEd0
_ZNK7crpropa12MagneticLens20transformModelVectorEPdd0
_ZN7crpropa12MagneticLens11setLensPartERKN5Eigen12SparseMatrixIdLi0EiEEdd3
_ZN7crpropa12MagneticLens12_checkMatrixERKN5Eigen12SparseMatrixIdLi0EiEE3
_ZN7crpropa12MagneticLens20updateRigidityBoundsEdd3
_ZN7crpropa12MagneticLens18transformCosmicRayEdRNS_7Vector3IdEE4
_ZN7crpropa12MagneticLens18transformCosmicRayEdRdS1_12293
_ZNK7crpropa12MagneticLens11getLensPartEd12293
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html deleted file mode 100644 index 291746429..000000000 --- a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/MagneticLens.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - MagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4310441.3 %
Date:2024-04-08 14:58:22Functions:61346.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12MagneticLens11setLensPartERKN5Eigen12SparseMatrixIdLi0EiEEdd3
_ZN7crpropa12MagneticLens12_checkMatrixERKN5Eigen12SparseMatrixIdLi0EiEE3
_ZN7crpropa12MagneticLens12loadLensPartERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEdd0
_ZN7crpropa12MagneticLens13normalizeLensEv0
_ZN7crpropa12MagneticLens18normalizeLenspartsEv0
_ZN7crpropa12MagneticLens18transformCosmicRayEdRNS_7Vector3IdEE4
_ZN7crpropa12MagneticLens18transformCosmicRayEdRdS1_12293
_ZN7crpropa12MagneticLens20updateRigidityBoundsEdd3
_ZN7crpropa12MagneticLens22normalizeMatrixColumnsEv0
_ZN7crpropa12MagneticLens8loadLensERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa12MagneticLens11getLensPartEd12293
_ZNK7crpropa12MagneticLens15rigidityCoveredEd0
_ZNK7crpropa12MagneticLens20transformModelVectorEPdd0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html b/doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html deleted file mode 100644 index 88d65754f..000000000 --- a/doc/coverageReport/src/magneticLens/MagneticLens.cpp.gcov.html +++ /dev/null @@ -1,353 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/MagneticLens.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - MagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4310441.3 %
Date:2024-04-08 14:58:22Functions:61346.2 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : //----------------------------------------------------------------------
-       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
-       3             : // a parametrized simulation engine for cosmic rays.
-       4             : //
-       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
-       6             : //                     RWTH Aachen University, Germany
-       7             : // Contact: winchen@physik.rwth-aachen.de
-       8             : //
-       9             : //  This program is free software: you can redistribute it and/or
-      10             : //  modify it under the terms of the GNU General Public License as
-      11             : //  published by the Free Software Foundation, either version 3 of
-      12             : //  the License, or (at your option) any later version.
-      13             : //
-      14             : //  This program is distributed in the hope that it will be useful,
-      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      17             : //  GNU General Public License for more details.
-      18             : //
-      19             : //  You should have received a copy of the GNU General Public License
-      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
-      21             : //----------------------------------------------------------------------
-      22             : 
-      23             : #include "crpropa/magneticLens/MagneticLens.h"
-      24             : 
-      25             : #include "crpropa/Random.h"
-      26             : #include "crpropa/Units.h"
-      27             : 
-      28             : // needed for memcpy in gcc 4.3.2
-      29             : #include <cstring>
-      30             : 
-      31             : namespace crpropa 
-      32             : {
-      33             : 
-      34           0 : void MagneticLens::loadLens(const string &filename)
-      35             : {
-      36           0 :         ifstream infile(filename.c_str());
-      37           0 :         if (!infile)
-      38             :         {
-      39           0 :                 throw std::runtime_error("Can't read file: " + filename);
-      40             :         }
-      41             :         string line;
-      42             : 
-      43             :         string prefix;
-      44           0 :         int sp = filename.find_last_of("/");
-      45           0 :         if (sp >= 0)
-      46             :         {
-      47           0 :                 prefix = filename.substr(0, sp);
-      48           0 :                 prefix.append("/");
-      49             :         }
-      50             :         string mfdatfile;
-      51             :         double emin, emax;
-      52             : 
-      53             :         int lineCounter = 0;
-      54           0 :         while (!infile.eof())
-      55             :         {
-      56           0 :                 getline(infile, line);
-      57           0 :                 lineCounter++;
-      58           0 :                 if (line.find('#') == string::npos)
-      59             :                 {
-      60           0 :                         stringstream ss;
-      61             :                         ss << line;
-      62           0 :                         ss >> mfdatfile >> emin >> emax;
-      63           0 :                         if (ss.fail())
-      64             :                         {
-      65           0 :                                 cerr << "WARNING! Cannot read line " << lineCounter << " of file " << filename << " :\n [" << lineCounter << " ]: " << line << " \n";
-      66           0 :                                 cerr << " ... Skipping line and continue\n";
-      67             :                         }
-      68             :                         else
-      69             :                         {
-      70           0 :                                 this->loadLensPart(prefix + mfdatfile, pow(10, emin) * eV, pow(10, emax) * eV);
-      71             :                         }
-      72           0 :                 }
-      73             :         }
-      74           0 : }
-      75             : 
-      76       12293 : bool MagneticLens::transformCosmicRay(double rigidity, double& phi,
-      77             :                 double& theta) 
-      78             : {
-      79       12293 :         uint32_t c = _pixelization->direction2Pix(phi, theta);
-      80       12293 :         LensPart *lenspart = getLensPart(rigidity);
-      81       12293 :         if (!lenspart)
-      82             :         {
-      83           1 :                 std::cerr << "Warning. Trying to transform cosmic ray with rigidity " << rigidity / eV << " eV which is not covered by this lens!.\n";
-      84           2 :                 std::cerr << " This lens covers the range " << _minimumRigidity /eV << " eV - " << _maximumRigidity << " eV.\n";
-      85           1 :                 return false;
-      86             :         }
-      87             : 
-      88       12292 :         ModelVectorType v = lenspart->getMatrix().col(c);
-      89             : 
-      90             :         uint32_t r;
-      91             : 
-      92             :         // the random number to compare with
-      93       12292 :         double rn = Random::instance().rand();
-      94             : 
-      95             :         ModelVectorType::InnerIterator i(v);
-      96             :   double cpv = 0;
-      97       12292 :   while (i)
-      98             :   {
-      99       12292 :                 cpv += i.value();
-     100       12292 :                 if (rn < cpv)
-     101             :                 {
-     102       12292 :                         _pixelization->pix2Direction(i.index(), phi, theta);
-     103             :                         return true;
-     104             :     }
-     105             :     else
-     106             :     {
-     107             :                         ++i;
-     108             :     }
-     109             :    }
-     110             :   return false;
-     111             : }
-     112             : 
-     113           4 : bool MagneticLens::transformCosmicRay(double rigidity, Vector3d &p){
-     114             : 
-     115           4 :                         double galacticLongitude = atan2(-p.y, -p.x);
-     116           4 :                         double galacticLatitude =       M_PI / 2 - acos(-p.z/ sqrt(p.x*p.x + p.y*p.y + p.z*p.z));
-     117           4 :                         bool result = transformCosmicRay(rigidity, galacticLongitude, galacticLatitude);
-     118             :                         
-     119           4 :                         p.x = -1 * cos(galacticLongitude) * sin(M_PI / 2 - galacticLatitude);
-     120           4 :                         p.y = -1 * sin(galacticLongitude) * sin(M_PI / 2 - galacticLatitude);
-     121           4 :                         p.z = -1. * cos(M_PI / 2 - galacticLatitude);
-     122             : 
-     123           4 :                         return result;
-     124             : }
-     125             : 
-     126           0 : void MagneticLens::loadLensPart(const string &filename, double rigidityMin,
-     127             :                 double rigidityMax)
-     128             : {
-     129           0 :         updateRigidityBounds(rigidityMin, rigidityMax);
-     130             : 
-     131           0 :         LensPart *p = new LensPart(filename, rigidityMin, rigidityMax);
-     132             :         p->loadMatrixFromFile();
-     133           0 :         _checkMatrix(p->getMatrix());
-     134             : 
-     135           0 :         _lensParts.push_back(p);
-     136           0 : }
-     137             : 
-     138           3 : void MagneticLens::_checkMatrix(const ModelMatrixType &M)
-     139             : {
-     140           3 :         if (M.rows() != M.cols())
-     141             :         {
-     142           0 :                 throw std::runtime_error("Not a square Matrix!");
-     143             :         }
-     144             : 
-     145           3 :         if (_pixelization)
-     146             :         {
-     147           3 :                 if (_pixelization->nPix() != M.cols())
-     148             :                 {
-     149             :                         std::cerr << "*** ERROR ***" << endl;
-     150           0 :                         std::cerr << "  Pixelization: " << _pixelization->nPix() << endl;
-     151             :                         std::cerr << "  Matrix Size : " << M.cols() << endl;
-     152           0 :                         throw std::runtime_error("Matrix doesn't fit into Lense");
-     153             :                 }
-     154             :         }
-     155             :         else
-     156             :         {
-     157           0 :                 uint32_t morder = Pixelization::pix2Order(M.cols());
-     158           0 :                 if (morder == 0)
-     159             :                 {
-     160           0 :                         throw std::runtime_error(
-     161           0 :                                         "Matrix size doesn't match healpix scheme!");
-     162             :                 }
-     163           0 :                 _pixelization = new Pixelization(morder);
-     164             :         }
-     165           3 : }
-     166             : 
-     167           3 : void MagneticLens::updateRigidityBounds(double rigidityMin, double rigidityMax)
-     168             : {
-     169           3 :         if (rigidityMin >= rigidityMax)
-     170             :         {
-     171           0 :                 throw std::runtime_error("rigidityMin >= rigidityMax");
-     172             :         }
-     173           3 :         if (rigidityMin < _minimumRigidity)
-     174             :         {
-     175           3 :                 _minimumRigidity = rigidityMin;
-     176             :         }
-     177             : 
-     178           3 :         if (_maximumRigidity < rigidityMin)
-     179             :         {
-     180           3 :                 _maximumRigidity = rigidityMax;
-     181             :         }
-     182           3 : }
-     183             : 
-     184           3 : void MagneticLens::setLensPart(const ModelMatrixType &M, double rigidityMin,
-     185             :                 double rigidityMax)
-     186             : {
-     187           3 :         updateRigidityBounds(rigidityMin, rigidityMax);
-     188           3 :         LensPart *p = new LensPart("Direct Input", rigidityMin, rigidityMax);
-     189             : 
-     190             :         p->setMatrix(M);
-     191             : 
-     192           3 :         _checkMatrix(p->getMatrix());
-     193           3 :         _lensParts.push_back(p);
-     194           3 : }
-     195             : 
-     196       12293 : LensPart* MagneticLens::getLensPart(double rigidity) const
-     197             : {
-     198             :         const_LensPartIter i = _lensParts.begin();
-     199       12294 :         while (i != _lensParts.end())
-     200             :         {
-     201       12293 :                 if (((*i)->getMinimumRigidity() < rigidity / eV)
-     202       12293 :                                 && ((*i)->getMaximumRigidity() >= rigidity / eV))
-     203             :                 {
-     204             :                         return (*i);
-     205             :                 }
-     206             :                 ++i;
-     207             :         }
-     208             :         return NULL;
-     209             : }
-     210             : 
-     211           0 : bool MagneticLens::rigidityCovered(double rigidity) const
-     212             : {
-     213           0 :         if (getLensPart(rigidity))
-     214             :                 return true;
-     215             :         else
-     216           0 :                 return false;
-     217             : }
-     218             : 
-     219             : 
-     220           0 : void MagneticLens::normalizeMatrixColumns()
-     221             : {
-     222           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
-     223             :                         ++iter)
-     224             :         {
-     225           0 :                 normalizeColumns((*iter)->getMatrix());
-     226             :         }
-     227           0 : }
-     228             : 
-     229             : 
-     230           0 : void MagneticLens::normalizeLens()
-     231             : {
-     232             :         // get maximum of sums of columns, and normalize each matrix to that
-     233             :         double norm = 0;
-     234           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
-     235             :                         ++iter)
-     236             :         {
-     237           0 :                 if ((*iter)->getMaximumOfSumsOfColumns() > norm)
-     238             :                 {
-     239           0 :                         norm = (*iter)->getMaximumOfSumsOfColumns();
-     240             :                 }
-     241             :         }
-     242           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
-     243             :                         ++iter)
-     244             :         {
-     245           0 :                 normalizeMatrix((*iter)->getMatrix(), norm);
-     246             :         }
-     247           0 :   _norm = norm;
-     248           0 : }
-     249             : 
-     250           0 : void MagneticLens::normalizeLensparts()
-     251             : {
-     252           0 :         for (LensPartIter iter = _lensParts.begin(); iter != _lensParts.end();
-     253             :                         ++iter)
-     254             :         {
-     255           0 :                 double norm = (*iter)->getMaximumOfSumsOfColumns();
-     256           0 :                 normalizeMatrix((*iter)->getMatrix(), norm);
-     257             :         }
-     258           0 : }
-     259             : 
-     260           0 : void MagneticLens::transformModelVector(double* model, double rigidity) const
-     261             : {
-     262           0 :         LensPart* lenspart = getLensPart(rigidity);
-     263             :         
-     264           0 :         if (!lenspart)
-     265             :         {
-     266           0 :                 std::cerr << "Warning. Trying to transform vector with rigidity " << rigidity / eV << "eV which is not covered by this lens!.\n" << std::endl;
-     267           0 :                 return;
-     268             :         }
-     269             : 
-     270           0 :         prod_up(lenspart->getMatrix(), model);
-     271             : 
-     272             : }
-     273             : 
-     274             : 
-     275             : 
-     276             : } // namespace parsec
-     277             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html deleted file mode 100644 index 0b636302b..000000000 --- a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/ModelMatrix.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - ModelMatrix.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11deserializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa15normalizeMatrixERN5Eigen12SparseMatrixIdLi0EiEEd0
_ZN7crpropa16normalizeColumnsERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa22maximumOfSumsOfColumnsERKN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa6norm_1ERKN5Eigen12SparseVectorIdLi0EiEE0
_ZN7crpropa7prod_upERKN5Eigen12SparseMatrixIdLi0EiEEPd0
_ZN7crpropa9serializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKN5Eigen12SparseMatrixIdLi0EiEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html deleted file mode 100644 index 9869c0266..000000000 --- a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/ModelMatrix.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - ModelMatrix.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11deserializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa15normalizeMatrixERN5Eigen12SparseMatrixIdLi0EiEEd0
_ZN7crpropa16normalizeColumnsERN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa22maximumOfSumsOfColumnsERKN5Eigen12SparseMatrixIdLi0EiEE0
_ZN7crpropa6norm_1ERKN5Eigen12SparseVectorIdLi0EiEE0
_ZN7crpropa7prod_upERKN5Eigen12SparseMatrixIdLi0EiEEPd0
_ZN7crpropa9serializeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKN5Eigen12SparseMatrixIdLi0EiEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html b/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html deleted file mode 100644 index e0c22d95b..000000000 --- a/doc/coverageReport/src/magneticLens/ModelMatrix.cpp.gcov.html +++ /dev/null @@ -1,237 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/ModelMatrix.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - ModelMatrix.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0630.0 %
Date:2024-04-08 14:58:22Functions:070.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : //----------------------------------------------------------------------
-       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
-       3             : // a parametrized simulation engine for cosmic rays.
-       4             : //
-       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
-       6             : //                     RWTH Aachen University, Germany
-       7             : // Contact: winchen@physik.rwth-aachen.de
-       8             : //
-       9             : //  This program is free software: you can redistribute it and/or
-      10             : //  modify it under the terms of the GNU General Public License as
-      11             : //  published by the Free Software Foundation, either version 3 of
-      12             : //  the License, or (at your option) any later version.
-      13             : //
-      14             : //  This program is distributed in the hope that it will be useful,
-      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      17             : //  GNU General Public License for more details.
-      18             : //
-      19             : //  You should have received a copy of the GNU General Public License
-      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
-      21             : //----------------------------------------------------------------------
-      22             : 
-      23             : #include "crpropa/magneticLens/ModelMatrix.h"
-      24             : #include <ctime>
-      25             : 
-      26             : #include <Eigen/Core>
-      27             : namespace crpropa 
-      28             : {
-      29             : 
-      30           0 : void serialize(const string &filename, const ModelMatrixType& matrix)
-      31             : {
-      32           0 :         ofstream outfile(filename.c_str(), ios::binary);
-      33           0 :         if (!outfile)
-      34             :         {
-      35           0 :                 throw runtime_error("Can't write file: " + filename);
-      36             :         }
-      37             : 
-      38           0 :         uint32_t C = 0;
-      39             :         double val;
-      40             : 
-      41           0 :         C = (uint32_t) (matrix.nonZeros());
-      42           0 :         outfile.write((char*) &C, sizeof(uint32_t));
-      43           0 :         C = (uint32_t) (matrix.rows());
-      44           0 :         outfile.write((char*) &C, sizeof(uint32_t));
-      45           0 :         C = (uint32_t) (matrix.cols());
-      46           0 :         outfile.write((char*) &C, sizeof(uint32_t));
-      47             : 
-      48             :         // serialize non zero elements
-      49           0 :         for (size_t col_idx = 0; col_idx < matrix.cols(); ++col_idx)
-      50             :         {
-      51           0 :                 for (ModelMatrixType::InnerIterator it(matrix,col_idx); it; ++it)
-      52             :                         {
-      53             :                                 it.value();
-      54           0 :                                 C = (uint32_t) it.row();
-      55           0 :                                 outfile.write((char*) &C, sizeof(uint32_t));
-      56             : 
-      57           0 :                                 C = (uint32_t) it.col();
-      58           0 :                                 outfile.write((char*) &C, sizeof(uint32_t));
-      59             : 
-      60           0 :                                 val = it.value();
-      61           0 :                                 outfile.write((char*) &val, sizeof(double));
-      62           0 :                                 if (outfile.fail())
-      63             :                                 {
-      64           0 :                                         throw runtime_error("Error writing file: " + filename);
-      65             :                                 }
-      66             :                         }
-      67             :         }
-      68             : 
-      69           0 :         outfile.close();
-      70           0 : }
-      71             : 
-      72             : 
-      73           0 : void deserialize(const string &filename, ModelMatrixType& matrix)
-      74             : {
-      75           0 :         ifstream infile(filename.c_str(), ios::binary);
-      76           0 :         if (!infile)
-      77             :         {
-      78           0 :                 throw runtime_error("Can't read file: " + filename);
-      79             :         }
-      80             : 
-      81             :         uint32_t nnz, nRows, nColumns;
-      82           0 :         infile.read((char*) &nnz, sizeof(uint32_t));
-      83           0 :         infile.read((char*) &nRows, sizeof(uint32_t));
-      84           0 :         infile.read((char*) &nColumns, sizeof(uint32_t));
-      85           0 :         matrix.resize(nRows, nColumns);
-      86           0 :         matrix.reserve(nnz);
-      87             : 
-      88             :         uint32_t row, column;
-      89             :         double val;
-      90             :         std::vector< Eigen::Triplet<double> > triplets;
-      91           0 :         triplets.resize(nnz);
-      92           0 :         for (size_t i = 0; i < nnz; i++)
-      93             :         {
-      94           0 :                 infile.read((char*) &row, sizeof(uint32_t));
-      95           0 :                 infile.read((char*) &column, sizeof(uint32_t));
-      96           0 :                 infile.read((char*) &val, sizeof(double));
-      97             :                 //M(size1,size2) = val;
-      98           0 :                 triplets[i] = Eigen::Triplet<double>(row, column, val);
-      99             :         }
-     100           0 :         matrix.setFromTriplets(triplets.begin(), triplets.end());
-     101           0 :         matrix.makeCompressed();
-     102           0 : }
-     103             : 
-     104             : 
-     105           0 : double norm_1(const ModelVectorType &v)
-     106             : {
-     107           0 :         return v.cwiseAbs().sum();
-     108             : }
-     109             : 
-     110             : 
-     111           0 : void normalizeColumns(ModelMatrixType &matrix){
-     112           0 :         for (size_t i=0; i< matrix.cols(); i++)
-     113             :         {
-     114           0 :                 ModelVectorType v = matrix.col(i);
-     115           0 :                 double rn = norm_1(v);
-     116           0 :                 matrix.col(i) = v/rn;
-     117             :         }
-     118           0 : }
-     119             : 
-     120             : 
-     121           0 : double maximumOfSumsOfColumns(const ModelMatrixType &matrix) 
-     122             : {
-     123             :         double summax = 0;
-     124           0 :         for (size_t i = 0; i < matrix.cols(); i++)
-     125             :         {
-     126           0 :                 double sum = matrix.col(i).sum();
-     127           0 :                 if (sum > summax)
-     128             :                         summax = sum;
-     129             :         }
-     130           0 :         return summax;
-     131             : }
-     132             : 
-     133           0 :         void normalizeMatrix(ModelMatrixType& matrix, double norm)
-     134             : {
-     135           0 :         matrix /= norm;
-     136           0 : }
-     137             : 
-     138           0 :         void prod_up(const ModelMatrixType& matrix, double* model)
-     139             : {
-     140             : 
-     141             :         // copy storage of model, as matrix vector product cannot be done
-     142             :         // in place
-     143             :         
-     144           0 :         const size_t mSize = matrix.cols();
-     145           0 :         double *origVectorStorage = new double[mSize];
-     146             :         memcpy(origVectorStorage, model, mSize * sizeof(double));
-     147             : 
-     148             : 
-     149             : 
-     150             :         Eigen::Map<Eigen::Matrix<double, Eigen::Dynamic, 1> > origVectorAdaptor(origVectorStorage, mSize);
-     151             :         Eigen::Map<Eigen::Matrix<double, Eigen::Dynamic, 1> > modelVectorAdaptor(model, mSize);
-     152             : 
-     153             :         // perform the optimized product
-     154           0 :         modelVectorAdaptor = matrix * origVectorAdaptor;
-     155             : 
-     156             :         // clean up
-     157           0 :         delete[] origVectorStorage;
-     158           0 : }
-     159             : 
-     160             : 
-     161             : } // namespace parsec
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html deleted file mode 100644 index 20670889d..000000000 --- a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/ParticleMapsContainer.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - ParticleMapsContainer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7410570.5 %
Date:2024-04-08 14:58:22Functions:91369.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer11addParticleEidRKNS_7Vector3IdEEd0
_ZN7crpropa21ParticleMapsContainer17forceWeightUpdateEv0
_ZN7crpropa21ParticleMapsContainer6getMapEid0
_ZN7crpropa21ParticleMapsContainer9applyLensERNS_12MagneticLensE0
_ZN7crpropa21ParticleMapsContainer11getEnergiesEi1
_ZN7crpropa21ParticleMapsContainer14getParticleIdsEv1
_ZN7crpropa21ParticleMapsContainer18getRandomParticlesEmRSt6vectorIiSaIiEERS1_IdSaIdEES7_S7_1
_ZN7crpropa21ParticleMapsContainer11addParticleEidddd2
_ZN7crpropa21ParticleMapsContainerD2Ev2
_ZN7crpropa21ParticleMapsContainer10placeOnMapEidRdS1_420
_ZN7crpropa21ParticleMapsContainer14_updateWeightsEv421
_ZNK7crpropa21ParticleMapsContainer10idx2EnergyEi421
_ZNK7crpropa21ParticleMapsContainer10energy2IdxEd422
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html deleted file mode 100644 index fec3680af..000000000 --- a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/ParticleMapsContainer.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - ParticleMapsContainer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7410570.5 %
Date:2024-04-08 14:58:22Functions:91369.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa21ParticleMapsContainer10placeOnMapEidRdS1_420
_ZN7crpropa21ParticleMapsContainer11addParticleEidRKNS_7Vector3IdEEd0
_ZN7crpropa21ParticleMapsContainer11addParticleEidddd2
_ZN7crpropa21ParticleMapsContainer11getEnergiesEi1
_ZN7crpropa21ParticleMapsContainer14_updateWeightsEv421
_ZN7crpropa21ParticleMapsContainer14getParticleIdsEv1
_ZN7crpropa21ParticleMapsContainer17forceWeightUpdateEv0
_ZN7crpropa21ParticleMapsContainer18getRandomParticlesEmRSt6vectorIiSaIiEERS1_IdSaIdEES7_S7_1
_ZN7crpropa21ParticleMapsContainer6getMapEid0
_ZN7crpropa21ParticleMapsContainer9applyLensERNS_12MagneticLensE0
_ZN7crpropa21ParticleMapsContainerD2Ev2
_ZNK7crpropa21ParticleMapsContainer10energy2IdxEd422
_ZNK7crpropa21ParticleMapsContainer10idx2EnergyEi421
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html b/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html deleted file mode 100644 index 58e7fc9e5..000000000 --- a/doc/coverageReport/src/magneticLens/ParticleMapsContainer.cpp.gcov.html +++ /dev/null @@ -1,275 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/ParticleMapsContainer.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - ParticleMapsContainer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:7410570.5 %
Date:2024-04-08 14:58:22Functions:91369.2 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "HepPID/ParticleIDMethods.hh"
-       2             : #include "crpropa/Random.h"
-       3             : #include "crpropa/magneticLens/ParticleMapsContainer.h"
-       4             : #include "crpropa/Units.h"
-       5             : 
-       6             : #include <iostream>
-       7             : #include <fstream>
-       8             : 
-       9             : namespace crpropa  {
-      10             : 
-      11           2 : ParticleMapsContainer::~ParticleMapsContainer() {
-      12           2 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
-      13           4 :                         pid_iter != _data.end(); ++pid_iter) {
-      14           2 :                 for(std::map<int, double*>::iterator energy_iter = pid_iter->second.begin();
-      15           4 :                         energy_iter != pid_iter->second.end(); ++energy_iter) {
-      16           2 :                         delete[] (energy_iter->second);
-      17             :                 }
-      18             :         }
-      19           2 : }
-      20             : 
-      21         422 : int ParticleMapsContainer::energy2Idx(double energy) const {
-      22         422 :         double lE = log10(energy / eV);
-      23         422 :         return int((lE - _bin0lowerEdge) / _deltaLogE);
-      24             : }
-      25             : 
-      26         421 : double ParticleMapsContainer::idx2Energy(int idx) const {
-      27         421 :         return pow(10, idx * _deltaLogE + _bin0lowerEdge + _deltaLogE / 2) * eV;
-      28             : }
-      29             : 
-      30             :                 
-      31           0 : double* ParticleMapsContainer::getMap(const int particleId, double energy) {
-      32           0 :         _weightsUpToDate = false;
-      33           0 :         if (_data.find(particleId) == _data.end()) {
-      34           0 :                 std::cerr << "No map for ParticleID " << particleId << std::endl;
-      35           0 :                 return NULL;
-      36             :         }
-      37           0 :         int energyIdx   = energy2Idx(energy);
-      38           0 :         if (_data[particleId].find(energyIdx) == _data[particleId].end()) {
-      39           0 :                 std::cerr << "No map for ParticleID and energy" << energy / eV << " eV" << std::endl;
-      40           0 :                 return NULL;
-      41             :         }
-      42           0 :         return _data[particleId][energy2Idx(energy)];
-      43             : }
-      44             :                         
-      45             :                         
-      46           2 : void ParticleMapsContainer::addParticle(const int particleId, double energy, double galacticLongitude, double galacticLatitude, double weight) {
-      47           2 :         _weightsUpToDate = false;
-      48           2 :         if (_data.find(particleId) == _data.end()) {
-      49             :                 map<int, double*> M;
-      50           2 :                 _data[particleId] = M;
-      51             :         }
-      52             : 
-      53           2 :         int energyIdx   = energy2Idx(energy);
-      54           4 :         if (_data[particleId].find(energyIdx) == _data[particleId].end()) {
-      55           2 :                 _data[particleId][energyIdx] = new double[_pixelization.getNumberOfPixels()];
-      56           2 :                 std::fill(_data[particleId][energyIdx], _data[particleId][energyIdx] + _pixelization.getNumberOfPixels(), 0);
-      57             :         }
-      58             : 
-      59           2 :         uint32_t pixel = _pixelization.direction2Pix(galacticLongitude, galacticLatitude);
-      60           2 :         _data[particleId][energyIdx][pixel] += weight;
-      61           2 : }
-      62             : 
-      63             : 
-      64           0 : void ParticleMapsContainer::addParticle(const int particleId, double energy, const Vector3d &p, double weight) {
-      65           0 :         double galacticLongitude = atan2(-p.y, -p.x);
-      66           0 :         double galacticLatitude =       M_PI / 2 - acos(-p.z / p.getR());
-      67           0 :         addParticle(particleId, energy, galacticLongitude, galacticLatitude, weight);
-      68           0 : }
-      69             : 
-      70             : 
-      71           1 : std::vector<int> ParticleMapsContainer::getParticleIds() {
-      72             :         std::vector<int> ids;
-      73           1 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
-      74           2 :                         pid_iter != _data.end(); ++pid_iter) {
-      75           1 :                 ids.push_back(pid_iter->first);
-      76             :         }
-      77           1 :         return ids;
-      78             : }
-      79             : 
-      80             : 
-      81           1 : std::vector<double> ParticleMapsContainer::getEnergies(int pid) {
-      82             :         std::vector<double> energies;
-      83           1 :         if (_data.find(pid) != _data.end()) {
-      84           1 :                 for(std::map<int, double*>::iterator iter = _data[pid].begin(); 
-      85           2 :                         iter != _data[pid].end(); ++iter) {
-      86           1 :                         energies.push_back( idx2Energy(iter->first) / eV );
-      87             :                 }
-      88             :         }
-      89           1 :         return energies;
-      90             : }
-      91             : 
-      92             : 
-      93           0 : void ParticleMapsContainer::applyLens(MagneticLens &lens) {
-      94             :         // if lens is normalized, this should not be necessary.
-      95           0 :         _weightsUpToDate = false;
-      96             : 
-      97           0 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
-      98           0 :                         pid_iter != _data.end(); ++pid_iter) {
-      99           0 :                 for(std::map<int, double*>::iterator energy_iter = pid_iter->second.begin();
-     100           0 :                         energy_iter != pid_iter->second.end(); ++energy_iter) {
-     101             :                         // transform only nuclei
-     102           0 :                         double energy = idx2Energy(energy_iter->first);
-     103           0 :                         int chargeNumber = HepPID::Z(pid_iter->first);
-     104           0 :                         if (chargeNumber != 0 && lens.rigidityCovered(energy / chargeNumber)) {
-     105           0 :                                 lens.transformModelVector(energy_iter->second, energy / chargeNumber);
-     106             :                         } else { // still normalize the vectors 
-     107           0 :                                 for(size_t j=0; j< _pixelization.getNumberOfPixels() ; j++) {
-     108           0 :                                         energy_iter->second[j] /= lens.getNorm();
-     109             :                                 }
-     110             :                         }
-     111             :                 }
-     112             :         }
-     113           0 : }
-     114             : 
-     115             : 
-     116         421 : void ParticleMapsContainer::_updateWeights() {
-     117         421 :         if (_weightsUpToDate)
-     118             :                 return;
-     119             : 
-     120           1 :         for(std::map<int, std::map<int, double*> >::iterator pid_iter = _data.begin(); 
-     121           2 :                         pid_iter != _data.end(); ++pid_iter) {
-     122           1 :                 _weightsPID[pid_iter->first] = 0;
-     123             : 
-     124           1 :                 for(std::map<int, double*>::iterator energy_iter = pid_iter->second.begin();
-     125           2 :                         energy_iter != pid_iter->second.end(); ++energy_iter)  {
-     126             : 
-     127           1 :                         _weights_pidEnergy[pid_iter->first][energy_iter->first] = 0;
-     128       49153 :                         for(size_t j = 0; j< _pixelization.getNumberOfPixels() ; j++) {
-     129       49152 :                                 _weights_pidEnergy[pid_iter->first][energy_iter->first] +=energy_iter->second[j];
-     130       49152 :                                 _weightsPID[pid_iter->first]+=energy_iter->second[j];
-     131             :                         }
-     132           1 :                         _sumOfWeights+=_weights_pidEnergy[pid_iter->first][energy_iter->first];
-     133             :                 }
-     134             :         }
-     135           1 :         _weightsUpToDate = true;
-     136             : }
-     137             : 
-     138             : 
-     139           1 : void ParticleMapsContainer::getRandomParticles(size_t N, vector<int> &particleId, 
-     140             :         vector<double> &energy, vector<double> &galacticLongitudes,
-     141             :         vector<double> &galacticLatitudes) {
-     142           1 :         _updateWeights();
-     143             : 
-     144           1 :         particleId.resize(N);
-     145           1 :         energy.resize(N);
-     146           1 :         galacticLongitudes.resize(N);
-     147           1 :         galacticLatitudes.resize(N);
-     148             : 
-     149         421 :         for(size_t i=0; i< N; i++) {
-     150             :                 //get particle
-     151         420 :                 double r = Random::instance().rand() * _sumOfWeights;
-     152             :                 std::map<int, double>::iterator iter = _weightsPID.begin();
-     153         420 :                 while ((r-= iter->second) > 0) {
-     154             :                         ++iter; 
-     155             :                 }
-     156         420 :                 particleId[i] = iter->first;
-     157             :         
-     158             :                 //get energy
-     159         420 :                 r = Random::instance().rand() * iter->second;
-     160         420 :                 iter = _weights_pidEnergy[particleId[i]].begin();
-     161         420 :                 while ((r-= iter->second) > 0) {
-     162             :                  ++iter; 
-     163             :                 }
-     164         420 :                 energy[i] = idx2Energy(iter->first) / eV;
-     165             : 
-     166         420 :                 placeOnMap(particleId[i], energy[i] * eV, galacticLongitudes[i], galacticLatitudes[i]);
-     167             :         }
-     168           1 : }
-     169             : 
-     170             : 
-     171         420 : bool ParticleMapsContainer::placeOnMap(int pid, double energy, double &galacticLongitude, double &galacticLatitude) {
-     172         420 :         _updateWeights();
-     173             : 
-     174         420 :         if (_data.find(pid) == _data.end()) {
-     175             :                 return false;
-     176             :         }
-     177         420 :         int energyIdx   = energy2Idx(energy);
-     178         840 :         if (_data[pid].find(energyIdx) == _data[pid].end()) {
-     179             :                 return false;
-     180             :         }
-     181             : 
-     182         420 :         double r = Random::instance().rand() * _weights_pidEnergy[pid][energyIdx];
-     183             : 
-     184    10268580 :         for(size_t j = 0; j< _pixelization.getNumberOfPixels(); j++) {
-     185    10268580 :                 r -= _data[pid][energyIdx][j];
-     186    10268580 :                 if (r <= 0) {
-     187         420 :                         _pixelization.getRandomDirectionInPixel(j, galacticLongitude, galacticLatitude);
-     188         420 :                         return true;
-     189             :                 }
-     190             :         }
-     191             :         return false;
-     192             : }
-     193             : 
-     194             : 
-     195           0 : void ParticleMapsContainer::forceWeightUpdate() {
-     196           0 :         _weightsUpToDate = false;
-     197           0 : }
-     198             : 
-     199             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html b/doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html deleted file mode 100644 index 70dfc7376..000000000 --- a/doc/coverageReport/src/magneticLens/Pixelization.cpp.func-sort-c.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/Pixelization.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - Pixelization.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:305060.0 %
Date:2024-04-08 14:58:22Functions:6875.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization4nPixEh0
_ZN7crpropa12Pixelization9pix2OrderEj0
_ZN7crpropa12Pixelization25getRandomDirectionInPixelEjRdS1_421
_ZNK7crpropa12Pixelization11spherCo2VecEddRN7healpix6vec3_tIdEE24585
_ZNK7crpropa12Pixelization13direction2PixEdd24585
_ZNK7crpropa12Pixelization13pix2DirectionEjRdS1_36868
_ZNK7crpropa12Pixelization12vec2SphereCoERdS1_RKN7healpix6vec3_tIdEE37289
_ZNK7crpropa12Pixelization15angularDistanceEjj49152
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html b/doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html deleted file mode 100644 index d568a50f3..000000000 --- a/doc/coverageReport/src/magneticLens/Pixelization.cpp.func.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/Pixelization.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - Pixelization.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:305060.0 %
Date:2024-04-08 14:58:22Functions:6875.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12Pixelization25getRandomDirectionInPixelEjRdS1_421
_ZN7crpropa12Pixelization4nPixEh0
_ZN7crpropa12Pixelization9pix2OrderEj0
_ZNK7crpropa12Pixelization11spherCo2VecEddRN7healpix6vec3_tIdEE24585
_ZNK7crpropa12Pixelization12vec2SphereCoERdS1_RKN7healpix6vec3_tIdEE37289
_ZNK7crpropa12Pixelization13direction2PixEdd24585
_ZNK7crpropa12Pixelization13pix2DirectionEjRdS1_36868
_ZNK7crpropa12Pixelization15angularDistanceEjj49152
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html b/doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html deleted file mode 100644 index 26f97cb78..000000000 --- a/doc/coverageReport/src/magneticLens/Pixelization.cpp.gcov.html +++ /dev/null @@ -1,205 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens/Pixelization.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLens - Pixelization.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:305060.0 %
Date:2024-04-08 14:58:22Functions:6875.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : //----------------------------------------------------------------------
-       2             : // This file is part of PARSEC (http://physik.rwth-aachen.de/parsec)
-       3             : // a parametrized simulation engine for cosmic rays.
-       4             : //
-       5             : // Copyright (C) 2011  Martin Erdmann, Peter Schiffer, Tobias Winchen
-       6             : //                     RWTH Aachen University, Germany
-       7             : // Contact: winchen@physik.rwth-aachen.de
-       8             : //
-       9             : //  This program is free software: you can redistribute it and/or
-      10             : //  modify it under the terms of the GNU General Public License as
-      11             : //  published by the Free Software Foundation, either version 3 of
-      12             : //  the License, or (at your option) any later version.
-      13             : //
-      14             : //  This program is distributed in the hope that it will be useful,
-      15             : //  but WITHOUT ANY WARRANTY; without even the implied warranty of
-      16             : //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-      17             : //  GNU General Public License for more details.
-      18             : //
-      19             : //  You should have received a copy of the GNU General Public License
-      20             : //  along with this program. If not, see <http://www.gnu.org/licenses/>.
-      21             : //----------------------------------------------------------------------
-      22             : 
-      23             : #include "crpropa/magneticLens/Pixelization.h"
-      24             : #include "crpropa/Random.h"
-      25             : 
-      26             : namespace crpropa 
-      27             : {
-      28             : 
-      29             :         healpix::T_Healpix_Base<healpix::int64> Pixelization::_healpix_nest = healpix::T_Healpix_Base<healpix::int64>(29, healpix::NEST);
-      30             : 
-      31             : 
-      32           0 : uint8_t Pixelization::pix2Order(uint32_t pix)
-      33             : {
-      34           0 :         for (uint8_t i = 0; i < _nOrder_max; i++)
-      35             :         {
-      36           0 :                 if (pix == _nPix[i])
-      37           0 :                         return i + 1;
-      38             :         }
-      39             :         return 0;
-      40             : }
-      41             : 
-      42           0 : uint32_t Pixelization::nPix(uint8_t order)
-      43             : {
-      44           0 :         if (order > _nOrder_max)
-      45             :         {
-      46             :                 return 0;
-      47             :         }
-      48             :         else
-      49             :         {
-      50           0 :                 return _nPix[order - 1];
-      51             :         }
-      52             : }
-      53             : 
-      54       24585 : uint32_t Pixelization::direction2Pix(double longitude, double latitude) const
-      55             : {
-      56             :         healpix::vec3 v;
-      57       24585 :         spherCo2Vec(longitude, latitude, v);
-      58             :         try
-      59             :         {
-      60       24585 :                 uint32_t i = (uint32_t) _healpix->vec2pix(v);
-      61       24585 :                 return i;
-      62             :         }
-      63           0 :         catch (healpix::PlanckError &e)
-      64             :         {
-      65           0 :                 std::cerr << "Healpix error triggered from direction2Pix(" << longitude << ", " << latitude  << ")\n";
-      66           0 :                 std::cerr << " v = " << v.x <<", " << v.y << ", " <<  v.z << std::endl;
-      67           0 :                 std::cerr << "\n The original exception reads:\n";
-      68           0 :                 std::cerr << e.what() << std::endl;
-      69           0 :                 throw;
-      70           0 :         }
-      71             : }
-      72             : 
-      73       36868 : void Pixelization::pix2Direction(uint32_t i, double &longitude,
-      74             :                 double &latitude) const
-      75             : {
-      76             :         healpix::vec3 v;
-      77             :         try{
-      78       36868 :                 v = _healpix->pix2vec(i);
-      79             :         }
-      80           0 :         catch (healpix::PlanckError &e)
-      81             :         {
-      82           0 :                 std::cerr << "Healpix error triggered from pix2Direction(" << i << ", &longitude, &latitude " << ")\n";
-      83           0 :                 std::cerr << "The original exception reads:\n";
-      84           0 :                 std::cerr << e.what() << std::endl;
-      85           0 :                 throw;
-      86           0 :         }
-      87             : 
-      88       36868 :         vec2SphereCo(longitude, latitude, v);
-      89       36868 : }
-      90             : 
-      91       24585 : void Pixelization::spherCo2Vec(double phi, double theta,
-      92             :                 healpix::vec3 &V) const
-      93             : {
-      94       24585 :         V.x = cos(phi) * cos(theta);
-      95       24585 :         V.y = sin(phi) * cos(theta);
-      96       24585 :         V.z = sin(theta);
-      97       24585 : }
-      98             : 
-      99       37289 : void Pixelization::vec2SphereCo(double &phi, double &theta,
-     100             :                 const healpix::vec3 &V) const
-     101             : {
-     102       37289 :         theta = asin(V.z);
-     103       37289 :         phi = healpix::safe_atan2(V.y, V.x);
-     104       37289 : }
-     105             : 
-     106             : 
-     107       49152 : double Pixelization::angularDistance(uint32_t i, uint32_t j) const
-     108             : {
-     109             :         healpix::vec3 v1, v2;
-     110       49152 :         v1 = _healpix->pix2vec(i);
-     111       49152 :         v2 = _healpix->pix2vec(j);
-     112       49152 :         double s = v1.x * v2.x + v1.y * v2.y + v1.z * v2.z;
-     113             :         // Failsafe for numerical inaccuracies
-     114       49152 :         return ((s > 1) ? 0 : ((s < -1) ? M_PI : acos(s)));
-     115             : }
-     116             : 
-     117         421 : void Pixelization::getRandomDirectionInPixel(uint32_t i, double &longitude, double &latitude) 
-     118             : {
-     119             :         
-     120         421 :         uint64_t inest = _healpix->ring2nest(i);
-     121         421 :         uint64_t nUp = 29 - _healpix->Order();
-     122         421 :         uint64_t iUp = inest * pow(4, nUp);
-     123         421 :         iUp += Random::instance().randInt64(pow(4, nUp));
-     124             : 
-     125         421 :         healpix::vec3 v = _healpix_nest.pix2vec(iUp);
-     126             :         
-     127         421 :         vec2SphereCo(longitude, latitude, v);
-     128         421 : }
-     129             : } // namespace
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/index-sort-f.html b/doc/coverageReport/src/magneticLens/index-sort-f.html deleted file mode 100644 index 2a95e9fb8..000000000 --- a/doc/coverageReport/src/magneticLens/index-sort-f.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:14732245.7 %
Date:2024-04-08 14:58:22Functions:214151.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ModelMatrix.cpp -
0.0%
-
0.0 %0 / 630.0 %0 / 7
MagneticLens.cpp -
41.3%41.3%
-
41.3 %43 / 10446.2 %6 / 13
ParticleMapsContainer.cpp -
70.5%70.5%
-
70.5 %74 / 10569.2 %9 / 13
Pixelization.cpp -
60.0%60.0%
-
60.0 %30 / 5075.0 %6 / 8
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/index-sort-l.html b/doc/coverageReport/src/magneticLens/index-sort-l.html deleted file mode 100644 index 7bd0ec2a3..000000000 --- a/doc/coverageReport/src/magneticLens/index-sort-l.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:14732245.7 %
Date:2024-04-08 14:58:22Functions:214151.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ModelMatrix.cpp -
0.0%
-
0.0 %0 / 630.0 %0 / 7
MagneticLens.cpp -
41.3%41.3%
-
41.3 %43 / 10446.2 %6 / 13
Pixelization.cpp -
60.0%60.0%
-
60.0 %30 / 5075.0 %6 / 8
ParticleMapsContainer.cpp -
70.5%70.5%
-
70.5 %74 / 10569.2 %9 / 13
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/magneticLens/index.html b/doc/coverageReport/src/magneticLens/index.html deleted file mode 100644 index bacc94ec2..000000000 --- a/doc/coverageReport/src/magneticLens/index.html +++ /dev/null @@ -1,123 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/magneticLens - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/magneticLensHitTotalCoverage
Test:coverage.info.cleanedLines:14732245.7 %
Date:2024-04-08 14:58:22Functions:214151.2 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
MagneticLens.cpp -
41.3%41.3%
-
41.3 %43 / 10446.2 %6 / 13
ModelMatrix.cpp -
0.0%
-
0.0 %0 / 630.0 %0 / 7
ParticleMapsContainer.cpp -
70.5%70.5%
-
70.5 %74 / 10569.2 %9 / 13
Pixelization.cpp -
60.0%60.0%
-
60.0 %30 / 5075.0 %6 / 8
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html deleted file mode 100644 index 506fe0201..000000000 --- a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func-sort-c.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/ConstantDensity.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - ConstantDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:748983.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15ConstantDensity14getDescriptionB5cxx11Ev0
_ZN7crpropa15ConstantDensity5setH2Eb1
_ZN7crpropa15ConstantDensity5setH2Ed1
_ZN7crpropa15ConstantDensity5setHIEb1
_ZN7crpropa15ConstantDensity5setHIEd1
_ZN7crpropa15ConstantDensity6setHIIEb1
_ZN7crpropa15ConstantDensity6setHIIEd1
_ZN7crpropa15ConstantDensity10getIsForH2Ev2
_ZN7crpropa15ConstantDensity10getIsForHIEv2
_ZN7crpropa15ConstantDensity11getIsForHIIEv2
_ZN7crpropa15ConstantDensityC2Eddd3
_ZNK7crpropa15ConstantDensity10getDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getH2DensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getHIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity13getHIIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity17getNucleonDensityERKNS_7Vector3IdEE4
_ZN7crpropa15ConstantDensity5setH2Ebd5
_ZN7crpropa15ConstantDensity5setHIEbd5
_ZN7crpropa15ConstantDensity6setHIIEbd5
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html deleted file mode 100644 index f0cb8a317..000000000 --- a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.func.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/ConstantDensity.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - ConstantDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:748983.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15ConstantDensity10getIsForH2Ev2
_ZN7crpropa15ConstantDensity10getIsForHIEv2
_ZN7crpropa15ConstantDensity11getIsForHIIEv2
_ZN7crpropa15ConstantDensity14getDescriptionB5cxx11Ev0
_ZN7crpropa15ConstantDensity5setH2Eb1
_ZN7crpropa15ConstantDensity5setH2Ebd5
_ZN7crpropa15ConstantDensity5setH2Ed1
_ZN7crpropa15ConstantDensity5setHIEb1
_ZN7crpropa15ConstantDensity5setHIEbd5
_ZN7crpropa15ConstantDensity5setHIEd1
_ZN7crpropa15ConstantDensity6setHIIEb1
_ZN7crpropa15ConstantDensity6setHIIEbd5
_ZN7crpropa15ConstantDensity6setHIIEd1
_ZN7crpropa15ConstantDensityC2Eddd3
_ZNK7crpropa15ConstantDensity10getDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getH2DensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity12getHIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity13getHIIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa15ConstantDensity17getNucleonDensityERKNS_7Vector3IdEE4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html b/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html deleted file mode 100644 index 94c4d2718..000000000 --- a/doc/coverageReport/src/massDistribution/ConstantDensity.cpp.gcov.html +++ /dev/null @@ -1,213 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/ConstantDensity.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - ConstantDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:748983.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/massDistribution/ConstantDensity.h"
-       2             : 
-       3             : #include "kiss/logger.h"
-       4             : 
-       5             : #include <sstream>
-       6             : 
-       7             : namespace crpropa{
-       8             : 
-       9           3 : ConstantDensity::ConstantDensity(double HI, double HII, double H2) {
-      10             :         // set all types active which are not equal 0 and change number density
-      11           3 :         if(HI!=0)
-      12           3 :                 setHI(true, HI);
-      13           3 :         if(HII!=0)
-      14           3 :                 setHII(true, HII);
-      15           3 :         if(H2!=0)
-      16           3 :                 setH2(true, H2);
-      17           3 : }
-      18             : 
-      19           4 : double ConstantDensity::getDensity(const Vector3d &position) const {
-      20             :         double n = 0;
-      21             : 
-      22           4 :         if(isHI)
-      23           3 :                 n += HIdensitynumber;
-      24           4 :         if(isHII)
-      25           3 :                 n += HIIdensitynumber;
-      26           4 :         if(isH2)
-      27           3 :                 n += H2densitynumber;
-      28             : 
-      29             :         // check if all densities are deactivated and raise warning if so
-      30           4 :         if((isHI || isHII || isH2) == false){
-      31           2 :                 KISS_LOG_WARNING
-      32           1 :                         << "\nCalled getNucleonDensity on fully deactivated ConstantDensity "
-      33           1 :                         << "gas density model. In this case the density is allways set to 0. \n";
-      34             :         }
-      35             : 
-      36           4 :         return n;
-      37             : }
-      38             : 
-      39           4 : double ConstantDensity::getNucleonDensity(const Vector3d &position) const {
-      40             :         double n = 0;
-      41             : 
-      42           4 :         if(isHI)
-      43           3 :                 n += HIdensitynumber;
-      44           4 :         if(isHII)
-      45           3 :                 n += HIIdensitynumber;
-      46           4 :         if(isH2)
-      47           3 :                 n += 2*H2densitynumber;
-      48             : 
-      49             :         // check if all densities are deactivated and raise warning if so
-      50           4 :         if((isHI || isHII || isH2) == false){
-      51           2 :                 KISS_LOG_WARNING
-      52           1 :                         << "\nCalled getNucleonDensity on fully deactivated ConstantDensity "
-      53           1 :                         << "gas density model. In this case the density is allways set to 0. \n";
-      54             :         }
-      55           4 :         return n;
-      56             : }
-      57             : 
-      58           4 : double ConstantDensity::getHIDensity(const Vector3d &position) const {
-      59           4 :         return HIdensitynumber;
-      60             : }
-      61             : 
-      62           4 : double ConstantDensity::getHIIDensity(const Vector3d &position) const{
-      63           4 :         return HIIdensitynumber;
-      64             : }
-      65             : 
-      66           4 : double ConstantDensity::getH2Density(const Vector3d &position) const{
-      67           4 :         return H2densitynumber;
-      68             : }
-      69             : 
-      70           2 : bool ConstantDensity::getIsForHI() {
-      71           2 :         return isHI;
-      72             : }
-      73             : 
-      74           2 : bool ConstantDensity::getIsForHII() {
-      75           2 :         return isHII;
-      76             : }
-      77             : 
-      78           2 : bool ConstantDensity::getIsForH2() {
-      79           2 :         return isH2;
-      80             : }
-      81             : 
-      82           5 : void ConstantDensity::setHI(bool activate, double densitynumber) {
-      83           5 :         isHI = activate;
-      84           5 :         HIdensitynumber = densitynumber;
-      85           5 : }
-      86             : 
-      87           1 : void ConstantDensity::setHI(bool activate) {
-      88           1 :         setHI(activate, HIdensitynumber);
-      89           1 : }
-      90             : 
-      91           1 : void ConstantDensity::setHI(double densitynumber) {
-      92           1 :         setHI(isHI, densitynumber);
-      93           1 : }
-      94             : 
-      95           5 : void ConstantDensity::setHII(bool activate, double densitynumber) {
-      96           5 :         isHII = activate;
-      97           5 :         HIIdensitynumber = densitynumber;
-      98           5 : }
-      99             : 
-     100           1 : void ConstantDensity::setHII(bool activate) {
-     101           1 :         setHII(activate, HIIdensitynumber);
-     102           1 : }
-     103             : 
-     104           1 : void ConstantDensity::setHII(double densitynumber) {
-     105           1 :         setHII(isHII, densitynumber);
-     106           1 : }
-     107             : 
-     108           5 : void ConstantDensity::setH2(bool activate, double densitynumber) {
-     109           5 :         isH2 = activate;
-     110           5 :         H2densitynumber = densitynumber;
-     111           5 : }
-     112             : 
-     113           1 : void ConstantDensity::setH2(bool activate) {
-     114           1 :         setH2(activate, H2densitynumber);
-     115           1 : }
-     116             : 
-     117           1 : void ConstantDensity::setH2(double densitynumber) {
-     118           1 :         setH2(isH2, densitynumber);
-     119           1 : }
-     120             : 
-     121           0 : std::string ConstantDensity::getDescription() {
-     122           0 :         std::stringstream s;
-     123           0 :         s << "ConstantDensity:\n";
-     124           0 :         s<< "HI component is ";
-     125           0 :         if(!isHI)
-     126           0 :                 s<< "not ";
-     127           0 :         s<< "active and has a density of " << HIdensitynumber/ccm << " cm^-3" << "\nHII component is ";
-     128           0 :         if(!isHII)
-     129           0 :                 s<< "not ";
-     130           0 :         s<<"active and has a density of " << HIIdensitynumber/ccm<<" cm^-3" <<  "\nH2 component is ";
-     131           0 :         if(!isH2)
-     132           0 :                 s<<"not ";
-     133           0 :         s<<"active and has a density of " << H2densitynumber/ccm << " cm^-3";
-     134           0 :         return s.str();
-     135           0 : }
-     136             : 
-     137             : }  // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html deleted file mode 100644 index 5ac34bc19..000000000 --- a/doc/coverageReport/src/massDistribution/Cordes.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Cordes.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Cordes.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:162176.2 %
Date:2024-04-08 14:58:22Functions:6785.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Cordes14getDescriptionB5cxx11Ev0
_ZN7crpropa6Cordes10getIsForH2Ev1
_ZN7crpropa6Cordes10getIsForHIEv1
_ZN7crpropa6Cordes11getIsForHIIEv1
_ZNK7crpropa6Cordes17getNucleonDensityERKNS_7Vector3IdEE1
_ZNK7crpropa6Cordes10getDensityERKNS_7Vector3IdEE2
_ZNK7crpropa6Cordes13getHIIDensityERKNS_7Vector3IdEE4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Cordes.cpp.func.html b/doc/coverageReport/src/massDistribution/Cordes.cpp.func.html deleted file mode 100644 index 6522e9bd4..000000000 --- a/doc/coverageReport/src/massDistribution/Cordes.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Cordes.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Cordes.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:162176.2 %
Date:2024-04-08 14:58:22Functions:6785.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Cordes10getIsForH2Ev1
_ZN7crpropa6Cordes10getIsForHIEv1
_ZN7crpropa6Cordes11getIsForHIIEv1
_ZN7crpropa6Cordes14getDescriptionB5cxx11Ev0
_ZNK7crpropa6Cordes10getDensityERKNS_7Vector3IdEE2
_ZNK7crpropa6Cordes13getHIIDensityERKNS_7Vector3IdEE4
_ZNK7crpropa6Cordes17getNucleonDensityERKNS_7Vector3IdEE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html deleted file mode 100644 index 47a3e4fcf..000000000 --- a/doc/coverageReport/src/massDistribution/Cordes.cpp.gcov.html +++ /dev/null @@ -1,122 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Cordes.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Cordes.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:162176.2 %
Date:2024-04-08 14:58:22Functions:6785.7 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/massDistribution/Cordes.h"
-       2             : #include "crpropa/Common.h"
-       3             : 
-       4             : #include <sstream>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           4 : double Cordes::getHIIDensity(const Vector3d &position) const {
-       9             :         double n=0;  // in m^-3
-      10             : 
-      11           4 :         double z=position.z;
-      12           4 :         double R = sqrt(position.x*position.x+position.y*position.y);  //radius in galactic disk
-      13             : 
-      14           4 :         n += 0.025/ccm*exp(-fabs(z)/(1*kpc))*exp(-pow_integer<2>(R/(20*kpc)));  // galactocentric component
-      15           4 :         n += 0.2/ccm*exp(-fabs(z)/(0.15*kpc))*exp(-pow_integer<2>((R-4*kpc)/(2*kpc)));  // anular component
-      16             : 
-      17           4 :         return n;
-      18             : }
-      19             : 
-      20           2 : double Cordes::getDensity(const Vector3d &position) const {
-      21           2 :         return Cordes::getHIIDensity(position);
-      22             : }
-      23             : 
-      24           1 : double Cordes::getNucleonDensity(const Vector3d &position) const {
-      25           1 :         return getHIIDensity(position);
-      26             : }
-      27             : 
-      28           1 : bool Cordes::getIsForHI() {
-      29           1 :         return isforHI;
-      30             : }
-      31             : 
-      32           1 : bool Cordes::getIsForHII() {
-      33           1 :         return isforHII;
-      34             : }
-      35             : 
-      36           1 : bool Cordes::getIsForH2() {
-      37           1 :         return isforH2;
-      38             : }
-      39             : 
-      40           0 : std::string Cordes::getDescription() {
-      41           0 :         std::stringstream s;
-      42           0 :         s << "Density Cordes: includes only an HII component";
-      43           0 :         return s.str();
-      44           0 : }
-      45             : 
-      46             : }  // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html deleted file mode 100644 index 31d3bf13c..000000000 --- a/doc/coverageReport/src/massDistribution/Ferriere.cpp.func-sort-c.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Ferriere.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Ferriere.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13615190.1 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8Ferriere14getDescriptionB5cxx11Ev0
_ZN7crpropa8Ferriere10setIsForH2Eb1
_ZN7crpropa8Ferriere10setIsForHIEb1
_ZN7crpropa8Ferriere11setIsForHIIEb1
_ZN7crpropa8Ferriere10getIsForH2Ev4
_ZN7crpropa8Ferriere10getIsForHIEv4
_ZN7crpropa8Ferriere11getIsForHIIEv4
_ZNK7crpropa8Ferriere10getDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere17getNucleonDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere12getH2DensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere12getHIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere13getHIIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere17CMZTransformationERKNS_7Vector3IdEE13
_ZNK7crpropa8Ferriere18DiskTransformationERKNS_7Vector3IdEE13
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html b/doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html deleted file mode 100644 index 0c1bd9d00..000000000 --- a/doc/coverageReport/src/massDistribution/Ferriere.cpp.func.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Ferriere.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Ferriere.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13615190.1 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa8Ferriere10getIsForH2Ev4
_ZN7crpropa8Ferriere10getIsForHIEv4
_ZN7crpropa8Ferriere10setIsForH2Eb1
_ZN7crpropa8Ferriere10setIsForHIEb1
_ZN7crpropa8Ferriere11getIsForHIIEv4
_ZN7crpropa8Ferriere11setIsForHIIEb1
_ZN7crpropa8Ferriere14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Ferriere10getDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere12getH2DensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere12getHIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere13getHIIDensityERKNS_7Vector3IdEE12
_ZNK7crpropa8Ferriere17CMZTransformationERKNS_7Vector3IdEE13
_ZNK7crpropa8Ferriere17getNucleonDensityERKNS_7Vector3IdEE5
_ZNK7crpropa8Ferriere18DiskTransformationERKNS_7Vector3IdEE13
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html deleted file mode 100644 index b32294595..000000000 --- a/doc/coverageReport/src/massDistribution/Ferriere.cpp.gcov.html +++ /dev/null @@ -1,349 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Ferriere.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Ferriere.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13615190.1 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/massDistribution/Ferriere.h"
-       2             : #include "crpropa/Common.h"
-       3             : 
-       4             : #include "kiss/logger.h"
-       5             : 
-       6             : #include <sstream>
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10          13 : Vector3d Ferriere::CMZTransformation(const Vector3d &position) const {
-      11             :         // set galactocentric coordinate system with the Sun at (-8.5,0.,0.) instead of (8.5, 0, 0) to be consistand with JF12 implementation
-      12          13 :         double x = -position.x;
-      13          13 :         double y = -position.y;
-      14             : 
-      15             :         double xC = -50*pc;             //offset
-      16             :         double yC = 50*pc;
-      17             :         double sinTc = sin(70.*deg);
-      18             :         double cosTc = cos(70.*deg);
-      19             : 
-      20             :         Vector3d pos;
-      21          13 :         pos.x = (x - xC)*cosTc + (y - yC)*sinTc;
-      22          13 :         pos.y = -(x - xC)*sinTc + (y - yC)*cosTc;
-      23          13 :         pos.z = position.z;
-      24             : 
-      25          13 :         return pos;
-      26             : }
-      27             : 
-      28          13 : Vector3d Ferriere::DiskTransformation(const Vector3d &position) const {
-      29             :         // set galactocentric coordinate system with the Sun at (-8.5,0.,0.) instead of (8.5, 0, 0) to be consistand with JF12 implementation
-      30          13 :         double x = -position.x;
-      31          13 :         double y = - position.y;
-      32          13 :         double z = position.z;
-      33             : 
-      34             :         double alphaD = 13.5*deg;  // rotation arround x-axis
-      35             :         double sinAd = sin(alphaD);
-      36             :         double cosAd = cos(alphaD);
-      37             :         double betaD = 20.*deg;  // rotation arround y'-axis
-      38             :         double sinBd = sin(betaD);
-      39             :         double cosBd = cos(betaD);
-      40             :         double TettaD = 48.5*deg;  // rotation arround x"-axis
-      41             :         double sinTd = sin(TettaD);
-      42             :         double cosTd = cos(TettaD);
-      43             : 
-      44             :         Vector3d pos;
-      45             : 
-      46          13 :         pos.x = x*cosBd*cosTd - y*(sinAd*sinBd*cosTd -cosAd*sinTd)-z*(cosAd*sinBd*cosTd +sinAd*sinTd);
-      47             : 
-      48          13 :         pos.y =  -x*cosBd*sinTd;
-      49          13 :         pos.y += y*(sinAd*sinBd*sinTd +cosAd*cosTd);
-      50          13 :         pos.y += z*(cosAd*sinBd*sinTd -sinAd*cosTd);
-      51             : 
-      52          13 :         pos.z = x*sinBd;
-      53          13 :         pos.z += y*sinAd*cosBd;
-      54          13 :         pos.z += z*cosAd*cosBd;
-      55             : 
-      56          13 :         return pos;
-      57             : }
-      58             : 
-      59          12 : double Ferriere::getHIDensity(const Vector3d &position) const {
-      60             :         double n = 0;
-      61          12 :         double R = sqrt(position.x*position.x+position.y*position.y);
-      62             : 
-      63          12 :         if(R<3*kpc)
-      64             :         {
-      65             :                 // density at center
-      66           6 :                 Vector3d pos = CMZTransformation(position);  // coordinate trafo
-      67           6 :                 double x = pos.x/pc;  // all units in pc
-      68           6 :                 double y = pos.y/pc;
-      69           6 :                 double z = pos.z/pc;
-      70             : 
-      71           6 :                 double A = sqrt(x*x+2.5*2.5*y*y);
-      72           6 :                 double nCMZ = 8.8/ccm*exp(-pow_integer<4>((A-125.)/137))*exp(-pow_integer<2>(z/54.));
-      73             : 
-      74             :                 // density in disk
-      75           6 :                 pos = DiskTransformation(position);  // Corrdinate Trafo
-      76           6 :                 x = pos.x/pc;  // all units in pc
-      77           6 :                 y = pos.y/pc;
-      78           6 :                 z = pos.z/pc;
-      79             : 
-      80           6 :                 A = sqrt(x*x+3.1*3.1*y*y);
-      81           6 :                 double nDisk = 0.34/ccm*exp(-pow_integer<4>((A-1200.)/438.))*exp(-pow_integer<2>(z/120));
-      82             : 
-      83           6 :                 n = nCMZ + nDisk;
-      84             :         }
-      85             :         else{  // outer region
-      86           6 :                 double z = position.z/pc;
-      87             :                 double a;
-      88           6 :                 if(R<=Rsun){
-      89             :                         a = 1;
-      90             :                 } else {
-      91           3 :                         a = R/Rsun;
-      92             :                 }
-      93             : 
-      94           6 :                 double nCold = 0.859*exp(-pow_integer<2>(z/(127*a))); // cold HI
-      95           6 :                 nCold += 0.047*exp(-pow_integer<2>(z/(318*a)));
-      96           6 :                 nCold += 0.094*exp(-fabs(z)/(403*a));
-      97           6 :                 nCold *= 0.340/ccm/(a*a);
-      98             : 
-      99           6 :                 double nWarm = (1.745 - 1.289/a)*exp(-pow_integer<2>(z/(127*a)));  // warm HI
-     100           6 :                 nWarm += (0.473 - 0.070/a)*exp(-pow_integer<2>(z/(318*a)));
-     101           6 :                 nWarm += (0.283 - 0.142/a)*exp(-fabs(z)/(403*a));
-     102           6 :                 nWarm *= 0.226/ccm/a;
-     103             : 
-     104           6 :                 n = nWarm + nCold;
-     105             :         }
-     106             : 
-     107          12 :         return n;
-     108             : }
-     109             : 
-     110          12 : double Ferriere::getHIIDensity(const Vector3d &position) const {
-     111             :         double n = 0;
-     112          12 :         double R = sqrt(position.x*position.x+position.y*position.y);
-     113             : 
-     114          12 :         if(R< 3*kpc){   // inner
-     115           6 :                 double x = position.x/pc;
-     116           6 :                 double y = position.y/pc;
-     117           6 :                 double z = position.z/pc;
-     118             : 
-     119             :                 // warm interstellar matter
-     120           6 :                 double H = (x*x + pow_integer<2>(y+10.))/(145*145);
-     121           6 :                 double nWIM = exp(-H)* exp(-pow_integer<2>(z+20.)/(26*26));
-     122           6 :                 nWIM += 0.009*exp(-pow_integer<2>((R/pc-3700)/(0.5*3700)))*1/pow_integer<2>(cosh(z/140.));
-     123           6 :                 nWIM += 0.005*cos(M_PI*R/pc*0.5/17000)*1/pow_integer<2>(cosh(z/950.));
-     124           6 :                 nWIM *= 8.0/ccm;  // rescaling with density at center
-     125             : 
-     126             :                 //very hot interstellar matter
-     127             :                 double alphaVH = 21.*deg;  // angle for very hot IM in radiant
-     128             :                 double cosA = cos(alphaVH);
-     129             :                 double sinA = sin(alphaVH);
-     130           6 :                 double etta = y*cosA+z*sinA;  // coordinate transformation for VHIM along major axis
-     131           6 :                 double chi = -y*sinA+z*cosA;
-     132             : 
-     133           6 :                 double nVHIM = 0.29/ccm*exp(-((x*x+etta*etta)/(162.*162.)+chi*chi/(90*90)));
-     134             : 
-     135           6 :                 n = nWIM + nVHIM;
-     136             :         } else {  // outer region
-     137           6 :                 double z = position.z;
-     138             : 
-     139           6 :                 double nWarm = 0.0237/ccm*exp(-(R*R-Rsun*Rsun)/pow_integer<2>(37*kpc))*exp(-fabs(z)/(1*kpc));
-     140           6 :                 nWarm += 0.0013/ccm*exp(-(pow_integer<2>(R-4*kpc)-pow_integer<2>(Rsun-4*kpc))/pow_integer<2>(2*kpc))*exp(-fabs(z)/(150*pc));
-     141             : 
-     142           6 :                 double nHot = 0.12*exp(-(R-Rsun)/(4.9*kpc));
-     143           6 :                 nHot += 0.88*exp(-(pow_integer<2>(R-4.5*kpc)-pow_integer<2>(Rsun-4.5*kpc))/pow_integer<2>(2.9*kpc));
-     144           6 :                 nHot *= pow(R/Rsun, -1.65);
-     145           6 :                 nHot *= exp(-fabs(z)/((1500*pc)*pow(R/Rsun,1.65)));
-     146           6 :                 nHot *= 4.8e-4/ccm;
-     147             : 
-     148           6 :                 n= nWarm + nHot;
-     149             :         }
-     150          12 :         return n;
-     151             : }
-     152             : 
-     153          12 : double Ferriere::getH2Density(const Vector3d &position) const{
-     154             :         double n=0;
-     155          12 :         double R=sqrt(position.x*position.x+position.y*position.y);
-     156             : 
-     157          12 :         if(R<3*kpc) {
-     158             :                 // density at center
-     159           6 :                 Vector3d pos =CMZTransformation(position);  // coord trafo for CMZ
-     160           6 :                 double x = pos.x/pc;  // all units in pc
-     161           6 :                 double y = pos.y/pc;
-     162           6 :                 double z = pos.z/pc;
-     163             : 
-     164           6 :                 double A = sqrt(x*x+pow(2.5*y,2));  // ellipticity
-     165           6 :                 double nCMZ = exp(-pow((A-125.)/137.,4))*exp(-pow(z/18.,2));
-     166           6 :                 nCMZ *= 150/ccm;  // rescaling
-     167             : 
-     168             :                 // density in disk
-     169           6 :                 pos = DiskTransformation(position);  // coord trafo for disk
-     170           6 :                 x=pos.x/pc;
-     171           6 :                 y=pos.y/pc;
-     172           6 :                 z=pos.z/pc;
-     173             : 
-     174           6 :                 A = sqrt(x*x+pow_integer<2>(3.1*y));
-     175           6 :                 double nDISK = exp(-pow_integer<4>((A-1200)/438))*exp(-pow_integer<2>(z/42));
-     176           6 :                 nDISK *= 4.8/ccm;  // rescaling
-     177             : 
-     178           6 :                 n = nCMZ + nDISK;
-     179             :         } else {  // outer region
-     180           6 :                 double z = position.z/pc;
-     181           6 :                 n = pow(R/Rsun, -0.58);
-     182           6 :                 n *= exp(-(pow_integer<2>(R-4.5*kpc)-pow_integer<2>(Rsun-4.5*kpc))/pow_integer<2>(2.9*kpc));
-     183           6 :                 n *= exp(-pow_integer<2>(z/(81*pow(R/Rsun,0.58))));
-     184           6 :                 n *= 0.58/ccm;  // rescaling
-     185             :         }
-     186             : 
-     187          12 :         return n;
-     188             : }
-     189             : 
-     190           5 : double Ferriere::getDensity(const Vector3d &position) const{
-     191             :         double n=0;
-     192           5 :         if(isforHI){
-     193           4 :                 n += getHIDensity(position);
-     194             :         }
-     195           5 :         if(isforHII){
-     196           4 :                 n+=getHIIDensity(position);
-     197             :         }
-     198           5 :         if(isforH2){
-     199           4 :                 n+=getH2Density(position);
-     200             :         }
-     201             :         // check if all densities are deactivated and raise warning if so
-     202           5 :         if((isforHI || isforHII || isforH2) == false){
-     203           2 :                 KISS_LOG_WARNING
-     204           1 :                         << "\nCalled getDensity on fully deactivated Ferriere \n"
-     205           1 :                         << "gas density model. The total density is set to 0.";
-     206             :         }
-     207             : 
-     208           5 :         return n;
-     209             : }
-     210             : 
-     211           5 : double Ferriere::getNucleonDensity(const Vector3d &position) const{
-     212             :         double n=0;
-     213           5 :         if(isforHI){
-     214           4 :                 n += getHIDensity(position);
-     215             :         }
-     216           5 :         if(isforHII){
-     217           4 :                 n+=getHIIDensity(position);
-     218             :         }
-     219           5 :         if(isforH2){
-     220           4 :                 n+= 2*getH2Density(position);
-     221             :         }
-     222             : 
-     223             :         // check if all densities are deactivated and raise warning if so
-     224           5 :         if((isforHI || isforHII || isforH2) == false){
-     225           2 :                 KISS_LOG_WARNING
-     226           1 :                         << "\nCalled getNucleonDensity on fully deactivated Ferriere \n"
-     227           1 :                         << "gas density model. The total density is set to 0.";
-     228             :         }
-     229             : 
-     230           5 :         return n;
-     231             : }
-     232             : 
-     233           1 : void Ferriere::setIsForHI(bool HI){
-     234           1 :         isforHI = HI;
-     235           1 : }
-     236             : 
-     237           1 : void Ferriere::setIsForHII(bool HII){
-     238           1 :         isforHII = HII;
-     239           1 : }
-     240             : 
-     241           1 : void Ferriere::setIsForH2(bool H2){
-     242           1 :         isforH2 = H2;
-     243           1 : }
-     244             : 
-     245           4 : bool Ferriere::getIsForHI(){
-     246           4 :         return isforHI;
-     247             : }
-     248             : 
-     249           4 : bool Ferriere::getIsForHII(){
-     250           4 :         return isforHII;
-     251             : }
-     252             : 
-     253           4 : bool Ferriere::getIsForH2(){
-     254           4 :         return isforH2;
-     255             : }
-     256             : 
-     257           0 : std::string Ferriere::getDescription() {
-     258           0 :         std::stringstream s;
-     259           0 :         s << "Density model Ferriere 2007:\n";
-     260           0 :         s<< "HI component is ";
-     261           0 :         if(!isforHI)
-     262           0 :                 s<< "not ";
-     263           0 :         s<< "active.\nHII component is ";
-     264           0 :         if(!isforHII)
-     265           0 :                 s<< "not ";
-     266           0 :         s<<"active.\nH2 component is ";
-     267           0 :         if(!isforH2)
-     268           0 :                 s<<"not ";
-     269           0 :         s<<"active.";
-     270           0 :         return s.str();
-     271           0 : }
-     272             : 
-     273             : }  // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html deleted file mode 100644 index bf02e8f4f..000000000 --- a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func-sort-c.html +++ /dev/null @@ -1,160 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Massdistribution.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Massdistribution.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:658576.5 %
Date:2024-04-08 14:58:22Functions:192286.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11DensityGrid14getDescriptionB5cxx11Ev0
_ZN7crpropa11DensityGrid7setGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa11DensityList14getDescriptionB5cxx11Ev0
_ZN7crpropa11DensityGrid10setIsForH2Eb1
_ZN7crpropa11DensityGrid10setIsForHIEb1
_ZN7crpropa11DensityGrid11setIsForHIIEb1
_ZNK7crpropa11DensityGrid10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityGrid17getNucleonDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getH2DensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getHIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList13getHIIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList17getNucleonDensityERKNS_7Vector3IdEE1
_ZN7crpropa11DensityGrid10getIsForH2Ev2
_ZN7crpropa11DensityGrid10getIsForHIEv2
_ZN7crpropa11DensityGrid11getIsForHIIEv2
_ZN7crpropa11DensityGridC2ENS_7ref_ptrINS_4GridIfEEEEbbb2
_ZN7crpropa11DensityList10addDensityENS_7ref_ptrINS_7DensityEEE2
_ZNK7crpropa11DensityGrid12getH2DensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid12getHIDensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid13getHIIDensityERKNS_7Vector3IdEE3
_ZN7crpropa11DensityGrid12checkAndWarnEv5
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html deleted file mode 100644 index 350b48552..000000000 --- a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.func.html +++ /dev/null @@ -1,160 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Massdistribution.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Massdistribution.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:658576.5 %
Date:2024-04-08 14:58:22Functions:192286.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11DensityGrid10getIsForH2Ev2
_ZN7crpropa11DensityGrid10getIsForHIEv2
_ZN7crpropa11DensityGrid10setIsForH2Eb1
_ZN7crpropa11DensityGrid10setIsForHIEb1
_ZN7crpropa11DensityGrid11getIsForHIIEv2
_ZN7crpropa11DensityGrid11setIsForHIIEb1
_ZN7crpropa11DensityGrid12checkAndWarnEv5
_ZN7crpropa11DensityGrid14getDescriptionB5cxx11Ev0
_ZN7crpropa11DensityGrid7setGridENS_7ref_ptrINS_4GridIfEEEE0
_ZN7crpropa11DensityGridC2ENS_7ref_ptrINS_4GridIfEEEEbbb2
_ZN7crpropa11DensityList10addDensityENS_7ref_ptrINS_7DensityEEE2
_ZN7crpropa11DensityList14getDescriptionB5cxx11Ev0
_ZNK7crpropa11DensityGrid10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityGrid12getH2DensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid12getHIDensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid13getHIIDensityERKNS_7Vector3IdEE3
_ZNK7crpropa11DensityGrid17getNucleonDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList10getDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getH2DensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList12getHIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList13getHIIDensityERKNS_7Vector3IdEE1
_ZNK7crpropa11DensityList17getNucleonDensityERKNS_7Vector3IdEE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html deleted file mode 100644 index 8d925d1a5..000000000 --- a/doc/coverageReport/src/massDistribution/Massdistribution.cpp.gcov.html +++ /dev/null @@ -1,222 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Massdistribution.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Massdistribution.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:658576.5 %
Date:2024-04-08 14:58:22Functions:192286.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/massDistribution/Massdistribution.h"
-       2             : #include <sstream>
-       3             : namespace crpropa {
-       4             : 
-       5           2 : void DensityList::addDensity(ref_ptr<Density> dens) {
-       6           2 :         DensityList.push_back(dens);
-       7           2 : }
-       8             : 
-       9           1 : double DensityList::getDensity(const Vector3d &position) const {
-      10             :         double n = 0.;
-      11           3 :         for (int i = 0; i < DensityList.size(); i++)
-      12           2 :                 n += DensityList[i]->getDensity(position);
-      13           1 :         return n;
-      14             : }
-      15             : 
-      16           1 : double DensityList::getHIDensity(const Vector3d &position) const {
-      17             :         double n = 0.;
-      18           3 :         for (int i = 0; i < DensityList.size(); i++)
-      19           2 :                 n += DensityList[i]->getHIDensity(position);
-      20           1 :         return n;
-      21             : }
-      22             : 
-      23           1 : double DensityList::getHIIDensity(const Vector3d &position) const {
-      24             :         double n = 0.;
-      25           3 :         for (int i = 0; i < DensityList.size(); i++)
-      26           2 :                 n += DensityList[i]->getHIIDensity(position);
-      27           1 :         return n;
-      28             : }
-      29             : 
-      30           1 : double DensityList::getH2Density(const Vector3d &position) const {
-      31             :         double n = 0.;
-      32           3 :         for (int i = 0; i < DensityList.size(); i++)
-      33           2 :                 n += DensityList[i]->getH2Density(position);
-      34           1 :         return n;
-      35             : }
-      36             : 
-      37           1 : double DensityList::getNucleonDensity(const Vector3d &position) const {
-      38             :         double n = 0.;
-      39           3 :         for (int i = 0; i < DensityList.size(); i++)
-      40           2 :                 n += DensityList[i]->getNucleonDensity(position);
-      41           1 :         return n;
-      42             : }
-      43             : 
-      44           0 : std::string DensityList::getDescription() {
-      45           0 :         std::stringstream ss; 
-      46           0 :         ss << "DensityList with " << DensityList.size() << " modules: \n";
-      47           0 :         for (int i = 0; i < DensityList.size(); i++) {
-      48           0 :                 ss << "density " << i + 1 << ": " << DensityList[i] -> getDescription();
-      49             :         }
-      50             :         
-      51           0 :         return ss.str();
-      52           0 : }
-      53             : 
-      54             : // ----------- DensityGrid -----------------------------------------------------------------
-      55             : 
-      56           2 : DensityGrid::DensityGrid(ref_ptr<Grid1f> grid, bool isForHI, bool isForHII, bool isForH2) : 
-      57           2 :         grid(grid), isForHI(isForHI), isForHII(isForHII), isForH2(isForH2) {
-      58           2 :                 checkAndWarn();
-      59           2 :         }
-      60             : 
-      61           5 : void DensityGrid::checkAndWarn() {
-      62           5 :         bool allDeactivated = (isForHI == false) && (isForHII == false) && (isForH2 == false);
-      63             :         if (allDeactivated) {
-      64           0 :                 KISS_LOG_WARNING << "DensityGrid has all types deactivated."
-      65           0 :                         << "In this case all output will be n = 0. \n"
-      66           0 :                         << "Please activate the intended particle type. \n";
-      67             :         }
-      68           5 : }
-      69             : 
-      70           3 : double DensityGrid::getHIDensity(const Vector3d &position) const {
-      71           3 :         if (isForHI)
-      72           3 :                 return grid -> interpolate(position);
-      73             :         else 
-      74             :                 return 0.;
-      75             : }
-      76             : 
-      77           3 : double DensityGrid::getHIIDensity(const Vector3d &position) const {
-      78           3 :         if (isForHII) 
-      79           0 :                 return grid -> interpolate(position);
-      80             :         else
-      81             :                 return 0.;
-      82             : }
-      83             : 
-      84           3 : double DensityGrid::getH2Density(const Vector3d &position) const {
-      85           3 :         if (isForH2)
-      86           0 :                 return grid -> interpolate(position);
-      87             :         else
-      88             :                 return 0.;
-      89             : }
-      90             : 
-      91           1 : double DensityGrid::getDensity(const Vector3d &position) const {
-      92             :         double n = 0;
-      93           1 :         n += getHIDensity(position);
-      94           1 :         n += getHIIDensity(position);
-      95           1 :         n += getH2Density(position);
-      96             : 
-      97           1 :         return n;
-      98             : }
-      99             : 
-     100           1 : double DensityGrid::getNucleonDensity(const Vector3d &position) const {
-     101             :         double n = 0;
-     102           1 :         n += getHIDensity(position);
-     103           1 :         n += getHIIDensity(position);
-     104           1 :         n += 2 * getH2Density(position);
-     105             : 
-     106           1 :         return n;
-     107             : }
-     108             : 
-     109           2 : bool DensityGrid::getIsForHI() {
-     110           2 :         return isForHI;
-     111             : }
-     112             : 
-     113           2 : bool DensityGrid::getIsForHII() {
-     114           2 :         return isForHII;
-     115             : }
-     116             : 
-     117           2 : bool DensityGrid::getIsForH2() {
-     118           2 :         return isForH2;
-     119             : }
-     120             : 
-     121           1 : void DensityGrid::setIsForHI(bool b) {
-     122           1 :         isForHI = b;
-     123           1 :         checkAndWarn();
-     124           1 : }
-     125             : 
-     126           1 : void DensityGrid::setIsForHII(bool b) {
-     127           1 :         isForHII = b;
-     128           1 :         checkAndWarn();
-     129           1 : }
-     130             : 
-     131           1 : void DensityGrid::setIsForH2(bool b) {
-     132           1 :         isForH2 = b;
-     133           1 :         checkAndWarn();
-     134           1 : }
-     135             : 
-     136           0 : void DensityGrid::setGrid(ref_ptr<Grid1f> grid) {
-     137           0 :         this->grid = grid;
-     138           0 : }
-     139             : 
-     140           0 : std::string DensityGrid::getDescription() {
-     141           0 :         std::stringstream ss;
-     142           0 :         ss << "Density in a given grid \n"; 
-     143           0 :         return ss.str();
-     144           0 : }
-     145             : 
-     146             : } //namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html deleted file mode 100644 index 6cf5bc02a..000000000 --- a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func-sort-c.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Nakanishi.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Nakanishi.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:587082.9 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Nakanishi14getDescriptionB5cxx11Ev0
_ZN7crpropa9Nakanishi10setIsForH2Eb1
_ZN7crpropa9Nakanishi10setIsForHIEb1
_ZN7crpropa9Nakanishi11getIsForHIIEv1
_ZN7crpropa9Nakanishi10getIsForH2Ev3
_ZN7crpropa9Nakanishi10getIsForHIEv3
_ZNK7crpropa9Nakanishi10getDensityERKNS_7Vector3IdEE3
_ZNK7crpropa9Nakanishi17getNucleonDensityERKNS_7Vector3IdEE3
_ZNK7crpropa9Nakanishi12getH2DensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi12getHIDensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi16getH2ScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi16getHIScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getH2PlanedensityERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getHIPlanedensityERKNS_7Vector3IdEE8
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html deleted file mode 100644 index 13484a861..000000000 --- a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.func.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Nakanishi.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Nakanishi.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:587082.9 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa9Nakanishi10getIsForH2Ev3
_ZN7crpropa9Nakanishi10getIsForHIEv3
_ZN7crpropa9Nakanishi10setIsForH2Eb1
_ZN7crpropa9Nakanishi10setIsForHIEb1
_ZN7crpropa9Nakanishi11getIsForHIIEv1
_ZN7crpropa9Nakanishi14getDescriptionB5cxx11Ev0
_ZNK7crpropa9Nakanishi10getDensityERKNS_7Vector3IdEE3
_ZNK7crpropa9Nakanishi12getH2DensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi12getHIDensityERKNS_7Vector3IdEE6
_ZNK7crpropa9Nakanishi16getH2ScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi16getHIScaleheightERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getH2PlanedensityERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getHIPlanedensityERKNS_7Vector3IdEE8
_ZNK7crpropa9Nakanishi17getNucleonDensityERKNS_7Vector3IdEE3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html b/doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html deleted file mode 100644 index 79649cf3d..000000000 --- a/doc/coverageReport/src/massDistribution/Nakanishi.cpp.gcov.html +++ /dev/null @@ -1,195 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution/Nakanishi.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistribution - Nakanishi.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:587082.9 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/massDistribution/Nakanishi.h"
-       2             : #include "crpropa/Common.h"
-       3             : 
-       4             : #include "kiss/logger.h"
-       5             : 
-       6             : #include <sstream>
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10           8 : double Nakanishi::getHIScaleheight(const Vector3d &position) const {
-      11           8 :         double R = sqrt(pow_integer<2>(position.x)+pow_integer<2>(position.y));      // radius in galactic plane
-      12           8 :         double scaleheight = 1.06*pc*(116.3 +19.3*R/kpc+4.1*pow_integer<2>(R/kpc)-0.05*pow_integer<3>(R/kpc));
-      13           8 :         return scaleheight;
-      14             :         }
-      15             : 
-      16           8 : double Nakanishi::getHIPlanedensity(const Vector3d &position) const {
-      17           8 :         double R = sqrt(pow_integer<2>(position.x)+pow_integer<2>(position.y));      // radius in galactic plane
-      18           8 :         double planedensity = 0.94/ccm*(0.6*exp(-R/(2.4*kpc))+0.24*exp(-pow_integer<2>((R-9.5*kpc)/(4.8*kpc))));
-      19           8 :         return planedensity;
-      20             :         }
-      21             : 
-      22             : 
-      23           8 : double Nakanishi::getH2Scaleheight(const Vector3d &position) const {
-      24           8 :         double R = sqrt(pow_integer<2>(position.x)+ pow_integer<2>(position.y));  // radius in galactic plane
-      25           8 :         double scaleheight = 1.06*pc*( 10.8*exp(0.28*R/kpc)+42.78);
-      26           8 :         return scaleheight;
-      27             : }
-      28             : 
-      29           8 : double Nakanishi::getH2Planedensity(const Vector3d &position) const {
-      30           8 :         double R = sqrt(pow_integer<2>(position.x)+pow_integer<2>(position.y));  // radius in galactic plane
-      31           8 :         double planedensity =0.94/ccm*(11.2*exp(-R*R/(0.874*kpc*kpc)) +0.83*exp(-pow_integer<2>((R-4*kpc)/(3.2*kpc))));
-      32           8 :         return planedensity;
-      33             : }
-      34             : 
-      35           6 : double Nakanishi::getHIDensity(const Vector3d &position) const {
-      36             :         double n = 0;  // density
-      37           6 :         double planedensity = getHIPlanedensity(position);
-      38           6 :         double scaleheight = getHIScaleheight(position);
-      39           6 :         n = planedensity*pow(0.5,pow_integer<2>(position.z/scaleheight));
-      40             : 
-      41           6 :         return n;
-      42             : }
-      43             : 
-      44           6 : double Nakanishi::getH2Density(const Vector3d &position) const {
-      45             :         double n = 0;  // density
-      46           6 :         double planedensity = getH2Planedensity(position);
-      47           6 :         double scaleheight = getH2Scaleheight(position);
-      48           6 :         n = planedensity*pow(0.5,pow_integer<2>(position.z/scaleheight));
-      49             : 
-      50           6 :         return n;
-      51             : }
-      52             : 
-      53           3 : double Nakanishi::getDensity(const Vector3d &position) const {
-      54             :         double n = 0;
-      55           3 :         if(isforHI)
-      56           2 :                 n += getHIDensity(position);
-      57           3 :         if(isforH2)
-      58           2 :                 n += getH2Density(position);
-      59             :         
-      60             :         // check if all densities are deactivated and raise warning if so
-      61           3 :         if((isforHI || isforH2) == false){
-      62           2 :                 KISS_LOG_WARNING
-      63           1 :                         << "\n"<<"Called getDensity on fully deactivated Nakanishi \n"
-      64           1 :                         << "gas density model. The total density is set to 0.";
-      65             :         }
-      66           3 :         return n;
-      67             : }
-      68             : 
-      69           3 : double Nakanishi::getNucleonDensity(const Vector3d &position) const {
-      70             :         double n = 0;
-      71           3 :         if(isforHI)
-      72           2 :                 n += getHIDensity(position);
-      73           3 :         if(isforH2)
-      74           2 :                 n += 2*getH2Density(position);  // weight 2 for molecular hydrogen
-      75             : 
-      76             :         // check if all densities are deactivated and raise warning if so
-      77           3 :         if((isforHI || isforH2) == false){
-      78           2 :                 KISS_LOG_WARNING
-      79           1 :                         << "\n"<<"Called getNucleonDensity on fully deactivated Nakanishi \n"
-      80           1 :                         << "gas density model. The total density is set to 0.";
-      81             :         }
-      82             : 
-      83           3 :         return n;
-      84             : }
-      85             : 
-      86           3 : bool Nakanishi::getIsForHI() {
-      87           3 :         return isforHI;
-      88             : }
-      89             : 
-      90           1 : bool Nakanishi::getIsForHII() {
-      91           1 :         return isforHII;
-      92             : }
-      93           3 : bool Nakanishi::getIsForH2() {
-      94           3 :         return isforH2;
-      95             : }
-      96             : 
-      97           1 : void Nakanishi::setIsForHI(bool HI) {
-      98           1 :         isforHI = HI;
-      99           1 : }
-     100             : 
-     101           1 : void Nakanishi::setIsForH2(bool H2) {
-     102           1 :         isforH2 = H2;
-     103           1 : }
-     104             : 
-     105           0 : std::string Nakanishi::getDescription() {
-     106           0 :         std::stringstream s;
-     107           0 :         s << "Density model Nakanishi:\n";
-     108           0 :         s<< "HI component is ";
-     109           0 :         if(isforHI==false)
-     110           0 :                 s<< "not ";
-     111           0 :         s<< "active.\nH2 component is ";
-     112           0 :         if(isforH2==false)
-     113           0 :                 s<<"not ";
-     114           0 :         s<<"active.\nNakanishi has no HII component.";
-     115             : 
-     116           0 :         return s.str();
-     117           0 : }
-     118             : 
-     119             : }  // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/index-sort-f.html b/doc/coverageReport/src/massDistribution/index-sort-f.html deleted file mode 100644 index 8608e5fe2..000000000 --- a/doc/coverageReport/src/massDistribution/index-sort-f.html +++ /dev/null @@ -1,133 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:34941683.9 %
Date:2024-04-08 14:58:22Functions:697690.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Cordes.cpp -
76.2%76.2%
-
76.2 %16 / 2185.7 %6 / 7
Massdistribution.cpp -
76.5%76.5%
-
76.5 %65 / 8586.4 %19 / 22
Ferriere.cpp -
90.1%90.1%
-
90.1 %136 / 15192.9 %13 / 14
Nakanishi.cpp -
82.9%82.9%
-
82.9 %58 / 7092.9 %13 / 14
ConstantDensity.cpp -
83.1%83.1%
-
83.1 %74 / 8994.7 %18 / 19
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/index-sort-l.html b/doc/coverageReport/src/massDistribution/index-sort-l.html deleted file mode 100644 index 9ce5836f7..000000000 --- a/doc/coverageReport/src/massDistribution/index-sort-l.html +++ /dev/null @@ -1,133 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:34941683.9 %
Date:2024-04-08 14:58:22Functions:697690.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Cordes.cpp -
76.2%76.2%
-
76.2 %16 / 2185.7 %6 / 7
Massdistribution.cpp -
76.5%76.5%
-
76.5 %65 / 8586.4 %19 / 22
Nakanishi.cpp -
82.9%82.9%
-
82.9 %58 / 7092.9 %13 / 14
ConstantDensity.cpp -
83.1%83.1%
-
83.1 %74 / 8994.7 %18 / 19
Ferriere.cpp -
90.1%90.1%
-
90.1 %136 / 15192.9 %13 / 14
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/massDistribution/index.html b/doc/coverageReport/src/massDistribution/index.html deleted file mode 100644 index dbbcaaf42..000000000 --- a/doc/coverageReport/src/massDistribution/index.html +++ /dev/null @@ -1,133 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/massDistribution - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/massDistributionHitTotalCoverage
Test:coverage.info.cleanedLines:34941683.9 %
Date:2024-04-08 14:58:22Functions:697690.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
ConstantDensity.cpp -
83.1%83.1%
-
83.1 %74 / 8994.7 %18 / 19
Cordes.cpp -
76.2%76.2%
-
76.2 %16 / 2185.7 %6 / 7
Ferriere.cpp -
90.1%90.1%
-
90.1 %136 / 15192.9 %13 / 14
Massdistribution.cpp -
76.5%76.5%
-
76.5 %65 / 8586.4 %19 / 22
Nakanishi.cpp -
82.9%82.9%
-
82.9 %58 / 7092.9 %13 / 14
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html b/doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html deleted file mode 100644 index dcbc5453c..000000000 --- a/doc/coverageReport/src/module/Acceleration.cpp.func-sort-c.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Acceleration.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Acceleration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0890.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16SecondOrderFermiC2Eddj0
_ZN7crpropa17ParticleSplittingC2EPNS_7SurfaceEiidNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa17QuasiLinearTheory6modifyEdPNS_9CandidateE0
_ZN7crpropa17QuasiLinearTheoryC2Eddd0
_ZN7crpropa22DirectedFlowScatteringC2ENS_7Vector3IdEEd0
_ZN7crpropa26AbstractAccelerationModule3addEPNS_18StepLengthModifierE0
_ZN7crpropa26AbstractAccelerationModuleC2Ed0
_ZN7crpropa28DirectedFlowOfScatterCenters6modifyEdPNS_9CandidateE0
_ZN7crpropa28DirectedFlowOfScatterCentersC2ERKNS_7Vector3IdEE0
_ZNK7crpropa16SecondOrderFermi21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa17ParticleSplitting7processEPNS_9CandidateE0
_ZNK7crpropa22DirectedFlowScattering21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7processEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7scatterEPNS_9CandidateERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Acceleration.cpp.func.html b/doc/coverageReport/src/module/Acceleration.cpp.func.html deleted file mode 100644 index d528f5cfc..000000000 --- a/doc/coverageReport/src/module/Acceleration.cpp.func.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Acceleration.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Acceleration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0890.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16SecondOrderFermiC2Eddj0
_ZN7crpropa17ParticleSplittingC2EPNS_7SurfaceEiidNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa17QuasiLinearTheory6modifyEdPNS_9CandidateE0
_ZN7crpropa17QuasiLinearTheoryC2Eddd0
_ZN7crpropa22DirectedFlowScatteringC2ENS_7Vector3IdEEd0
_ZN7crpropa26AbstractAccelerationModule3addEPNS_18StepLengthModifierE0
_ZN7crpropa26AbstractAccelerationModuleC2Ed0
_ZN7crpropa28DirectedFlowOfScatterCenters6modifyEdPNS_9CandidateE0
_ZN7crpropa28DirectedFlowOfScatterCentersC2ERKNS_7Vector3IdEE0
_ZNK7crpropa16SecondOrderFermi21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa17ParticleSplitting7processEPNS_9CandidateE0
_ZNK7crpropa22DirectedFlowScattering21scatterCenterVelocityEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7processEPNS_9CandidateE0
_ZNK7crpropa26AbstractAccelerationModule7scatterEPNS_9CandidateERKNS_7Vector3IdEE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Acceleration.cpp.gcov.html b/doc/coverageReport/src/module/Acceleration.cpp.gcov.html deleted file mode 100644 index 11ea17011..000000000 --- a/doc/coverageReport/src/module/Acceleration.cpp.gcov.html +++ /dev/null @@ -1,260 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Acceleration.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Acceleration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0890.0 %
Date:2024-04-08 14:58:22Functions:0140.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/Acceleration.h"
-       2             : #include <crpropa/Common.h>
-       3             : #include <crpropa/Random.h>
-       4             : #include <cmath>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           0 : AbstractAccelerationModule::AbstractAccelerationModule(double _stepLength)
-       9           0 :         : crpropa::Module(), stepLength(_stepLength) {}
-      10             : 
-      11             : 
-      12           0 : void AbstractAccelerationModule::add(StepLengthModifier *modifier) {
-      13           0 :         modifiers.push_back(modifier);
-      14           0 : }
-      15             : 
-      16             : 
-      17           0 : void AbstractAccelerationModule::scatter(
-      18             :         crpropa::Candidate *candidate,
-      19             :         const crpropa::Vector3d &scatter_center_velocity) const {
-      20             :         // particle momentum in lab frame
-      21           0 :         const double E = candidate->current.getEnergy();
-      22           0 :         const crpropa::Vector3d p = candidate->current.getMomentum();
-      23             : 
-      24             :         // transform to rest frame of scatter center (p: prime)
-      25           0 :         const double beta = scatter_center_velocity.getR() / crpropa::c_light;
-      26           0 :         const double gamma = 1. / sqrt(1 - beta * beta);
-      27           0 :         const double Ep = gamma * (E - scatter_center_velocity.dot(p));
-      28             :         const crpropa::Vector3d pp = (p - scatter_center_velocity* E /
-      29             :                 (crpropa::c_light * crpropa::c_light)) * gamma;
-      30             : 
-      31             :         // scatter into random direction
-      32           0 :         const crpropa::Vector3d pp_new = crpropa::Random::instance().randVector() * pp.getR();
-      33             : 
-      34             :         // transform back
-      35           0 :         const double E_new = gamma * (Ep + scatter_center_velocity.dot(pp_new));
-      36             :         const crpropa::Vector3d p_new = (pp_new + scatter_center_velocity * Ep /
-      37             :                 (crpropa::c_light * crpropa::c_light)) * gamma;
-      38             : 
-      39             :         // update candidate properties
-      40           0 :         candidate->current.setEnergy(E_new);
-      41           0 :         candidate->current.setDirection(p_new / p_new.getR());
-      42           0 : }
-      43             : 
-      44             : 
-      45           0 : void AbstractAccelerationModule::process(crpropa::Candidate *candidate) const {
-      46           0 :         double currentStepLength = stepLength;
-      47           0 :         for (auto m : modifiers) {
-      48           0 :                 currentStepLength = m->modify(currentStepLength, candidate);
-      49             :         }
-      50             : 
-      51           0 :         double step = candidate->getCurrentStep();
-      52           0 :         while (step > 0) {
-      53           0 :                 double randDistance = -1. * log(crpropa::Random::instance().rand()) * currentStepLength;
-      54             : 
-      55           0 :                 if (step < randDistance) {
-      56           0 :                         candidate->limitNextStep(0.1 * currentStepLength);
-      57           0 :                         return;
-      58             :                 }
-      59           0 :                 scatter(candidate, scatterCenterVelocity(candidate));
-      60           0 :                 step -= randDistance;
-      61             :         }
-      62             : }
-      63             : 
-      64             : 
-      65           0 : SecondOrderFermi::SecondOrderFermi(double scatterVelocity, double stepLength,
-      66           0 :                                                                    unsigned int sizeOfPitchangleTable)
-      67             :         : AbstractAccelerationModule(stepLength),
-      68           0 :           scatterVelocity(scatterVelocity) {
-      69           0 :         setDescription("SecondOrderFermi Acceleration");
-      70           0 :         angle.resize(sizeOfPitchangleTable);
-      71           0 :         angleCDF.resize(sizeOfPitchangleTable);
-      72             : 
-      73             :         // have a discretized table of beamed pitch angles
-      74           0 :         for (unsigned int i =0; i < sizeOfPitchangleTable; i++) {
-      75           0 :                 angle[i] = i * M_PI / (sizeOfPitchangleTable-1);
-      76           0 :                 angleCDF[i] = (angle[i] +scatterVelocity / crpropa::c_light * sin(angle[i])) / M_PI;
-      77             :         }
-      78           0 : }
-      79             : 
-      80             : 
-      81           0 : crpropa::Vector3d SecondOrderFermi::scatterCenterVelocity(crpropa::Candidate *candidate) const
-      82             : {
-      83           0 :         size_t idx = crpropa::closestIndex(crpropa::Random::instance().rand(), angleCDF);
-      84           0 :         crpropa::Vector3d rv = crpropa::Random::instance().randVector();
-      85           0 :         crpropa::Vector3d rotationAxis = candidate->current.getDirection().cross(rv);
-      86             : 
-      87           0 :         rv = candidate->current.getDirection().getRotated(rotationAxis, M_PI - angle[idx]);
-      88           0 :         return rv * scatterVelocity;
-      89             : }
-      90             : 
-      91             : 
-      92           0 : DirectedFlowOfScatterCenters::DirectedFlowOfScatterCenters(
-      93           0 :         const Vector3d &scatterCenterVelocity)
-      94           0 :         : __scatterVelocity(scatterCenterVelocity) {}
-      95             : 
-      96             : 
-      97           0 : double DirectedFlowOfScatterCenters::modify(double steplength, Candidate* candidate)
-      98             : {
-      99           0 :         double directionModifier = (-1. * __scatterVelocity.dot(candidate->current.getDirection()) + c_light) / c_light;
-     100           0 :         return steplength / directionModifier;
-     101             : }
-     102             : 
-     103             : 
-     104           0 : DirectedFlowScattering::DirectedFlowScattering(
-     105           0 :         crpropa::Vector3d scatterCenterVelocity, double stepLength)
-     106           0 :         : __scatterVelocity(scatterCenterVelocity),
-     107           0 :           AbstractAccelerationModule(stepLength) {
-     108             : 
-     109             :         // In a directed field of scatter centers, the probability to encounter a
-     110             :         // scatter center depends on the direction of the candidate.
-     111           0 :         StepLengthModifier *mod = new DirectedFlowOfScatterCenters(__scatterVelocity);
-     112           0 :         this->add(mod);
-     113           0 : }
-     114             : 
-     115             : 
-     116           0 : crpropa::Vector3d DirectedFlowScattering::scatterCenterVelocity(
-     117             :         crpropa::Candidate *candidate) const { // does not depend on candidate here.
-     118           0 :         return __scatterVelocity;
-     119             : }
-     120             : 
-     121             : 
-     122           0 : QuasiLinearTheory::QuasiLinearTheory(double referenecEnergy,
-     123             :                                                                          double turbulenceIndex,
-     124           0 :                                                                          double minimumRigidity)
-     125           0 :         : __referenceEnergy(referenecEnergy), __turbulenceIndex(turbulenceIndex),
-     126           0 :           __minimumRigidity(minimumRigidity) {}
-     127             : 
-     128             : 
-     129           0 : double QuasiLinearTheory::modify(double steplength, Candidate* candidate)
-     130             : {
-     131           0 :         if (candidate->current.getRigidity() < __minimumRigidity)
-     132             :         {
-     133           0 :                 return steplength * std::pow(__minimumRigidity /
-     134           0 :                         (__referenceEnergy / eV), 2. - __turbulenceIndex);
-     135             :         }
-     136             :         else
-     137             :         {
-     138           0 :                 return steplength * std::pow(candidate->current.getRigidity() /
-     139           0 :                         (__referenceEnergy / eV), 2. - __turbulenceIndex);
-     140             :         }
-     141             : }
-     142             : 
-     143             : 
-     144           0 : ParticleSplitting::ParticleSplitting(Surface *surface, int      crossingThreshold, 
-     145           0 :         int numberSplits, double minWeight, std::string counterid)
-     146           0 :         : surface(surface), crossingThreshold(crossingThreshold),
-     147           0 :           numberSplits(numberSplits), minWeight(minWeight), counterid(counterid){};
-     148             : 
-     149           0 : void ParticleSplitting::process(Candidate *candidate) const {
-     150             :         const double currentDistance =
-     151           0 :                 surface->distance(candidate->current.getPosition());
-     152             :         const double previousDistance =
-     153           0 :                 surface->distance(candidate->previous.getPosition());
-     154             : 
-     155           0 :         if (currentDistance * previousDistance > 0)
-     156             :                 // candidate remains on the same side
-     157             :                 return;
-     158             : 
-     159           0 :         if (candidate->getWeight() < minWeight)
-     160             :                 return;
-     161             : 
-     162             :         int num_crossings = 1;
-     163           0 :         if (candidate->hasProperty(counterid))
-     164           0 :                 num_crossings = candidate->getProperty(counterid).toInt32() + 1;
-     165           0 :         candidate->setProperty(counterid, num_crossings);
-     166             : 
-     167           0 :         if (num_crossings % crossingThreshold != 0)
-     168             :                 return;
-     169             : 
-     170           0 :         candidate->updateWeight(1. / numberSplits);
-     171             : 
-     172           0 :         for (size_t i = 1; i < numberSplits; i++) {
-     173             :                 // No recursive split as the weights of the secondaries created
-     174             :                 // before the split are not affected
-     175           0 :                 ref_ptr<Candidate> new_candidate = candidate->clone(false);
-     176           0 :                 new_candidate->parent = candidate;
-     177           0 :                 uint64_t snr = Candidate::getNextSerialNumber();
-     178           0 :                 Candidate::setNextSerialNumber(snr + 1);
-     179           0 :                 new_candidate->setSerialNumber(snr);
-     180             :                 candidate->addSecondary(new_candidate);
-     181             :         }
-     182             : };
-     183             : 
-     184             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html b/doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html deleted file mode 100644 index d39555576..000000000 --- a/doc/coverageReport/src/module/AdiabaticCooling.cpp.func-sort-c.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/AdiabaticCooling.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - AdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:232785.2 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEEd1
_ZNK7crpropa16AdiabaticCooling8getLimitEv1
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEE2
_ZNK7crpropa16AdiabaticCooling7processEPNS_9CandidateE2
_ZN7crpropa16AdiabaticCooling8setLimitEd3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html b/doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html deleted file mode 100644 index c94a74943..000000000 --- a/doc/coverageReport/src/module/AdiabaticCooling.cpp.func.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/AdiabaticCooling.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - AdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:232785.2 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16AdiabaticCooling8setLimitEd3
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEE2
_ZN7crpropa16AdiabaticCoolingC2ENS_7ref_ptrINS_14AdvectionFieldEEEd1
_ZNK7crpropa16AdiabaticCooling7processEPNS_9CandidateE2
_ZNK7crpropa16AdiabaticCooling8getLimitEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html b/doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html deleted file mode 100644 index 1a9adcc18..000000000 --- a/doc/coverageReport/src/module/AdiabaticCooling.cpp.gcov.html +++ /dev/null @@ -1,130 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/AdiabaticCooling.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - AdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:232785.2 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/AdiabaticCooling.h"
-       2             : 
-       3             : namespace crpropa {
-       4             : 
-       5           2 : AdiabaticCooling::AdiabaticCooling(ref_ptr<AdvectionField> advectionField) :
-       6           2 :         advectionField(advectionField) {
-       7           2 :         setLimit(0.1);
-       8           2 : }
-       9             : 
-      10           1 : AdiabaticCooling::AdiabaticCooling(ref_ptr<AdvectionField> advectionField, double limit) :
-      11           1 :         advectionField(advectionField) {
-      12           1 :         setLimit(limit);
-      13           1 : }
-      14             : 
-      15           2 : void AdiabaticCooling::process(Candidate *c) const {
-      16             : 
-      17           2 :         Vector3d pos = c->current.getPosition();
-      18           2 :         double E = c->current.getEnergy(); // Note we use E=p/c (relativistic limit)
-      19             :         
-      20             :         double Div = 0.;        
-      21             :         try {
-      22           2 :                 Div +=  advectionField->getDivergence(pos);
-      23             :         } 
-      24           0 :         catch (std::exception &e) {
-      25           0 :                 KISS_LOG_ERROR  << "AdiabaticCooling: Exception in getDivergence.\n" 
-      26           0 :                                 << e.what();
-      27           0 :         }
-      28             :         
-      29           2 :         double dEdt = -E / 3. * Div;    // cooling due to advection -p/3 * div(V_wind)
-      30             :                                         // (see e.g. Kopp et al. Computer Physics Communication 183
-      31             :                                         // (2012) 530-542)
-      32           2 :         double dt = c->getCurrentStep() / c_light;
-      33           2 :         double dE = dEdt * dt;
-      34             :         
-      35           2 :         c->current.setEnergy(E + dE);
-      36           2 :         if (dEdt==0) {
-      37             :                 return;
-      38             :         }       
-      39           1 :         c->limitNextStep(limit * E / fabs(dEdt) *c_light);
-      40             : }
-      41             : 
-      42           3 : void AdiabaticCooling::setLimit(double l) {
-      43           3 :         limit = l;
-      44           3 : }
-      45             : 
-      46           1 : double AdiabaticCooling::getLimit() const {
-      47           1 :         return limit;
-      48             : }
-      49             :         
-      50             :         
-      51             : 
-      52             : 
-      53             : 
-      54             : } // end namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html b/doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html deleted file mode 100644 index 402ed01de..000000000 --- a/doc/coverageReport/src/module/Boundary.cpp.func-sort-c.html +++ /dev/null @@ -1,252 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Boundary.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Boundary.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10621948.4 %
Date:2024-04-08 14:58:22Functions:204544.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11PeriodicBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBoxC2Ev0
_ZN7crpropa13CubicBoundary7setSizeEd0
_ZN7crpropa13CubicBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa13CubicBoundaryC2Ev0
_ZN7crpropa13ReflectiveBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBoxC2Ev0
_ZN7crpropa17SphericalBoundary9setCenterENS_7Vector3IdEE0
_ZN7crpropa17SphericalBoundary9setRadiusEd0
_ZN7crpropa17SphericalBoundaryC2Ev0
_ZN7crpropa19CylindricalBoundary9setHeightEd0
_ZN7crpropa19CylindricalBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa19CylindricalBoundary9setRadiusEd0
_ZN7crpropa19CylindricalBoundaryC2Ev0
_ZN7crpropa19EllipsoidalBoundary12setMajorAxisEd0
_ZN7crpropa19EllipsoidalBoundary14setFocalPointsENS_7Vector3IdEES2_0
_ZN7crpropa19EllipsoidalBoundaryC2Ev0
_ZNK7crpropa11PeriodicBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa13CubicBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ReflectiveBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SphericalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19CylindricalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19EllipsoidalBoundary14getDescriptionB5cxx11Ev0
_ZN7crpropa13ReflectiveBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa17SphericalBoundary12setLimitStepEb1
_ZN7crpropa17SphericalBoundary9setMarginEd1
_ZN7crpropa19CylindricalBoundary12setLimitStepEb1
_ZN7crpropa19CylindricalBoundary9setMarginEd1
_ZN7crpropa19EllipsoidalBoundary12setLimitStepEb1
_ZN7crpropa19EllipsoidalBoundary9setMarginEd1
_ZNK7crpropa13ReflectiveBox7processEPNS_9CandidateE1
_ZN7crpropa11PeriodicBoxC2ENS_7Vector3IdEES2_2
_ZN7crpropa13CubicBoundary12setLimitStepEb2
_ZN7crpropa13CubicBoundary9setMarginEd2
_ZNK7crpropa11PeriodicBox7processEPNS_9CandidateE2
_ZN7crpropa17SphericalBoundaryC2ENS_7Vector3IdEEd3
_ZN7crpropa19CylindricalBoundaryC2ENS_7Vector3IdEEdd3
_ZN7crpropa19EllipsoidalBoundaryC2ENS_7Vector3IdEES2_d3
_ZNK7crpropa17SphericalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19CylindricalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19EllipsoidalBoundary7processEPNS_9CandidateE3
_ZN7crpropa13CubicBoundaryC2ENS_7Vector3IdEEd4
_ZNK7crpropa13CubicBoundary7processEPNS_9CandidateE4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Boundary.cpp.func.html b/doc/coverageReport/src/module/Boundary.cpp.func.html deleted file mode 100644 index faa7abed3..000000000 --- a/doc/coverageReport/src/module/Boundary.cpp.func.html +++ /dev/null @@ -1,252 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Boundary.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Boundary.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10621948.4 %
Date:2024-04-08 14:58:22Functions:204544.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa11PeriodicBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa11PeriodicBoxC2ENS_7Vector3IdEES2_2
_ZN7crpropa11PeriodicBoxC2Ev0
_ZN7crpropa13CubicBoundary12setLimitStepEb2
_ZN7crpropa13CubicBoundary7setSizeEd0
_ZN7crpropa13CubicBoundary9setMarginEd2
_ZN7crpropa13CubicBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa13CubicBoundaryC2ENS_7Vector3IdEEd4
_ZN7crpropa13CubicBoundaryC2Ev0
_ZN7crpropa13ReflectiveBox7setSizeENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBox9setOriginENS_7Vector3IdEE0
_ZN7crpropa13ReflectiveBoxC2ENS_7Vector3IdEES2_1
_ZN7crpropa13ReflectiveBoxC2Ev0
_ZN7crpropa17SphericalBoundary12setLimitStepEb1
_ZN7crpropa17SphericalBoundary9setCenterENS_7Vector3IdEE0
_ZN7crpropa17SphericalBoundary9setMarginEd1
_ZN7crpropa17SphericalBoundary9setRadiusEd0
_ZN7crpropa17SphericalBoundaryC2ENS_7Vector3IdEEd3
_ZN7crpropa17SphericalBoundaryC2Ev0
_ZN7crpropa19CylindricalBoundary12setLimitStepEb1
_ZN7crpropa19CylindricalBoundary9setHeightEd0
_ZN7crpropa19CylindricalBoundary9setMarginEd1
_ZN7crpropa19CylindricalBoundary9setOriginENS_7Vector3IdEE0
_ZN7crpropa19CylindricalBoundary9setRadiusEd0
_ZN7crpropa19CylindricalBoundaryC2ENS_7Vector3IdEEdd3
_ZN7crpropa19CylindricalBoundaryC2Ev0
_ZN7crpropa19EllipsoidalBoundary12setLimitStepEb1
_ZN7crpropa19EllipsoidalBoundary12setMajorAxisEd0
_ZN7crpropa19EllipsoidalBoundary14setFocalPointsENS_7Vector3IdEES2_0
_ZN7crpropa19EllipsoidalBoundary9setMarginEd1
_ZN7crpropa19EllipsoidalBoundaryC2ENS_7Vector3IdEES2_d3
_ZN7crpropa19EllipsoidalBoundaryC2Ev0
_ZNK7crpropa11PeriodicBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa11PeriodicBox7processEPNS_9CandidateE2
_ZNK7crpropa13CubicBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa13CubicBoundary7processEPNS_9CandidateE4
_ZNK7crpropa13ReflectiveBox14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ReflectiveBox7processEPNS_9CandidateE1
_ZNK7crpropa17SphericalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SphericalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19CylindricalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19CylindricalBoundary7processEPNS_9CandidateE3
_ZNK7crpropa19EllipsoidalBoundary14getDescriptionB5cxx11Ev0
_ZNK7crpropa19EllipsoidalBoundary7processEPNS_9CandidateE3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Boundary.cpp.gcov.html b/doc/coverageReport/src/module/Boundary.cpp.gcov.html deleted file mode 100644 index 0e651f732..000000000 --- a/doc/coverageReport/src/module/Boundary.cpp.gcov.html +++ /dev/null @@ -1,370 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Boundary.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Boundary.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:10621948.4 %
Date:2024-04-08 14:58:22Functions:204544.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/Boundary.h"
-       2             : #include "crpropa/Units.h"
-       3             : 
-       4             : #include <sstream>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           0 : PeriodicBox::PeriodicBox() :
-       9           0 :                 origin(Vector3d(0, 0, 0)), size(Vector3d(0, 0, 0)) {
-      10           0 : }
-      11             : 
-      12           2 : PeriodicBox::PeriodicBox(Vector3d o, Vector3d s) :
-      13           2 :                 origin(o), size(s) {
-      14           2 : }
-      15             : 
-      16           2 : void PeriodicBox::process(Candidate *c) const {
-      17           2 :         Vector3d pos = c->current.getPosition();
-      18           2 :         Vector3d n = ((pos - origin) / size).floor();
-      19             : 
-      20           2 :         if ((n.x == 0) and (n.y == 0) and (n.z == 0))
-      21             :                 return; // do nothing if candidate is inside the box
-      22             : 
-      23           2 :         c->current.setPosition(pos - n * size);
-      24           2 :         c->previous.setPosition(c->previous.getPosition() - n * size);
-      25           2 :         c->source.setPosition(c->source.getPosition() - n * size);
-      26           2 :         c->created.setPosition(c->created.getPosition() - n * size);
-      27             : }
-      28             : 
-      29           0 : void PeriodicBox::setOrigin(Vector3d o) {
-      30             :         origin = o;
-      31           0 : }
-      32           0 : void PeriodicBox::setSize(Vector3d s) {
-      33             :         size = s;
-      34           0 : }
-      35             : 
-      36           0 : std::string PeriodicBox::getDescription() const {
-      37           0 :         std::stringstream s;
-      38           0 :         s << "Periodic box: origin " << origin / Mpc << " Mpc, ";
-      39           0 :         s << "size " << size / Mpc << " Mpc";
-      40           0 :         return s.str();
-      41           0 : }
-      42             : 
-      43           0 : ReflectiveBox::ReflectiveBox() :
-      44           0 :                 origin(Vector3d(0, 0, 0)), size(Vector3d(0, 0, 0)) {
-      45           0 : }
-      46             : 
-      47           1 : ReflectiveBox::ReflectiveBox(Vector3d o, Vector3d s) :
-      48           1 :                 origin(o), size(s) {
-      49           1 : }
-      50             : 
-      51           1 : void ReflectiveBox::process(Candidate *c) const {
-      52           1 :         Vector3d cur = (c->current.getPosition() - origin) / size; // current position in cell units
-      53           1 :         Vector3d n = cur.floor();
-      54             : 
-      55           1 :         if ((n.x == 0) and (n.y == 0) and (n.z == 0))
-      56             :                 return; // do nothing if candidate is inside the box
-      57             : 
-      58             :         // flip direction
-      59           1 :         Vector3d nReflect(pow(-1, n.x), pow(-1, n.y), pow(-1, n.z));
-      60           1 :         c->current.setDirection(c->current.getDirection() * nReflect);
-      61           1 :         c->previous.setDirection(c->previous.getDirection() * nReflect);
-      62           1 :         c->created.setDirection(c->created.getDirection() * nReflect);
-      63           1 :         c->source.setDirection(c->source.getDirection() * nReflect);
-      64             : 
-      65           1 :         Vector3d src = (c->source.getPosition() - origin) / size; // initial position in cell units
-      66           1 :         Vector3d cre = (c->created.getPosition() - origin) / size; // initial position in cell units
-      67           1 :         Vector3d prv = (c->previous.getPosition() - origin) / size; // previous position in cell units
-      68             : 
-      69             :         // repeatedly translate until the current position is inside the cell
-      70           1 :         while ((cur.x < 0) or (cur.x > 1)) {
-      71           0 :                 double t = 2 * (cur.x > 1);
-      72           0 :                 src.x = t - src.x;
-      73           0 :                 cre.x = t - cre.x;
-      74           0 :                 prv.x = t - prv.x;
-      75           0 :                 cur.x = t - cur.x;
-      76             :         }
-      77           1 :         while ((cur.y < 0) or (cur.y > 1)) {
-      78           0 :                 double t = 2 * (cur.y > 1);
-      79           0 :                 src.y = t - src.y;
-      80           0 :                 cre.y = t - cre.y;
-      81           0 :                 prv.y = t - prv.y;
-      82           0 :                 cur.y = t - cur.y;
-      83             :         }
-      84           2 :         while ((cur.z < 0) or (cur.z > 1)) {
-      85           1 :                 double t = 2 * (cur.z > 1);
-      86           1 :                 src.z = t - src.z;
-      87           1 :                 cre.z = t - cre.z;
-      88           1 :                 prv.z = t - prv.z;
-      89           1 :                 cur.z = t - cur.z;
-      90             :         }
-      91             : 
-      92           1 :         c->current.setPosition(cur * size + origin);
-      93           1 :         c->source.setPosition(src * size + origin);
-      94           1 :         c->created.setPosition(cre * size + origin);
-      95           1 :         c->previous.setPosition(prv * size + origin);
-      96             : }
-      97             : 
-      98           0 : void ReflectiveBox::setOrigin(Vector3d o) {
-      99             :         origin = o;
-     100           0 : }
-     101           0 : void ReflectiveBox::setSize(Vector3d s) {
-     102             :         size = s;
-     103           0 : }
-     104             : 
-     105           0 : std::string ReflectiveBox::getDescription() const {
-     106           0 :         std::stringstream s;
-     107           0 :         s << "Reflective box: origin " << origin / Mpc << " Mpc, ";
-     108           0 :         s << "size " << size / Mpc << " Mpc";
-     109           0 :         return s.str();
-     110           0 : }
-     111             : 
-     112           0 : CubicBoundary::CubicBoundary() :
-     113           0 :                 origin(Vector3d(0, 0, 0)), size(0), limitStep(true), margin(0.1 * kpc) {
-     114           0 : }
-     115             : 
-     116           4 : CubicBoundary::CubicBoundary(Vector3d o, double s) :
-     117           4 :                 origin(o), size(s), limitStep(true), margin(0.1 * kpc) {
-     118           4 : }
-     119             : 
-     120           4 : void CubicBoundary::process(Candidate *c) const {
-     121           4 :         Vector3d r = c->current.getPosition() - origin;
-     122             :         double lo = r.min();
-     123             :         double hi = r.max();
-     124           4 :         if ((lo <= 0) or (hi >= size)) {
-     125           1 :                 reject(c);
-     126             :         }
-     127           4 :         if (limitStep) {
-     128           4 :                 c->limitNextStep(lo + margin);
-     129           4 :                 c->limitNextStep(size - hi + margin);
-     130             :         }
-     131           4 : }
-     132             : 
-     133           0 : void CubicBoundary::setOrigin(Vector3d o) {
-     134             :         origin = o;
-     135           0 : }
-     136           0 : void CubicBoundary::setSize(double s) {
-     137           0 :         size = s;
-     138           0 : }
-     139           2 : void CubicBoundary::setMargin(double m) {
-     140           2 :         margin = m;
-     141           2 : }
-     142           2 : void CubicBoundary::setLimitStep(bool b) {
-     143           2 :         limitStep = b;
-     144           2 : }
-     145             : 
-     146           0 : std::string CubicBoundary::getDescription() const {
-     147           0 :         std::stringstream s;
-     148           0 :         s << "Cubic Boundary: origin " << origin / Mpc << " Mpc, ";
-     149           0 :         s << "size " << size / Mpc << " Mpc, ";
-     150           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     151           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     152           0 :         if (rejectAction.valid())
-     153           0 :                 s << ", Action: " << rejectAction->getDescription();
-     154           0 :         return s.str();
-     155           0 : }
-     156             : 
-     157           0 : SphericalBoundary::SphericalBoundary() :
-     158           0 :                 center(Vector3d(0, 0, 0)), radius(0), limitStep(true), margin(0.1 * kpc) {
-     159           0 : }
-     160             : 
-     161           3 : SphericalBoundary::SphericalBoundary(Vector3d c, double r) :
-     162           3 :                 center(c), radius(r), limitStep(true), margin(0.1 * kpc) {
-     163           3 : }
-     164             : 
-     165           3 : void SphericalBoundary::process(Candidate *c) const {
-     166           3 :         double d = (c->current.getPosition() - center).getR();
-     167           3 :         if (d >= radius) {
-     168           1 :                 reject(c);
-     169             :         }
-     170           3 :         if (limitStep)
-     171           3 :                 c->limitNextStep(radius - d + margin);
-     172           3 : }
-     173             : 
-     174           0 : void SphericalBoundary::setCenter(Vector3d c) {
-     175             :         center = c;
-     176           0 : }
-     177           0 : void SphericalBoundary::setRadius(double r) {
-     178           0 :         radius = r;
-     179           0 : }
-     180           1 : void SphericalBoundary::setMargin(double m) {
-     181           1 :         margin = m;
-     182           1 : }
-     183           1 : void SphericalBoundary::setLimitStep(bool b) {
-     184           1 :         limitStep = b;
-     185           1 : }
-     186             : 
-     187           0 : std::string SphericalBoundary::getDescription() const {
-     188           0 :         std::stringstream s;
-     189           0 :         s << "Spherical Boundary: radius " << radius / Mpc << " Mpc, ";
-     190           0 :         s << "around " << center / Mpc << " Mpc, ";
-     191           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     192           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     193           0 :         if (rejectAction.valid())
-     194           0 :                 s << ", Action: " << rejectAction->getDescription();
-     195           0 :         return s.str();
-     196           0 : }
-     197             : 
-     198           0 : EllipsoidalBoundary::EllipsoidalBoundary() :
-     199             :                 focalPoint1(Vector3d(0, 0, 0)), focalPoint2(Vector3d(0, 0, 0)),
-     200           0 :                 majorAxis(0), limitStep(true), margin(0.1 * kpc) {
-     201           0 : }
-     202             : 
-     203           3 : EllipsoidalBoundary::EllipsoidalBoundary(Vector3d f1, Vector3d f2, double a) :
-     204           3 :                 focalPoint1(f1), focalPoint2(f2), majorAxis(a), limitStep(true),
-     205           3 :                 margin(0.1 * kpc) {
-     206           3 : }
-     207             : 
-     208           3 : void EllipsoidalBoundary::process(Candidate *c) const {
-     209           3 :         Vector3d pos = c->current.getPosition();
-     210           3 :         double d = pos.getDistanceTo(focalPoint1) + pos.getDistanceTo(focalPoint2);
-     211           3 :         if (d >= majorAxis) {
-     212           1 :                 reject(c);
-     213             :         }
-     214           3 :         if (limitStep)
-     215           3 :                 c->limitNextStep(majorAxis - d + margin);
-     216           3 : }
-     217             : 
-     218           0 : void EllipsoidalBoundary::setFocalPoints(Vector3d f1, Vector3d f2) {
-     219             :         focalPoint1 = f1;
-     220             :         focalPoint2 = f2;
-     221           0 : }
-     222           0 : void EllipsoidalBoundary::setMajorAxis(double a) {
-     223           0 :         majorAxis = a;
-     224           0 : }
-     225           1 : void EllipsoidalBoundary::setMargin(double m) {
-     226           1 :         margin = m;
-     227           1 : }
-     228           1 : void EllipsoidalBoundary::setLimitStep(bool b) {
-     229           1 :         limitStep = b;
-     230           1 : }
-     231             : 
-     232           0 : std::string EllipsoidalBoundary::getDescription() const {
-     233           0 :         std::stringstream s;
-     234           0 :         s << "Ellipsoidal Boundary: F1 = " << focalPoint1 / Mpc << " Mpc, ";
-     235           0 :         s << "F2 = " << focalPoint2 / Mpc << " Mpc, ";
-     236           0 :         s << "major axis " << majorAxis / Mpc << " Mpc; ";
-     237           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     238           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     239           0 :         if (rejectAction.valid())
-     240           0 :                 s << ", Action: " << rejectAction->getDescription();
-     241           0 :         return s.str();
-     242           0 : }
-     243             : 
-     244           0 : CylindricalBoundary::CylindricalBoundary() :
-     245           0 :   origin(Vector3d(0,0,0)), height(0), radius(0), limitStep(false), margin(0) {
-     246           0 : }
-     247             : 
-     248           3 : CylindricalBoundary::CylindricalBoundary(Vector3d o, double h, double r) :
-     249           3 :   origin(o), height(h), radius(r), limitStep(false) , margin(0){
-     250           3 : }
-     251             : 
-     252           3 : void CylindricalBoundary::process(Candidate *c) const {
-     253           3 :         Vector3d d = c->current.getPosition() - origin;
-     254           3 :         double R2 = pow(d.x, 2.)+pow(d.y, 2.);
-     255           3 :         double Z = fabs(d.z);
-     256           3 :         if ( R2 < pow(radius, 2.) and Z < height/2.) {
-     257           2 :                 if(limitStep) {
-     258           2 :                         c->limitNextStep(std::min(radius - pow(R2, 0.5), height/2. - Z) + margin);   
-     259             :                 }
-     260             :           return;
-     261             :         }
-     262           1 :         reject(c);
-     263             : }
-     264             : 
-     265           0 : void CylindricalBoundary::setOrigin(Vector3d o) {
-     266             :         origin = o;
-     267           0 : }
-     268           0 : void CylindricalBoundary::setHeight(double h) {
-     269           0 :         height = h;
-     270           0 : }
-     271           0 : void CylindricalBoundary::setRadius(double r) {
-     272           0 :         radius = r;
-     273           0 : }
-     274           1 : void CylindricalBoundary::setLimitStep(bool b) {
-     275           1 :         limitStep = b;
-     276           1 : }
-     277           1 : void CylindricalBoundary::setMargin(double m) {
-     278           1 :         margin = m;
-     279           1 : }
-     280             : 
-     281             : 
-     282           0 : std::string CylindricalBoundary::getDescription() const {
-     283           0 :         std::stringstream s;
-     284           0 :         s << "Cylindrical Boundary: origin = " << origin / kpc << " kpc, ";
-     285           0 :         s << "radius = " << radius / kpc << " kpc, ";
-     286           0 :         s << "height" << height / kpc << " kpc; ";
-     287           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     288           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     289           0 :         if (rejectAction.valid())
-     290           0 :                 s << ", Action: " << rejectAction->getDescription();
-     291           0 :         return s.str();
-     292           0 : }
-     293             : 
-     294             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html b/doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html deleted file mode 100644 index 59b7031c8..000000000 --- a/doc/coverageReport/src/module/BreakCondition.cpp.func-sort-c.html +++ /dev/null @@ -1,224 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/BreakCondition.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - BreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6317236.6 %
Date:2024-04-08 14:58:22Functions:153839.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MinimumEnergy16setMinimumEnergyEd0
_ZN7crpropa15DetectionLength18setDetectionLengthEd0
_ZN7crpropa15MinimumRedshift18getMinimumRedshiftEv0
_ZN7crpropa15MinimumRedshift18setMinimumRedshiftEd0
_ZN7crpropa15MinimumRigidity18setMinimumRigidityEd0
_ZN7crpropa15MinimumRigidityC2Ed0
_ZN7crpropa19MinimumChargeNumber22setMinimumChargeNumberEi0
_ZN7crpropa23MaximumTrajectoryLength26setMaximumTrajectoryLengthEd0
_ZNK7crpropa13MinimumEnergy14getDescriptionB5cxx11Ev0
_ZNK7crpropa13MinimumEnergy16getMinimumEnergyEv0
_ZNK7crpropa15DetectionLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa15DetectionLength18getDetectionLengthEv0
_ZNK7crpropa15MinimumRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRigidity14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRigidity18getMinimumRigidityEv0
_ZNK7crpropa15MinimumRigidity7processEPNS_9CandidateE0
_ZNK7crpropa19MinimumChargeNumber14getDescriptionB5cxx11Ev0
_ZNK7crpropa19MinimumChargeNumber22getMinimumChargeNumberEv0
_ZNK7crpropa23MaximumTrajectoryLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa23MaximumTrajectoryLength20getObserverPositionsEv0
_ZNK7crpropa23MaximumTrajectoryLength26getMaximumTrajectoryLengthEv0
_ZNK7crpropa26MinimumEnergyPerParticleId14getDescriptionB5cxx11Ev0
_ZNK7crpropa26MinimumEnergyPerParticleId22getMinimumEnergyOthersEv0
_ZN7crpropa15DetectionLengthC2Ed1
_ZN7crpropa15MinimumRedshiftC2Ed1
_ZN7crpropa19MinimumChargeNumberC2Ei1
_ZN7crpropa23MaximumTrajectoryLength19addObserverPositionERKNS_7Vector3IdEE1
_ZN7crpropa26MinimumEnergyPerParticleId22setMinimumEnergyOthersEd1
_ZN7crpropa26MinimumEnergyPerParticleIdC2Ed1
_ZN7crpropa13MinimumEnergyC2Ed2
_ZNK7crpropa15DetectionLength7processEPNS_9CandidateE2
_ZNK7crpropa15MinimumRedshift7processEPNS_9CandidateE2
_ZN7crpropa26MinimumEnergyPerParticleId3addEid3
_ZNK7crpropa19MinimumChargeNumber7processEPNS_9CandidateE4
_ZNK7crpropa26MinimumEnergyPerParticleId7processEPNS_9CandidateE5
_ZN7crpropa23MaximumTrajectoryLengthC2Ed13
_ZNK7crpropa13MinimumEnergy7processEPNS_9CandidateE7644
_ZNK7crpropa23MaximumTrajectoryLength7processEPNS_9CandidateE491649
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/BreakCondition.cpp.func.html b/doc/coverageReport/src/module/BreakCondition.cpp.func.html deleted file mode 100644 index 9734252c0..000000000 --- a/doc/coverageReport/src/module/BreakCondition.cpp.func.html +++ /dev/null @@ -1,224 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/BreakCondition.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - BreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6317236.6 %
Date:2024-04-08 14:58:22Functions:153839.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13MinimumEnergy16setMinimumEnergyEd0
_ZN7crpropa13MinimumEnergyC2Ed2
_ZN7crpropa15DetectionLength18setDetectionLengthEd0
_ZN7crpropa15DetectionLengthC2Ed1
_ZN7crpropa15MinimumRedshift18getMinimumRedshiftEv0
_ZN7crpropa15MinimumRedshift18setMinimumRedshiftEd0
_ZN7crpropa15MinimumRedshiftC2Ed1
_ZN7crpropa15MinimumRigidity18setMinimumRigidityEd0
_ZN7crpropa15MinimumRigidityC2Ed0
_ZN7crpropa19MinimumChargeNumber22setMinimumChargeNumberEi0
_ZN7crpropa19MinimumChargeNumberC2Ei1
_ZN7crpropa23MaximumTrajectoryLength19addObserverPositionERKNS_7Vector3IdEE1
_ZN7crpropa23MaximumTrajectoryLength26setMaximumTrajectoryLengthEd0
_ZN7crpropa23MaximumTrajectoryLengthC2Ed13
_ZN7crpropa26MinimumEnergyPerParticleId22setMinimumEnergyOthersEd1
_ZN7crpropa26MinimumEnergyPerParticleId3addEid3
_ZN7crpropa26MinimumEnergyPerParticleIdC2Ed1
_ZNK7crpropa13MinimumEnergy14getDescriptionB5cxx11Ev0
_ZNK7crpropa13MinimumEnergy16getMinimumEnergyEv0
_ZNK7crpropa13MinimumEnergy7processEPNS_9CandidateE7644
_ZNK7crpropa15DetectionLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa15DetectionLength18getDetectionLengthEv0
_ZNK7crpropa15DetectionLength7processEPNS_9CandidateE2
_ZNK7crpropa15MinimumRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRedshift7processEPNS_9CandidateE2
_ZNK7crpropa15MinimumRigidity14getDescriptionB5cxx11Ev0
_ZNK7crpropa15MinimumRigidity18getMinimumRigidityEv0
_ZNK7crpropa15MinimumRigidity7processEPNS_9CandidateE0
_ZNK7crpropa19MinimumChargeNumber14getDescriptionB5cxx11Ev0
_ZNK7crpropa19MinimumChargeNumber22getMinimumChargeNumberEv0
_ZNK7crpropa19MinimumChargeNumber7processEPNS_9CandidateE4
_ZNK7crpropa23MaximumTrajectoryLength14getDescriptionB5cxx11Ev0
_ZNK7crpropa23MaximumTrajectoryLength20getObserverPositionsEv0
_ZNK7crpropa23MaximumTrajectoryLength26getMaximumTrajectoryLengthEv0
_ZNK7crpropa23MaximumTrajectoryLength7processEPNS_9CandidateE491649
_ZNK7crpropa26MinimumEnergyPerParticleId14getDescriptionB5cxx11Ev0
_ZNK7crpropa26MinimumEnergyPerParticleId22getMinimumEnergyOthersEv0
_ZNK7crpropa26MinimumEnergyPerParticleId7processEPNS_9CandidateE5
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/BreakCondition.cpp.gcov.html b/doc/coverageReport/src/module/BreakCondition.cpp.gcov.html deleted file mode 100644 index 315b82cba..000000000 --- a/doc/coverageReport/src/module/BreakCondition.cpp.gcov.html +++ /dev/null @@ -1,343 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/BreakCondition.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - BreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:6317236.6 %
Date:2024-04-08 14:58:22Functions:153839.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/BreakCondition.h"
-       2             : #include "crpropa/ParticleID.h"
-       3             : #include "crpropa/Units.h"
-       4             : 
-       5             : #include <sstream>
-       6             : 
-       7             : namespace crpropa {
-       8             : 
-       9          13 : MaximumTrajectoryLength::MaximumTrajectoryLength(double maxLength) :
-      10          13 :                 maxLength(maxLength) {
-      11          13 : }
-      12             : 
-      13           0 : void MaximumTrajectoryLength::setMaximumTrajectoryLength(double length) {
-      14           0 :         maxLength = length;
-      15           0 : }
-      16             : 
-      17           0 : double MaximumTrajectoryLength::getMaximumTrajectoryLength() const {
-      18           0 :         return maxLength;
-      19             : }
-      20             : 
-      21           1 : void MaximumTrajectoryLength::addObserverPosition(const Vector3d& position) {
-      22           1 :         observerPositions.push_back(position);
-      23           1 : }
-      24             : 
-      25           0 : const std::vector<Vector3d>& MaximumTrajectoryLength::getObserverPositions() const {
-      26           0 :         return observerPositions;
-      27             : }
-      28             : 
-      29           0 : std::string MaximumTrajectoryLength::getDescription() const {
-      30           0 :         std::stringstream s;
-      31           0 :         s << "Maximum trajectory length: " << maxLength / Mpc << " Mpc, ";
-      32           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-      33           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-      34           0 :         if (rejectAction.valid())
-      35           0 :                 s << ", Action: " << rejectAction->getDescription();
-      36           0 :         s << "\n  Observer positions: \n";
-      37           0 :         for (size_t i = 0; i < observerPositions.size(); i++)
-      38           0 :                 s << "    - " << observerPositions[i] / Mpc << " Mpc\n";
-      39           0 :         return s.str();
-      40           0 : }
-      41             : 
-      42      491649 : void MaximumTrajectoryLength::process(Candidate *c) const {
-      43      491649 :         double length = c->getTrajectoryLength();
-      44      491649 :         Vector3d position = c->current.getPosition();
-      45             : 
-      46      491649 :         if(observerPositions.size()) {
-      47             :                 bool inRange = false;
-      48           4 :                 for (size_t i = 0; i < observerPositions.size(); i++) {
-      49           2 :                         double distance = position.getDistanceTo(observerPositions[i]);
-      50           2 :                         if (distance + length < maxLength)
-      51             :                                 inRange = true;
-      52             :                 }
-      53           2 :                 if (!inRange) {
-      54           1 :                         reject(c);
-      55             :                         return;
-      56             :                 }
-      57             :         }
-      58             : 
-      59      491648 :         if (length >= maxLength) {
-      60        1107 :                 reject(c);
-      61             :         } else {
-      62      490541 :                 c->limitNextStep(maxLength - length);
-      63             :         }
-      64             : }
-      65             : 
-      66             : //*****************************************************************************
-      67           2 : MinimumEnergy::MinimumEnergy(double minEnergy) :
-      68           2 :                 minEnergy(minEnergy) {
-      69           2 : }
-      70             : 
-      71           0 : void MinimumEnergy::setMinimumEnergy(double energy) {
-      72           0 :         minEnergy = energy;
-      73           0 : }
-      74             : 
-      75           0 : double MinimumEnergy::getMinimumEnergy() const {
-      76           0 :         return minEnergy;
-      77             : }
-      78             : 
-      79        7644 : void MinimumEnergy::process(Candidate *c) const {
-      80        7644 :         if (c->current.getEnergy() > minEnergy)
-      81             :                 return;
-      82             :         else
-      83           1 :                 reject(c);
-      84             : }
-      85             : 
-      86           0 : std::string MinimumEnergy::getDescription() const {
-      87           0 :         std::stringstream s;
-      88           0 :         s << "Minimum energy: " << minEnergy / EeV << " EeV, ";
-      89           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-      90           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-      91           0 :         if (rejectAction.valid())
-      92           0 :                 s << ", Action: " << rejectAction->getDescription();
-      93           0 :         return s.str();
-      94           0 : }
-      95             : 
-      96             : //*****************************************************************************
-      97           0 : MinimumRigidity::MinimumRigidity(double minRigidity) :
-      98           0 :                 minRigidity(minRigidity) {
-      99           0 : }
-     100             : 
-     101           0 : void MinimumRigidity::setMinimumRigidity(double minRigidity) {
-     102           0 :         this->minRigidity = minRigidity;
-     103           0 : }
-     104             : 
-     105           0 : double MinimumRigidity::getMinimumRigidity() const {
-     106           0 :         return minRigidity;
-     107             : }
-     108             : 
-     109           0 : void MinimumRigidity::process(Candidate *c) const {
-     110           0 :         if (c->current.getRigidity() < minRigidity)
-     111           0 :                 reject(c);
-     112           0 : }
-     113             : 
-     114           0 : std::string MinimumRigidity::getDescription() const {
-     115           0 :         std::stringstream s;
-     116           0 :         s << "Minimum rigidity: " << minRigidity / EeV << " EeV, ";
-     117           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     118           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     119           0 :         if (rejectAction.valid())
-     120           0 :                 s << ", Action: " << rejectAction->getDescription();
-     121           0 :         return s.str();
-     122           0 : }
-     123             : 
-     124             : //*****************************************************************************
-     125           1 : MinimumRedshift::MinimumRedshift(double zmin) :
-     126           1 :                 zmin(zmin) {
-     127           1 : }
-     128             : 
-     129           0 : void MinimumRedshift::setMinimumRedshift(double z) {
-     130           0 :         zmin = z;
-     131           0 : }
-     132             : 
-     133           0 : double MinimumRedshift::getMinimumRedshift() {
-     134           0 :         return zmin;
-     135             : }
-     136             : 
-     137           2 : void MinimumRedshift::process(Candidate* c) const {
-     138           2 :         if (c->getRedshift() > zmin)
-     139             :                 return;
-     140             :         else
-     141           1 :                 reject(c);
-     142             : }
-     143             : 
-     144           0 : std::string MinimumRedshift::getDescription() const {
-     145           0 :         std::stringstream s;
-     146           0 :         s << "Minimum redshift: " << zmin << ", ";
-     147           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     148           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     149           0 :         if (rejectAction.valid())
-     150           0 :                 s << ", Action: " << rejectAction->getDescription();
-     151           0 :         return s.str();
-     152           0 : }
-     153             : 
-     154             : //*****************************************************************************
-     155           1 : MinimumChargeNumber::MinimumChargeNumber(int minChargeNumber) :
-     156           1 :                 minChargeNumber(minChargeNumber) {
-     157           1 : }
-     158             : 
-     159           0 : void MinimumChargeNumber::setMinimumChargeNumber(int chargeNumber) {
-     160           0 :         minChargeNumber = chargeNumber;
-     161           0 : }
-     162             : 
-     163           0 : int MinimumChargeNumber::getMinimumChargeNumber() const {
-     164           0 :         return minChargeNumber;
-     165             : }
-     166             : 
-     167           4 : void MinimumChargeNumber::process(Candidate *c) const {
-     168           4 :         if (chargeNumber(c->current.getId()) > minChargeNumber)
-     169             :                 return;
-     170             :         else
-     171           2 :                 reject(c);
-     172             : }
-     173             : 
-     174           0 : std::string MinimumChargeNumber::getDescription() const {
-     175           0 :         std::stringstream s;
-     176           0 :         s << "Minimum charge number: " << minChargeNumber;
-     177           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     178           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     179           0 :         if (rejectAction.valid())
-     180           0 :                 s << ", Action: " << rejectAction->getDescription();
-     181           0 :         return s.str();
-     182           0 : }
-     183             : 
-     184             : //*****************************************************************************
-     185           1 : MinimumEnergyPerParticleId::MinimumEnergyPerParticleId(double minEnergyOthers) {
-     186           1 :         setMinimumEnergyOthers(minEnergyOthers);
-     187           1 : }
-     188             : 
-     189           3 : void MinimumEnergyPerParticleId::add(int id, double energy) {
-     190           3 :         particleIds.push_back(id);
-     191           3 :         minEnergies.push_back(energy);
-     192           3 : }
-     193             : 
-     194           1 : void MinimumEnergyPerParticleId::setMinimumEnergyOthers(double energy) {
-     195           1 :         minEnergyOthers = energy;
-     196           1 : }
-     197             : 
-     198           0 : double MinimumEnergyPerParticleId::getMinimumEnergyOthers() const {
-     199           0 :         return minEnergyOthers;
-     200             : }
-     201             : 
-     202           5 : void MinimumEnergyPerParticleId::process(Candidate *c) const {
-     203          15 :         for (int i = 0; i < particleIds.size(); i++) {
-     204          12 :                 if (c->current.getId() == particleIds[i]) {
-     205           5 :                         if (c->current.getEnergy() < minEnergies[i])
-     206           3 :                                 reject(c);
-     207             :                         else
-     208             :                                 return;
-     209             :                 }
-     210             :         }
-     211             : 
-     212           3 :         if (c->current.getEnergy() < minEnergyOthers)
-     213           1 :                 reject(c);
-     214             :         else
-     215             :                 return;
-     216             : }
-     217             : 
-     218           0 : std::string MinimumEnergyPerParticleId::getDescription() const {
-     219           0 :         std::stringstream s;
-     220           0 :         s << "Minimum energy for non-specified particles: " << minEnergyOthers / eV << " eV";
-     221           0 :         for (int i = 0; i < minEnergies.size(); i++) {
-     222           0 :                 s << "  for particle " << particleIds[i] << " : " << minEnergies[i] / eV << " eV";
-     223             :         }
-     224           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     225           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     226           0 :         if (rejectAction.valid())
-     227           0 :                 s << ", Action: " << rejectAction->getDescription();
-     228           0 :         return s.str();
-     229           0 : }
-     230             : 
-     231             : //*****************************************************************************
-     232           1 : DetectionLength::DetectionLength(double detLength) :
-     233           1 :                 detLength(detLength) {
-     234           1 : }
-     235             : 
-     236           0 : void DetectionLength::setDetectionLength(double length) {
-     237           0 :         detLength = length;
-     238           0 : }
-     239             : 
-     240           0 : double DetectionLength::getDetectionLength() const {
-     241           0 :         return detLength;
-     242             : }
-     243             : 
-     244             : 
-     245           0 : std::string DetectionLength::getDescription() const {
-     246           0 :         std::stringstream s;
-     247           0 :         s << "Detection length: " << detLength / kpc << " kpc, ";
-     248           0 :         s << "Flag: '" << rejectFlagKey << "' -> '" << rejectFlagValue << "', ";
-     249           0 :         s << "MakeInactive: " << (makeRejectedInactive ? "yes" : "no");
-     250           0 :         if (rejectAction.valid())
-     251           0 :                 s << ", Action: " << rejectAction->getDescription();
-     252           0 :         return s.str();
-     253           0 : }
-     254             : 
-     255           2 : void DetectionLength::process(Candidate *c) const {
-     256           2 :         double length = c->getTrajectoryLength();
-     257           2 :         double step = c->getCurrentStep();
-     258             : 
-     259           2 :         if (length >= detLength && length - step < detLength) {
-     260           1 :                 reject(c);
-     261             :         } else {
-     262           1 :                 c->limitNextStep(detLength - length);
-     263             :         }
-     264           2 : }
-     265             : 
-     266             : 
-     267             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html b/doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html deleted file mode 100644 index d7f065f98..000000000 --- a/doc/coverageReport/src/module/CandidateSplitting.cpp.func-sort-c.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/CandidateSplitting.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - CandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:536186.9 %
Date:2024-04-08 14:58:22Functions:101190.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18CandidateSplittingC2Ev0
_ZN7crpropa18CandidateSplitting16setEnergyBinsDSAEddi1
_ZN7crpropa18CandidateSplittingC2Eddi1
_ZNK7crpropa18CandidateSplitting16getMinimalWeightEv1
_ZNK7crpropa18CandidateSplitting9getNsplitEv1
_ZN7crpropa18CandidateSplitting13setEnergyBinsEdddb3
_ZN7crpropa18CandidateSplittingC2Eiddddb3
_ZN7crpropa18CandidateSplitting16setMinimalWeightEd4
_ZN7crpropa18CandidateSplitting9setNsplitEi4
_ZNK7crpropa18CandidateSplitting13getEnergyBinsEv6
_ZNK7crpropa18CandidateSplitting7processEPNS_9CandidateE6
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/CandidateSplitting.cpp.func.html b/doc/coverageReport/src/module/CandidateSplitting.cpp.func.html deleted file mode 100644 index 8031c35f7..000000000 --- a/doc/coverageReport/src/module/CandidateSplitting.cpp.func.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/CandidateSplitting.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - CandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:536186.9 %
Date:2024-04-08 14:58:22Functions:101190.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa18CandidateSplitting13setEnergyBinsEdddb3
_ZN7crpropa18CandidateSplitting16setEnergyBinsDSAEddi1
_ZN7crpropa18CandidateSplitting16setMinimalWeightEd4
_ZN7crpropa18CandidateSplitting9setNsplitEi4
_ZN7crpropa18CandidateSplittingC2Eddi1
_ZN7crpropa18CandidateSplittingC2Eiddddb3
_ZN7crpropa18CandidateSplittingC2Ev0
_ZNK7crpropa18CandidateSplitting13getEnergyBinsEv6
_ZNK7crpropa18CandidateSplitting16getMinimalWeightEv1
_ZNK7crpropa18CandidateSplitting7processEPNS_9CandidateE6
_ZNK7crpropa18CandidateSplitting9getNsplitEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html b/doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html deleted file mode 100644 index c8cd11eb0..000000000 --- a/doc/coverageReport/src/module/CandidateSplitting.cpp.gcov.html +++ /dev/null @@ -1,194 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/CandidateSplitting.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - CandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:536186.9 %
Date:2024-04-08 14:58:22Functions:101190.9 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/CandidateSplitting.h"
-       2             : 
-       3             : namespace crpropa {
-       4             : 
-       5           0 : CandidateSplitting::CandidateSplitting() {
-       6             :         // no particle splitting if EnergyBins and NSplit are not specified
-       7           0 :         setNsplit(0);
-       8           0 :         setMinimalWeight(1.);
-       9           0 : }
-      10             : 
-      11           3 : CandidateSplitting::CandidateSplitting(int nSplit, double Emin, double Emax,  double nBins, double minWeight, bool log) {
-      12           3 :         setNsplit(nSplit);
-      13           3 :         setEnergyBins(Emin, Emax, nBins, log);
-      14           3 :         setMinimalWeight(minWeight);
-      15           3 : }
-      16             : 
-      17           1 : CandidateSplitting::CandidateSplitting(double spectralIndex, double Emin, int nBins)  {
-      18             :         // to use with Diffusive Shock Acceleration
-      19           1 :         if (spectralIndex > 0){
-      20           0 :                 throw std::runtime_error(
-      21           0 :                                 "CandidateSplitting: spectralIndex > 0 !"); 
-      22             :         }
-      23             : 
-      24           1 :         setNsplit(2); // always split in 2, calculate bins in energy for given spectrum:
-      25           1 :         double dE = pow(1. / 2, 1. / (spectralIndex + 1)); 
-      26           1 :         setEnergyBinsDSA(Emin, dE, nBins);
-      27           1 :         setMinimalWeight(1. / pow(2, nBins));
-      28           1 : }
-      29             : 
-      30           6 : void CandidateSplitting::process(Candidate *c) const {
-      31           6 :         double currE = c->current.getEnergy(); 
-      32           6 :         double prevE = c->previous.getEnergy();
-      33             : 
-      34           6 :         if (c->getWeight() <= minWeight){
-      35             :                 // minimal weight reached, no splitting
-      36             :                 return;
-      37             :         }
-      38           5 :         if (currE < Ebins[0] || nSplit == 0 ){
-      39             :                 // current energy is smaller than first bin -> no splitting
-      40             :                 // or, number of splits = 0
-      41             :                 return;
-      42             :         }
-      43           4 :         for (size_t i = 0; i < Ebins.size(); ++i){
-      44             :                 
-      45           4 :                 if( prevE < Ebins[i] ){
-      46             :                         // previous energy is in energy bin [i-1, i]
-      47           3 :                         if(currE < Ebins[i]){
-      48             :                                 //assuming that dE greater than 0, prevE and E in same energy bin -> no splitting
-      49             :                                 return;
-      50             :                         }
-      51             :                         // current energy is in energy bin [i,i+1] or higher -> particle splitting for each crossing
-      52           4 :                         for (size_t j = i; j < Ebins.size(); ++j ){
-      53             : 
-      54             :                                 // adapted from Acceleration Module:
-      55           4 :                                 c->updateWeight(1. / nSplit); // * 1/n_split
-      56             : 
-      57           8 :                                 for (int i = 1; i < nSplit; i++) {
-      58             :                                 
-      59           4 :                                         ref_ptr<Candidate> new_candidate = c->clone(false);
-      60           4 :                                         new_candidate->parent = c;
-      61           4 :                                         new_candidate->previous.setEnergy(currE); // so that new candidate is not split again in next step!
-      62             :                                         c->addSecondary(new_candidate);
-      63             :                                 }
-      64           4 :                                 if (j < Ebins.size()-1 && currE < Ebins[j+1]){
-      65             :                                         // candidate is in energy bin [j, j+1] -> no further splitting
-      66             :                                         return;
-      67             :                                 }
-      68             :                         }
-      69             :                         return;
-      70             :                 }
-      71             :         }
-      72             : }
-      73             : 
-      74           3 : void CandidateSplitting::setEnergyBins(double Emin, double Emax, double nBins, bool log) {
-      75           3 :         Ebins.resize(0);
-      76           3 :         if (Emin > Emax){
-      77           0 :                 throw std::runtime_error(
-      78           0 :                                 "CandidateSplitting: Emin > Emax!");
-      79             :         }
-      80           3 :         double dE = (Emax-Emin)/nBins;
-      81          14 :         for (size_t i = 0; i < nBins; ++i) {
-      82          11 :                 if (log == true) {
-      83           4 :                         Ebins.push_back(Emin * pow(Emax / Emin, i / (nBins - 1.0)));
-      84             :                 } else {
-      85           7 :                         Ebins.push_back(Emin + i * dE);
-      86             :                 }
-      87             :         }
-      88           3 : }
-      89             : 
-      90           1 : void CandidateSplitting::setEnergyBinsDSA(double Emin, double dE, int n) {
-      91           1 :         Ebins.resize(0);
-      92           5 :         for (size_t i = 1; i < n + 1; ++i) {
-      93           4 :                 Ebins.push_back(Emin * pow(dE, i));
-      94             :         }
-      95           1 : }
-      96             : 
-      97           6 : const std::vector<double>& CandidateSplitting::getEnergyBins() const {
-      98           6 :         return Ebins;
-      99             : }
-     100             : 
-     101           4 : void CandidateSplitting::setNsplit(int n) {
-     102           4 :         nSplit = n;
-     103           4 : }
-     104             : 
-     105           4 : void CandidateSplitting::setMinimalWeight(double w) {
-     106           4 :         minWeight = w;
-     107           4 : }
-     108             : 
-     109           1 : int CandidateSplitting::getNsplit() const {
-     110           1 :         return nSplit;
-     111             : }
-     112             : 
-     113           1 : double CandidateSplitting::getMinimalWeight() const {
-     114           1 :         return minWeight;
-     115             : }
-     116             : 
-     117             : } // end namespace crpropa
-     118             : 
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html b/doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html deleted file mode 100644 index 119a389bf..000000000 --- a/doc/coverageReport/src/module/DiffusionSDE.cpp.func-sort-c.html +++ /dev/null @@ -1,172 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/DiffusionSDE.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - DiffusionSDE.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15420276.2 %
Date:2024-04-08 14:58:22Functions:222588.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa12DiffusionSDE14getDescriptionB5cxx11Ev0
_ZNK7crpropa12DiffusionSDE16getMagneticFieldEv0
_ZNK7crpropa12DiffusionSDE17getAdvectionFieldEv0
_ZNK7crpropa12DiffusionSDE10getEpsilonEv1
_ZNK7crpropa12DiffusionSDE12getToleranceEv1
_ZNK7crpropa12DiffusionSDE14getMaximumStepEv1
_ZNK7crpropa12DiffusionSDE14getMinimumStepEv1
_ZN7crpropa12DiffusionSDE17setAdvectionFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEENS1_INS_14AdvectionFieldEEEdddd3
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEEdddd4
_ZNK7crpropa12DiffusionSDE8getAlphaEv5
_ZNK7crpropa12DiffusionSDE8getScaleEv5
_ZN7crpropa12DiffusionSDE10setEpsilonEd7
_ZN7crpropa12DiffusionSDE12setToleranceEd7
_ZN7crpropa12DiffusionSDE14setMaximumStepEd7
_ZN7crpropa12DiffusionSDE14setMinimumStepEd7
_ZN7crpropa12DiffusionSDE16setMagneticFieldENS_7ref_ptrINS_13MagneticFieldEEE7
_ZN7crpropa12DiffusionSDE8setAlphaEd7
_ZN7crpropa12DiffusionSDE8setScaleEd7
_ZNK7crpropa12DiffusionSDE9driftStepERKNS_7Vector3IdEERS2_d120001
_ZNK7crpropa12DiffusionSDE27getAdvectionFieldAtPositionENS_7Vector3IdEE120002
_ZNK7crpropa12DiffusionSDE16calculateBTensorEdPdNS_7Vector3IdEES3_d480002
_ZNK7crpropa12DiffusionSDE7processEPNS_9CandidateE480003
_ZNK7crpropa12DiffusionSDE7tryStepERKNS_7Vector3IdEERS2_S5_dd960004
_ZNK7crpropa12DiffusionSDE26getMagneticFieldAtPositionENS_7Vector3IdEEd5760025
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/DiffusionSDE.cpp.func.html b/doc/coverageReport/src/module/DiffusionSDE.cpp.func.html deleted file mode 100644 index d4e981a1a..000000000 --- a/doc/coverageReport/src/module/DiffusionSDE.cpp.func.html +++ /dev/null @@ -1,172 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/DiffusionSDE.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - DiffusionSDE.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15420276.2 %
Date:2024-04-08 14:58:22Functions:222588.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12DiffusionSDE10setEpsilonEd7
_ZN7crpropa12DiffusionSDE12setToleranceEd7
_ZN7crpropa12DiffusionSDE14setMaximumStepEd7
_ZN7crpropa12DiffusionSDE14setMinimumStepEd7
_ZN7crpropa12DiffusionSDE16setMagneticFieldENS_7ref_ptrINS_13MagneticFieldEEE7
_ZN7crpropa12DiffusionSDE17setAdvectionFieldENS_7ref_ptrINS_14AdvectionFieldEEE3
_ZN7crpropa12DiffusionSDE8setAlphaEd7
_ZN7crpropa12DiffusionSDE8setScaleEd7
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEENS1_INS_14AdvectionFieldEEEdddd3
_ZN7crpropa12DiffusionSDEC2ENS_7ref_ptrINS_13MagneticFieldEEEdddd4
_ZNK7crpropa12DiffusionSDE10getEpsilonEv1
_ZNK7crpropa12DiffusionSDE12getToleranceEv1
_ZNK7crpropa12DiffusionSDE14getDescriptionB5cxx11Ev0
_ZNK7crpropa12DiffusionSDE14getMaximumStepEv1
_ZNK7crpropa12DiffusionSDE14getMinimumStepEv1
_ZNK7crpropa12DiffusionSDE16calculateBTensorEdPdNS_7Vector3IdEES3_d480002
_ZNK7crpropa12DiffusionSDE16getMagneticFieldEv0
_ZNK7crpropa12DiffusionSDE17getAdvectionFieldEv0
_ZNK7crpropa12DiffusionSDE26getMagneticFieldAtPositionENS_7Vector3IdEEd5760025
_ZNK7crpropa12DiffusionSDE27getAdvectionFieldAtPositionENS_7Vector3IdEE120002
_ZNK7crpropa12DiffusionSDE7processEPNS_9CandidateE480003
_ZNK7crpropa12DiffusionSDE7tryStepERKNS_7Vector3IdEERS2_S5_dd960004
_ZNK7crpropa12DiffusionSDE8getAlphaEv5
_ZNK7crpropa12DiffusionSDE8getScaleEv5
_ZNK7crpropa12DiffusionSDE9driftStepERKNS_7Vector3IdEERS2_d120001
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html b/doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html deleted file mode 100644 index 51ca09aab..000000000 --- a/doc/coverageReport/src/module/DiffusionSDE.cpp.gcov.html +++ /dev/null @@ -1,480 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/DiffusionSDE.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - DiffusionSDE.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15420276.2 %
Date:2024-04-08 14:58:22Functions:222588.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/DiffusionSDE.h"
-       2             : 
-       3             : 
-       4             : using namespace crpropa;
-       5             : 
-       6             : // Defining Cash-Karp coefficients
-       7             : const double a[] = { 0., 0., 0., 0., 0., 0., 1. / 5., 0., 0., 0., 0.,
-       8             :                 0., 3. / 40., 9. / 40., 0., 0., 0., 0., 3. / 10., -9. / 10., 6. / 5.,
-       9             :                 0., 0., 0., -11. / 54., 5. / 2., -70. / 27., 35. / 27., 0., 0., 1631.
-      10             :                                 / 55296., 175. / 512., 575. / 13824., 44275. / 110592., 253.
-      11             :                                 / 4096., 0. };
-      12             : 
-      13             : const double b[] = { 37. / 378., 0, 250. / 621., 125. / 594., 0., 512.
-      14             :                 / 1771. };
-      15             : 
-      16             : const double bs[] = { 2825. / 27648., 0., 18575. / 48384., 13525.
-      17             :                 / 55296., 277. / 14336., 1. / 4. };
-      18             : 
-      19             : 
-      20             : 
-      21           4 : DiffusionSDE::DiffusionSDE(ref_ptr<MagneticField> magneticField, double tolerance,
-      22           4 :                                  double minStep, double maxStep, double epsilon) :
-      23           4 :         minStep(0)
-      24             : {
-      25           4 :         setMagneticField(magneticField);
-      26           4 :         setMaximumStep(maxStep);
-      27           4 :         setMinimumStep(minStep);
-      28           4 :         setTolerance(tolerance);
-      29           4 :         setEpsilon(epsilon);
-      30           4 :         setScale(1.);
-      31           4 :         setAlpha(1./3.);
-      32           4 :         }
-      33             : 
-      34           3 : DiffusionSDE::DiffusionSDE(ref_ptr<MagneticField> magneticField, ref_ptr<AdvectionField> advectionField, double tolerance, double minStep, double maxStep, double epsilon) :
-      35           3 :         minStep(0)
-      36             : {
-      37           6 :         setMagneticField(magneticField);
-      38           3 :         setAdvectionField(advectionField);
-      39           3 :         setMaximumStep(maxStep);
-      40           3 :         setMinimumStep(minStep);
-      41           3 :         setTolerance(tolerance);
-      42           3 :         setEpsilon(epsilon);
-      43           3 :         setScale(1.);
-      44           3 :         setAlpha(1./3.);
-      45           3 :         }
-      46             : 
-      47      480003 : void DiffusionSDE::process(Candidate *candidate) const {
-      48             : 
-      49             :     // save the new previous particle state
-      50             : 
-      51      480003 :         ParticleState &current = candidate->current;
-      52             :         candidate->previous = current;
-      53             : 
-      54      480003 :         double h = clip(candidate->getNextStep(), minStep, maxStep) / c_light;
-      55      480003 :         Vector3d PosIn = current.getPosition();
-      56      480003 :         Vector3d DirIn = current.getDirection();
-      57             : 
-      58             :     // rectilinear propagation for neutral particles
-      59             :     // If an advection field is provided the drift is also included
-      60      480003 :         if (current.getCharge() == 0) {
-      61           1 :                 Vector3d dir = current.getDirection();
-      62           1 :                 Vector3d Pos = current.getPosition();
-      63             : 
-      64             :                 Vector3d LinProp(0.);
-      65           1 :                 if (advectionField){
-      66           0 :                         driftStep(Pos, LinProp, h);
-      67             :                 }
-      68             : 
-      69           1 :                 current.setPosition(Pos + LinProp + dir*h*c_light);
-      70           1 :                 candidate->setCurrentStep(h * c_light);
-      71           1 :                 candidate->setNextStep(maxStep);
-      72             :                 return;
-      73             :         }
-      74             : 
-      75      480002 :         double z = candidate->getRedshift();
-      76      480002 :         double rig = current.getEnergy() / current.getCharge();
-      77             : 
-      78             : 
-      79             :     // Calculate the Diffusion tensor
-      80      480002 :         double BTensor[] = {0., 0., 0., 0., 0., 0., 0., 0., 0.};
-      81      480002 :         calculateBTensor(rig, BTensor, PosIn, DirIn, z);
-      82             : 
-      83             : 
-      84             :     // Generate random numbers
-      85      480002 :         double eta[] = {0., 0., 0.};
-      86     1920008 :         for(size_t i=0; i < 3; i++) {
-      87     1440006 :                 eta[i] =  Random::instance().randNorm();
-      88             :         }
-      89             : 
-      90      480002 :         double TStep = BTensor[0] * eta[0];
-      91      480002 :         double NStep = BTensor[4] * eta[1];
-      92      480002 :         double BStep = BTensor[8] * eta[2];
-      93             : 
-      94             :         Vector3d TVec(0.);
-      95             :         Vector3d NVec(0.);
-      96             :         Vector3d BVec(0.);
-      97             : 
-      98             :         Vector3d DirOut = Vector3d(0.);
-      99             : 
-     100             : 
-     101      480002 :         double propTime = TStep * sqrt(h) / c_light;
-     102             :         size_t counter = 0;
-     103             :         double r=42.; //arbitrary number larger than one
-     104             : 
-     105             :         do {
-     106             :                 Vector3d PosOut = Vector3d(0.);
-     107             :                 Vector3d PosErr = Vector3d(0.);
-     108      480002 :                 tryStep(PosIn, PosOut, PosErr, z, propTime);
-     109             :             // calculate the relative position error r and the next time step h
-     110      480002 :                 r = PosErr.getR() / tolerance;
-     111      480002 :                 propTime *= 0.5;
-     112      480002 :                 counter += 1;
-     113             : 
-     114             :     // Check for better break condition
-     115      480002 :         } while (r > 1 && fabs(propTime) >= minStep/c_light);
-     116             : 
-     117             : 
-     118      480002 :         size_t stepNumber = pow(2, counter-1);
-     119      480002 :         double allowedTime = TStep * sqrt(h) / c_light / stepNumber;
-     120             :         Vector3d Start = PosIn;
-     121             :         Vector3d PosOut = Vector3d(0.);
-     122             :         Vector3d PosErr = Vector3d(0.);
-     123      960004 :         for (size_t j=0; j<stepNumber; j++) {
-     124      480002 :                 tryStep(Start, PosOut, PosErr, z, allowedTime);
-     125             :                 Start = PosOut;
-     126             :         }
-     127             : 
-     128             :     // Normalize the tangent vector
-     129      480002 :         TVec = (PosOut-PosIn).getUnitVector();
-     130             :     // Exception: If the magnetic field vanishes: Use only advection.
-     131             :     // If an advection field is not provided --> rectilinear propagation.
-     132             :         double tTest = TVec.getR();
-     133      480002 :         if (tTest != tTest) {
-     134           2 :                 Vector3d dir = current.getDirection();
-     135           2 :                 Vector3d Pos = current.getPosition();
-     136             :                 Vector3d LinProp(0.);
-     137           2 :                 if (advectionField){
-     138           1 :                         driftStep(Pos, LinProp, h);
-     139           1 :                         current.setPosition(Pos + LinProp);
-     140           1 :                         candidate->setCurrentStep(h*c_light);
-     141           1 :                         double newStep = 5*h*c_light;
-     142             :                         newStep = clip(newStep, minStep, maxStep);
-     143           1 :                         candidate->setNextStep(newStep);
-     144             :                         return;
-     145             :                 }
-     146           1 :                 current.setPosition(Pos + dir*h*c_light);
-     147           1 :                 candidate->setCurrentStep(h*c_light);
-     148           1 :                 double newStep = 5*h*c_light;
-     149           1 :                 newStep = clip(newStep, minStep, maxStep);
-     150           1 :                 candidate->setNextStep(newStep);
-     151           1 :                 return;
-     152             :         }
-     153             : 
-     154             :     // Choose a random perpendicular vector as the Normal-vector.
-     155             :     // Prevent 'nan's in the NVec-vector in the case of <TVec, NVec> = 0.
-     156      960000 :         while (NVec.getR()==0.){
-     157      480000 :                 Vector3d RandomVector = Random::instance().randVector();
-     158             :                 NVec = TVec.cross( RandomVector );
-     159             :         }
-     160      480000 :         NVec = NVec.getUnitVector();
-     161             : 
-     162             :     // Calculate the Binormal-vector
-     163      480000 :         BVec = (TVec.cross(NVec)).getUnitVector();
-     164             : 
-     165             :     // Calculate the advection step
-     166             :         Vector3d LinProp(0.);
-     167      480000 :         if (advectionField){
-     168      120000 :                 driftStep(PosIn, LinProp, h);
-     169             :         }
-     170             : 
-     171             :     // Integration of the SDE with a Mayorama-Euler-method
-     172      480000 :         Vector3d PO = PosOut + LinProp + (NVec * NStep + BVec * BStep) * sqrt(h) ;
-     173             : 
-     174             :     // Throw error message if something went wrong with propagation.
-     175             :     // Deactivate candidate.
-     176             :         bool NaN = std::isnan(PO.getR());
-     177      480000 :         if (NaN == true){
-     178           0 :                   candidate->setActive(false);
-     179           0 :                   KISS_LOG_WARNING
-     180           0 :                         << "\nCandidate with 'nan'-position occured: \n"
-     181           0 :                         << "position = " << PO << "\n"
-     182           0 :                         << "PosIn = " << PosIn << "\n"
-     183           0 :                         << "TVec = " << TVec << "\n"
-     184           0 :                         << "TStep = " << std::abs(TStep) << "\n"
-     185           0 :                         << "NVec = " << NVec << "\n"
-     186             :                         << "NStep = " << NStep << "\n"
-     187           0 :                         << "BVec = " << BVec << "\n"
-     188             :                         << "BStep = " << BStep << "\n"
-     189           0 :                         << "Candidate is deactivated!\n";
-     190             :                   return;
-     191             :         }
-     192             : 
-     193             :         //DirOut = (PO - PosIn - LinProp).getUnitVector(); //Advection does not change the momentum vector
-     194             :         // Random direction around the tangential direction accounts for the pitch angle average.
-     195      480000 :         DirOut = Random::instance().randConeVector(TVec, M_PI/2.);
-     196      480000 :         current.setPosition(PO);
-     197      480000 :         current.setDirection(DirOut);
-     198      480000 :         candidate->setCurrentStep(h * c_light);
-     199             : 
-     200             :         double nextStep;
-     201      480000 :         if (stepNumber>1){
-     202           0 :                 nextStep = h*pow(stepNumber, -2.)*c_light;
-     203             :         }
-     204             :         else {
-     205      480000 :                 nextStep = 4 * h*c_light;
-     206             :         }
-     207             : 
-     208      480000 :         candidate->setNextStep(nextStep);
-     209             : 
-     210             :         // Debugging and Testing
-     211             :         // Delete comments if additional information should be stored in candidate
-     212             :         // This property "arcLength" can be interpreted as the effective arclength
-     213             :         // of the propagation along a magnetic field line.
-     214             : 
-     215             : /*
-     216             :         const std::string AL = "arcLength";
-     217             :         if (candidate->hasProperty(AL) == false){
-     218             :           double arcLen = (TStep + NStep + BStep) * sqrt(h);
-     219             :           candidate->setProperty(AL, arcLen);
-     220             :           return;
-     221             :         }
-     222             :         else {
-     223             :           double arcLen = candidate->getProperty(AL);
-     224             :           arcLen += (TStep + NStep + BStep) * sqrt(h);
-     225             :           candidate->setProperty(AL, arcLen);
-     226             :         }
-     227             : */
-     228             : 
-     229             : }
-     230             : 
-     231             : 
-     232      960004 : void DiffusionSDE::tryStep(const Vector3d &PosIn, Vector3d &POut, Vector3d &PosErr,double z, double propStep) const {
-     233             : 
-     234             :         Vector3d k[] = {Vector3d(0.),Vector3d(0.),Vector3d(0.),Vector3d(0.),Vector3d(0.),Vector3d(0.)};
-     235             :         POut = PosIn;
-     236             :         //calculate the sum k_i * b_i
-     237     6720028 :         for (size_t i = 0; i < 6; i++) {
-     238             : 
-     239             :                 Vector3d y_n = PosIn;
-     240    20160084 :                 for (size_t j = 0; j < i; j++)
-     241    14400060 :                   y_n += k[j] * a[i * 6 + j] * propStep;
-     242             : 
-     243             :                 // update k_i = direction of the regular magnetic mean field
-     244     5760024 :                 Vector3d BField = getMagneticFieldAtPosition(y_n, z);
-     245             : 
-     246     5760024 :                 k[i] = BField.getUnitVector() * c_light;
-     247             : 
-     248     5760024 :                 POut += k[i] * b[i] * propStep;
-     249     5760024 :                 PosErr +=  (k[i] * (b[i] - bs[i])) * propStep / kpc;
-     250             : 
-     251             :         }
-     252      960004 : }
-     253             : 
-     254      120001 : void DiffusionSDE::driftStep(const Vector3d &pos, Vector3d &linProp, double h) const {
-     255      120001 :         Vector3d advField = getAdvectionFieldAtPosition(pos);
-     256             :         linProp += advField * h;
-     257      120001 :         return;
-     258             : }
-     259             : 
-     260      480002 : void DiffusionSDE::calculateBTensor(double r, double BTen[], Vector3d pos, Vector3d dir, double z) const {
-     261             : 
-     262      480002 :     double DifCoeff = scale * 6.1e24 * pow((std::abs(r) / 4.0e9), alpha);
-     263      480002 :     BTen[0] = pow( 2  * DifCoeff, 0.5);
-     264      480002 :     BTen[4] = pow(2 * epsilon * DifCoeff, 0.5);
-     265      480002 :     BTen[8] = pow(2 * epsilon * DifCoeff, 0.5);
-     266      480002 :     return;
-     267             : 
-     268             : }
-     269             : 
-     270             : 
-     271           7 : void DiffusionSDE::setMinimumStep(double min) {
-     272           7 :         if (min < 0)
-     273           0 :                 throw std::runtime_error("DiffusionSDE: minStep < 0 ");
-     274           7 :         if (min > maxStep)
-     275           0 :                 throw std::runtime_error("DiffusionSDE: minStep > maxStep");
-     276           7 :         minStep = min;
-     277           7 : }
-     278             : 
-     279           7 : void DiffusionSDE::setMaximumStep(double max) {
-     280           7 :         if (max < minStep)
-     281           0 :                 throw std::runtime_error("DiffusionSDE: maxStep < minStep");
-     282           7 :         maxStep = max;
-     283           7 : }
-     284             : 
-     285             : 
-     286           7 : void DiffusionSDE::setTolerance(double tol) {
-     287           7 :         if ((tol > 1) or (tol < 0))
-     288           0 :                 throw std::runtime_error(
-     289           0 :                                 "DiffusionSDE: tolerance error not in range 0-1");
-     290           7 :         tolerance = tol;
-     291           7 : }
-     292             : 
-     293           7 : void DiffusionSDE::setEpsilon(double e) {
-     294           7 :         if ((e > 1) or (e < 0))
-     295           0 :                 throw std::runtime_error(
-     296           0 :                                 "DiffusionSDE: epsilon not in range 0-1");
-     297           7 :         epsilon = e;
-     298           7 : }
-     299             : 
-     300             : 
-     301           7 : void DiffusionSDE::setAlpha(double a) {
-     302           7 :         if ((a > 2.) or (a < 0))
-     303           0 :                 throw std::runtime_error(
-     304           0 :                                 "DiffusionSDE: alpha not in range 0-2");
-     305           7 :         alpha = a;
-     306           7 : }
-     307             : 
-     308           7 : void DiffusionSDE::setScale(double s) {
-     309           7 :         if (s < 0)
-     310           0 :                 throw std::runtime_error(
-     311           0 :                                 "DiffusionSDE: Scale error: Scale < 0");
-     312           7 :         scale = s;
-     313           7 : }
-     314             : 
-     315           7 : void DiffusionSDE::setMagneticField(ref_ptr<MagneticField> f) {
-     316           7 :         magneticField = f;
-     317           7 : }
-     318             : 
-     319           3 : void DiffusionSDE::setAdvectionField(ref_ptr<AdvectionField> f) {
-     320           3 :         advectionField = f;
-     321           3 : }
-     322             : 
-     323           1 : double DiffusionSDE::getMinimumStep() const {
-     324           1 :         return minStep;
-     325             : }
-     326             : 
-     327           1 : double DiffusionSDE::getMaximumStep() const {
-     328           1 :         return maxStep;
-     329             : }
-     330             : 
-     331           1 : double DiffusionSDE::getTolerance() const {
-     332           1 :         return tolerance;
-     333             : }
-     334             : 
-     335           1 : double DiffusionSDE::getEpsilon() const {
-     336           1 :         return epsilon;
-     337             : }
-     338             : 
-     339           5 : double DiffusionSDE::getAlpha() const {
-     340           5 :         return alpha;
-     341             : }
-     342             : 
-     343           5 : double DiffusionSDE::getScale() const {
-     344           5 :         return scale;
-     345             : }
-     346             : 
-     347           0 : ref_ptr<MagneticField> DiffusionSDE::getMagneticField() const {
-     348           0 :         return magneticField;
-     349             : }
-     350             : 
-     351     5760025 : Vector3d DiffusionSDE::getMagneticFieldAtPosition(Vector3d pos, double z) const {
-     352             :         Vector3d B(0, 0, 0);
-     353             :         try {
-     354             :                 // check if field is valid and use the field vector at the
-     355             :                 // position pos with the redshift z
-     356     5760025 :                 if (magneticField.valid())
-     357     5760025 :                         B = magneticField->getField(pos, z);
-     358             :         }
-     359           0 :         catch (std::exception &e) {
-     360           0 :                 KISS_LOG_ERROR  << "DiffusionSDE: Exception in DiffusionSDE::getMagneticFieldAtPosition.\n"
-     361           0 :                                 << e.what();
-     362           0 :         }       
-     363     5760025 :         return B;
-     364             : }
-     365             : 
-     366           0 : ref_ptr<AdvectionField> DiffusionSDE::getAdvectionField() const {
-     367           0 :         return advectionField;
-     368             : }
-     369             : 
-     370      120002 : Vector3d DiffusionSDE::getAdvectionFieldAtPosition(Vector3d pos) const {
-     371             :         Vector3d AdvField(0.);
-     372             :         try {
-     373             :                 // check if field is valid and use the field vector at the
-     374             :                 // position pos
-     375      120002 :                 if (advectionField.valid())
-     376      120002 :                         AdvField = advectionField->getField(pos);
-     377             :         }
-     378           0 :         catch (std::exception &e) {
-     379           0 :                 KISS_LOG_ERROR  << "DiffusionSDE: Exception in DiffusionSDE::getAdvectionFieldAtPosition.\n"
-     380           0 :                                 << e.what();
-     381           0 :         }
-     382      120002 :         return AdvField;
-     383             : }
-     384             : 
-     385           0 : std::string DiffusionSDE::getDescription() const {
-     386           0 :         std::stringstream s;
-     387           0 :         s << "minStep: " << minStep / kpc  << " kpc, ";
-     388           0 :         s << "maxStep: " << maxStep / kpc  << " kpc, ";
-     389           0 :         s << "tolerance: " << tolerance << "\n";
-     390             : 
-     391           0 :         if (epsilon != 0.1) {
-     392           0 :           s << "epsilon: " << epsilon << ", ";
-     393             :           }
-     394             : 
-     395           0 :         if (alpha != 1./3.) {
-     396           0 :           s << "alpha: " << alpha << "\n";
-     397             :           }
-     398             : 
-     399           0 :         if (scale != 1.) {
-     400           0 :           s << "D_0: " << scale*6.1e24 << " m^2/s" << "\n";
-     401             :           }
-     402             : 
-     403           0 :         return s.str();
-     404           0 : }
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html deleted file mode 100644 index a80dbd404..000000000 --- a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func-sort-c.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMDoublePairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMDoublePairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:687294.4 %
Date:2024-04-08 14:58:22Functions:1010100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22EMDoublePairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa22EMDoublePairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa22EMDoublePairProduction7processEPNS_9CandidateE1
_ZNK7crpropa22EMDoublePairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa22EMDoublePairProduction11setThinningEd3
_ZN7crpropa22EMDoublePairProduction8setLimitEd3
_ZN7crpropa22EMDoublePairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZN7crpropa22EMDoublePairProduction16setHaveElectronsEb4
_ZN7crpropa22EMDoublePairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa22EMDoublePairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html deleted file mode 100644 index 4e691a3a6..000000000 --- a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.func.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMDoublePairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMDoublePairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:687294.4 %
Date:2024-04-08 14:58:22Functions:1010100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22EMDoublePairProduction11setThinningEd3
_ZN7crpropa22EMDoublePairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa22EMDoublePairProduction16setHaveElectronsEb4
_ZN7crpropa22EMDoublePairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22EMDoublePairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa22EMDoublePairProduction8setLimitEd3
_ZN7crpropa22EMDoublePairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZNK7crpropa22EMDoublePairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa22EMDoublePairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa22EMDoublePairProduction7processEPNS_9CandidateE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html b/doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html deleted file mode 100644 index 5469562c6..000000000 --- a/doc/coverageReport/src/module/EMDoublePairProduction.cpp.gcov.html +++ /dev/null @@ -1,209 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMDoublePairProduction.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMDoublePairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:687294.4 %
Date:2024-04-08 14:58:22Functions:1010100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/EMDoublePairProduction.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #include <fstream>
-       6             : #include <limits>
-       7             : #include <stdexcept>
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11           3 : EMDoublePairProduction::EMDoublePairProduction(ref_ptr<PhotonField> photonField, bool haveElectrons, double thinning, double limit) {
-      12           3 :         setPhotonField(photonField);
-      13           3 :         setHaveElectrons(haveElectrons);
-      14           3 :         setLimit(limit);
-      15           3 :         setThinning(thinning);
-      16           3 : }
-      17             : 
-      18          15 : void EMDoublePairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
-      19          15 :         this->photonField = photonField;
-      20          15 :         std::string fname = photonField->getFieldName();
-      21          15 :         setDescription("EMDoublePairProduction: " + fname);
-      22          45 :         initRate(getDataPath("EMDoublePairProduction/rate_" + fname + ".txt"));
-      23          15 : }
-      24             : 
-      25           4 : void EMDoublePairProduction::setHaveElectrons(bool haveElectrons) {
-      26           4 :         this->haveElectrons = haveElectrons;
-      27           4 : }
-      28             : 
-      29           3 : void EMDoublePairProduction::setLimit(double limit) {
-      30           3 :         this->limit = limit;
-      31           3 : }
-      32             : 
-      33           3 : void EMDoublePairProduction::setThinning(double thinning) {
-      34           3 :         this->thinning = thinning;
-      35           3 : }
-      36             : 
-      37          15 : void EMDoublePairProduction::initRate(std::string filename) {
-      38          15 :         std::ifstream infile(filename.c_str());
-      39             : 
-      40          15 :         if (!infile.good())
-      41           0 :                 throw std::runtime_error("EMDoublePairProduction: could not open file " + filename);
-      42             : 
-      43             :         // clear previously loaded interaction rates
-      44          15 :         tabEnergy.clear();
-      45          15 :         tabRate.clear();
-      46             : 
-      47        3306 :         while (infile.good()) {
-      48        3291 :                 if (infile.peek() != '#') {
-      49             :                         double a, b;
-      50             :                         infile >> a >> b;
-      51        3231 :                         if (infile) {
-      52        3216 :                                 tabEnergy.push_back(pow(10, a) * eV);
-      53        3216 :                                 tabRate.push_back(b / Mpc);
-      54             :                         }
-      55             :                 }
-      56        3291 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      57             :         }
-      58          15 :         infile.close();
-      59          15 : }
-      60             : 
-      61             : 
-      62           1 : void EMDoublePairProduction::performInteraction(Candidate *candidate) const {
-      63             :         // the photon is lost after the interaction
-      64           1 :         candidate->setActive(false);
-      65             : 
-      66           1 :         if (not haveElectrons)
-      67           0 :                 return;
-      68             : 
-      69             :         // Use assumption of Lee 96 arXiv:9604098
-      70             :         // Energy is equally shared between one e+e- pair, but take mass of second e+e- pair into account.
-      71             :         // This approximation has been shown to be valid within -1.5%.
-      72           1 :         double z = candidate->getRedshift();
-      73           1 :         double E = candidate->current.getEnergy() * (1 + z);
-      74           1 :         double Ee = (E - 2 * mass_electron * c_squared) / 2;
-      75             : 
-      76           1 :         Random &random = Random::instance();
-      77           1 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-      78             : 
-      79           1 :         double f = Ee / E;
-      80             : 
-      81           1 :         if (haveElectrons) {
-      82           1 :                 if (random.rand() < pow(1 - f, thinning)) {
-      83           1 :                         double w = 1. / pow(1 - f, thinning);
-      84           1 :                         candidate->addSecondary( 11, Ee / (1 + z), pos, w, interactionTag);
-      85             :                 } 
-      86           1 :                 if (random.rand() < pow(f, thinning)) {
-      87           1 :                         double w = 1. / pow(f, thinning);
-      88           1 :                         candidate->addSecondary(-11, Ee / (1 + z), pos, w, interactionTag);
-      89             :                 }
-      90             :         }
-      91             : }
-      92             : 
-      93           1 : void EMDoublePairProduction::process(Candidate *candidate) const {
-      94             :         // check if photon
-      95           1 :         if (candidate->current.getId() != 22)
-      96             :                 return;
-      97             : 
-      98             :         // scale the electron energy instead of background photons
-      99           1 :         double z = candidate->getRedshift();
-     100           1 :         double E = (1 + z) * candidate->current.getEnergy();
-     101             : 
-     102             :         // check if in tabulated energy range
-     103           1 :         if (E < tabEnergy.front() or (E > tabEnergy.back()))
-     104             :                 return;
-     105             : 
-     106             :         // interaction rate
-     107           1 :         double rate = interpolate(E, tabEnergy, tabRate);
-     108           1 :         rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
-     109             : 
-     110             :         // check for interaction
-     111           1 :         Random &random = Random::instance();
-     112           1 :         double randDistance = -log(random.rand()) / rate;
-     113           1 :         double step = candidate->getCurrentStep();
-     114           1 :         if (step < randDistance) {
-     115           1 :                 candidate->limitNextStep(limit / rate);
-     116           1 :                 return;
-     117             :         } else { // after performing interaction photon ceases to exist (hence return)
-     118           0 :                 performInteraction(candidate);
-     119           0 :                 return;
-     120             :         }
-     121             : 
-     122             : }
-     123             : 
-     124           1 : void EMDoublePairProduction::setInteractionTag(std::string tag) {
-     125           1 :         interactionTag = tag;
-     126           1 : }
-     127             : 
-     128           2 : std::string EMDoublePairProduction::getInteractionTag() const {
-     129           2 :         return interactionTag;
-     130             : }
-     131             : 
-     132             : 
-     133             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html deleted file mode 100644 index 8878c9d70..000000000 --- a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMInverseComptonScattering.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMInverseComptonScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12813396.2 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa26EMInverseComptonScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa32ICSSecondariesEnergyDistribution6sampleEdd1
_ZN7crpropa32ICSSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa26EMInverseComptonScattering18performInteractionEPNS_9CandidateE1
_ZNK7crpropa26EMInverseComptonScattering17getInteractionTagB5cxx11Ev2
_ZN7crpropa26EMInverseComptonScattering11setThinningEd5
_ZN7crpropa26EMInverseComptonScattering8setLimitEd5
_ZN7crpropa26EMInverseComptonScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd5
_ZN7crpropa26EMInverseComptonScattering14setHavePhotonsEb6
_ZN7crpropa26EMInverseComptonScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE17
_ZN7crpropa26EMInverseComptonScattering18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZN7crpropa26EMInverseComptonScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZNK7crpropa26EMInverseComptonScattering7processEPNS_9CandidateE15285
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html deleted file mode 100644 index aa4472145..000000000 --- a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMInverseComptonScattering.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMInverseComptonScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12813396.2 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa26EMInverseComptonScattering11setThinningEd5
_ZN7crpropa26EMInverseComptonScattering14setHavePhotonsEb6
_ZN7crpropa26EMInverseComptonScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE17
_ZN7crpropa26EMInverseComptonScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa26EMInverseComptonScattering18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZN7crpropa26EMInverseComptonScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE17
_ZN7crpropa26EMInverseComptonScattering8setLimitEd5
_ZN7crpropa26EMInverseComptonScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd5
_ZN7crpropa32ICSSecondariesEnergyDistribution6sampleEdd1
_ZN7crpropa32ICSSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa26EMInverseComptonScattering17getInteractionTagB5cxx11Ev2
_ZNK7crpropa26EMInverseComptonScattering18performInteractionEPNS_9CandidateE1
_ZNK7crpropa26EMInverseComptonScattering7processEPNS_9CandidateE15285
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html b/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html deleted file mode 100644 index c5f4dfec4..000000000 --- a/doc/coverageReport/src/module/EMInverseComptonScattering.cpp.gcov.html +++ /dev/null @@ -1,325 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMInverseComptonScattering.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMInverseComptonScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:12813396.2 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/EMInverseComptonScattering.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Random.h"
-       4             : #include "crpropa/Common.h"
-       5             : 
-       6             : #include <fstream>
-       7             : #include <limits>
-       8             : #include <stdexcept>
-       9             : 
-      10             : namespace crpropa {
-      11             : 
-      12             : static const double mec2 = mass_electron * c_squared;
-      13             : 
-      14           5 : EMInverseComptonScattering::EMInverseComptonScattering(ref_ptr<PhotonField> photonField, bool havePhotons, double thinning, double limit) {
-      15           5 :         setPhotonField(photonField);
-      16           5 :         setHavePhotons(havePhotons);
-      17           5 :         setLimit(limit);
-      18           5 :         setThinning(thinning);
-      19           5 : }
-      20             : 
-      21          17 : void EMInverseComptonScattering::setPhotonField(ref_ptr<PhotonField> photonField) {
-      22          17 :         this->photonField = photonField;
-      23          17 :         std::string fname = photonField->getFieldName();
-      24          17 :         setDescription("EMInverseComptonScattering: " + fname);
-      25          51 :         initRate(getDataPath("EMInverseComptonScattering/rate_" + fname + ".txt"));
-      26          51 :         initCumulativeRate(getDataPath("EMInverseComptonScattering/cdf_" + fname + ".txt"));
-      27          17 : }
-      28             : 
-      29           6 : void EMInverseComptonScattering::setHavePhotons(bool havePhotons) {
-      30           6 :         this->havePhotons = havePhotons;
-      31           6 : }
-      32             : 
-      33           5 : void EMInverseComptonScattering::setLimit(double limit) {
-      34           5 :         this->limit = limit;
-      35           5 : }
-      36             : 
-      37           5 : void EMInverseComptonScattering::setThinning(double thinning) {
-      38           5 :         this->thinning = thinning;
-      39           5 : }
-      40             : 
-      41          17 : void EMInverseComptonScattering::initRate(std::string filename) {
-      42          17 :         std::ifstream infile(filename.c_str());
-      43             : 
-      44          17 :         if (!infile.good())
-      45           0 :                 throw std::runtime_error("EMInverseComptonScattering: could not open file " + filename);
-      46             : 
-      47             :         // clear previously loaded tables
-      48          17 :         tabEnergy.clear();
-      49          17 :         tabRate.clear();
-      50             : 
-      51        4879 :         while (infile.good()) {
-      52        4862 :                 if (infile.peek() != '#') {
-      53             :                         double a, b;
-      54             :                         infile >> a >> b;
-      55        4794 :                         if (infile) {
-      56        4777 :                                 tabEnergy.push_back(pow(10, a) * eV);
-      57        4777 :                                 tabRate.push_back(b / Mpc);
-      58             :                         }
-      59             :                 }
-      60        4862 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      61             :         }
-      62          17 :         infile.close();
-      63          17 : }
-      64             : 
-      65          17 : void EMInverseComptonScattering::initCumulativeRate(std::string filename) {
-      66          17 :         std::ifstream infile(filename.c_str());
-      67             : 
-      68          17 :         if (!infile.good())
-      69           0 :                 throw std::runtime_error("EMInverseComptonScattering: could not open file " + filename);
-      70             : 
-      71             :         // clear previously loaded tables
-      72          17 :         tabE.clear();
-      73          17 :         tabs.clear();
-      74          17 :         tabCDF.clear();
-      75             :         
-      76             :         // skip header
-      77          85 :         while (infile.peek() == '#')
-      78          68 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      79             : 
-      80             :         // read s values in first line
-      81             :         double a;
-      82             :         infile >> a; // skip first value
-      83        3000 :         while (infile.good() and (infile.peek() != '\n')) {
-      84             :                 infile >> a;
-      85        2983 :                 tabs.push_back(pow(10, a) * eV * eV);
-      86             :         }
-      87             : 
-      88             :         // read all following lines: E, cdf values
-      89        4794 :         while (infile.good()) {
-      90             :                 infile >> a;
-      91        4794 :                 if (!infile)
-      92             :                         break;  // end of file
-      93        4777 :                 tabE.push_back(pow(10, a) * eV);
-      94             :                 std::vector<double> cdf;
-      95      843000 :                 for (int i = 0; i < tabs.size(); i++) {
-      96             :                         infile >> a;
-      97      838223 :                         cdf.push_back(a / Mpc);
-      98             :                 }
-      99        4777 :                 tabCDF.push_back(cdf);
-     100             :         }
-     101          17 :         infile.close();
-     102          17 : }
-     103             : 
-     104             : // Class to calculate the energy distribution of the ICS photon and to sample from it
-     105             : class ICSSecondariesEnergyDistribution {
-     106             :         private:
-     107             :                 std::vector< std::vector<double> > data;
-     108             :                 std::vector<double> s_values;
-     109             :                 size_t Ns;
-     110             :                 size_t Nrer;
-     111             :                 double s_min;
-     112             :                 double s_max;
-     113             :                 double dls;
-     114             : 
-     115             :         public:
-     116             :                 // differential cross-section, see Lee '96 (arXiv:9604098), eq. 23 for x = Ee'/Ee
-     117             :                 double dSigmadE(double x, double beta) {
-     118     1000000 :                         double q = ((1 - beta) / beta) * (1 - 1./x);
-     119     1000000 :                         return ((1 + beta) / beta) * (x + 1./x + 2 * q + q * q);
-     120             :                 }
-     121             : 
-     122             :                 // create the cumulative energy distribution of the up-scattered photon
-     123           1 :                 ICSSecondariesEnergyDistribution() {
-     124           1 :                         Ns = 1000;
-     125           1 :                         Nrer = 1000;
-     126           1 :                         s_min = mec2 * mec2;
-     127           1 :                         s_max = 2e23 * eV * eV;
-     128           1 :                         dls = (log(s_max) - log(s_min)) / Ns;
-     129           1 :                         data = std::vector< std::vector<double> >(1000, std::vector<double>(1000));
-     130           1 :                         std::vector<double> data_i(1000);
-     131             : 
-     132             :                         // tabulate s bin borders
-     133           1 :                         s_values = std::vector<double>(1001);
-     134        1002 :                         for (size_t i = 0; i < Ns + 1; ++i)
-     135        1001 :                                 s_values[i] = s_min * exp(i*dls);
-     136             : 
-     137             : 
-     138             :                         // for each s tabulate cumulative differential cross section
-     139        1001 :                         for (size_t i = 0; i < Ns; i++) {
-     140        1000 :                                 double s = s_min * exp((i+0.5) * dls);
-     141        1000 :                                 double beta = (s - s_min) / (s + s_min);
-     142        1000 :                                 double x0 = (1 - beta) / (1 + beta);
-     143        1000 :                                 double dlx = -log(x0) / Nrer;
-     144             : 
-     145             :                                 // cumulative midpoint integration
-     146        1000 :                                 data_i[0] = dSigmadE(x0, beta) * expm1(dlx);
-     147     1000000 :                                 for (size_t j = 1; j < Nrer; j++) {
-     148      999000 :                                         double x = x0 * exp((j+0.5) * dlx);
-     149      999000 :                                         double dx = exp((j+1) * dlx) - exp(j * dlx);
-     150      999000 :                                         data_i[j] = dSigmadE(x, beta) * dx;
-     151      999000 :                                         data_i[j] += data_i[j-1];
-     152             :                                 }
-     153        1000 :                                 data[i] = data_i;
-     154             :                         }
-     155           1 :                 }
-     156             : 
-     157             :                 // draw random energy for the up-scattered photon Ep(Ee, s)
-     158           1 :                 double sample(double Ee, double s) {
-     159           1 :                         size_t idx = std::lower_bound(s_values.begin(), s_values.end(), s) - s_values.begin();
-     160           1 :                         std::vector<double> s0 = data[idx];
-     161           1 :                         Random &random = Random::instance();
-     162           1 :                         size_t j = random.randBin(s0) + 1; // draw random bin (upper bin boundary returned)
-     163           1 :                         double beta = (s - s_min) / (s + s_min);
-     164           1 :                         double x0 = (1 - beta) / (1 + beta);
-     165           1 :                         double dlx = -log(x0) / Nrer;
-     166           1 :                         double binWidth = x0 * (exp(j * dlx) - exp((j-1) * dlx));
-     167           1 :                         double Ep = (x0 * exp((j-1) * dlx) + binWidth) * Ee;
-     168           2 :                         return std::min(Ee, Ep); // prevent Ep > Ee from numerical inaccuracies
-     169             :                 }
-     170             : };
-     171             : 
-     172           1 : void EMInverseComptonScattering::performInteraction(Candidate *candidate) const {
-     173             :         // scale the particle energy instead of background photons
-     174           1 :         double z = candidate->getRedshift();
-     175           1 :         double E = candidate->current.getEnergy() * (1 + z);
-     176             : 
-     177           1 :         if (E < tabE.front() or E > tabE.back())
-     178             :                 return;
-     179             : 
-     180             :         // sample the value of s
-     181           1 :         Random &random = Random::instance();
-     182           1 :         size_t i = closestIndex(E, tabE);
-     183           1 :         size_t j = random.randBin(tabCDF[i]);
-     184           1 :         double s_kin = pow(10, log10(tabs[j]) + (random.rand() - 0.5) * 0.1);
-     185           1 :         double s = s_kin + mec2 * mec2;
-     186             : 
-     187             :         // sample electron energy after scattering
-     188           1 :         static ICSSecondariesEnergyDistribution distribution;
-     189           1 :         double Enew = distribution.sample(E, s);
-     190             : 
-     191             :         // add up-scattered photon
-     192           1 :         double Esecondary = E - Enew;
-     193           1 :         double f = Enew / E;
-     194           1 :         if (havePhotons) {
-     195           1 :                 if (random.rand() < pow(1 - f, thinning)) {
-     196           1 :                         double w = 1. / pow(1 - f, thinning);
-     197           1 :                         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     198           1 :                         candidate->addSecondary(22, Esecondary / (1 + z), pos, w, interactionTag);
-     199             :                 }
-     200             :         }
-     201             : 
-     202             :         // update the primary particle energy; do this after adding the secondary to correctly set the secondary's parent
-     203           1 :         candidate->current.setEnergy(Enew / (1 + z));
-     204             : }
-     205             : 
-     206       15285 : void EMInverseComptonScattering::process(Candidate *candidate) const {
-     207             :         // check if electron / positron
-     208       15285 :         int id = candidate->current.getId();
-     209       15285 :         if (abs(id) != 11)
-     210             :                 return;
-     211             : 
-     212             :         // scale the particle energy instead of background photons
-     213           1 :         double z = candidate->getRedshift();
-     214           1 :         double E = candidate->current.getEnergy() * (1 + z);
-     215             : 
-     216           1 :         if (E < tabEnergy.front() or (E > tabEnergy.back()))
-     217             :                 return;
-     218             : 
-     219             :         // interaction rate
-     220           1 :         double rate = interpolate(E, tabEnergy, tabRate);
-     221           1 :         rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
-     222             : 
-     223             :         // run this loop at least once to limit the step size
-     224           1 :         double step = candidate->getCurrentStep();
-     225           1 :         Random &random = Random::instance();
-     226             :         do {
-     227           1 :                 double randDistance = -log(random.rand()) / rate;
-     228             : 
-     229             :                 // check for interaction; if it doesn't ocurr, limit next step
-     230           1 :                 if (step < randDistance) {
-     231           1 :                         candidate->limitNextStep(limit / rate);
-     232           1 :                         return;
-     233             :                 }
-     234           0 :                 performInteraction(candidate);
-     235             : 
-     236             :                 // repeat with remaining step
-     237           0 :                 step -= randDistance;
-     238           0 :         } while (step > 0);
-     239             : }
-     240             : 
-     241           1 : void EMInverseComptonScattering::setInteractionTag(std::string tag) {
-     242           1 :         interactionTag = tag;
-     243           1 : }
-     244             : 
-     245           2 : std::string EMInverseComptonScattering::getInteractionTag() const {
-     246           2 :         return interactionTag;
-     247             : }
-     248             : 
-     249             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html deleted file mode 100644 index 084270148..000000000 --- a/doc/coverageReport/src/module/EMPairProduction.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMPairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13413797.8 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16EMPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa31PPSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa16EMPairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa16EMPairProduction8setLimitEd9
_ZN7crpropa16EMPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd9
_ZN7crpropa16EMPairProduction11setThinningEd13
_ZN7crpropa16EMPairProduction16setHaveElectronsEb14
_ZN7crpropa16EMPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE33
_ZN7crpropa16EMPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa16EMPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa31PPSecondariesEnergyDistribution6sampleEdd563
_ZNK7crpropa16EMPairProduction18performInteractionEPNS_9CandidateE563
_ZNK7crpropa16EMPairProduction7processEPNS_9CandidateE16965
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMPairProduction.cpp.func.html b/doc/coverageReport/src/module/EMPairProduction.cpp.func.html deleted file mode 100644 index 082cd9399..000000000 --- a/doc/coverageReport/src/module/EMPairProduction.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMPairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13413797.8 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16EMPairProduction11setThinningEd13
_ZN7crpropa16EMPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE33
_ZN7crpropa16EMPairProduction16setHaveElectronsEb14
_ZN7crpropa16EMPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa16EMPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa16EMPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE33
_ZN7crpropa16EMPairProduction8setLimitEd9
_ZN7crpropa16EMPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd9
_ZN7crpropa31PPSecondariesEnergyDistribution6sampleEdd563
_ZN7crpropa31PPSecondariesEnergyDistributionC2Ev1
_ZNK7crpropa16EMPairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa16EMPairProduction18performInteractionEPNS_9CandidateE563
_ZNK7crpropa16EMPairProduction7processEPNS_9CandidateE16965
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html b/doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html deleted file mode 100644 index b3986bf74..000000000 --- a/doc/coverageReport/src/module/EMPairProduction.cpp.gcov.html +++ /dev/null @@ -1,340 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMPairProduction.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13413797.8 %
Date:2024-04-08 14:58:22Functions:1313100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/EMPairProduction.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #include <fstream>
-       6             : #include <limits>
-       7             : #include <stdexcept>
-       8             : 
-       9             : 
-      10             : namespace crpropa {
-      11             : 
-      12             : static const double mec2 = mass_electron * c_squared;
-      13             : 
-      14           9 : EMPairProduction::EMPairProduction(ref_ptr<PhotonField> photonField, bool haveElectrons, double thinning, double limit) {
-      15           9 :         setPhotonField(photonField);
-      16           9 :         setThinning(thinning);
-      17           9 :         setLimit(limit);
-      18           9 :         setHaveElectrons(haveElectrons);
-      19           9 : }
-      20             : 
-      21          33 : void EMPairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
-      22          33 :         this->photonField = photonField;
-      23          33 :         std::string fname = photonField->getFieldName();
-      24          33 :         setDescription("EMPairProduction: " + fname);
-      25          99 :         initRate(getDataPath("EMPairProduction/rate_" + fname + ".txt"));
-      26          99 :         initCumulativeRate(getDataPath("EMPairProduction/cdf_" + fname + ".txt"));
-      27          33 : }
-      28             : 
-      29          14 : void EMPairProduction::setHaveElectrons(bool haveElectrons) {
-      30          14 :         this->haveElectrons = haveElectrons;
-      31          14 : }
-      32             : 
-      33           9 : void EMPairProduction::setLimit(double limit) {
-      34           9 :         this->limit = limit;
-      35           9 : }
-      36             : 
-      37          13 : void EMPairProduction::setThinning(double thinning) {
-      38          13 :         this->thinning = thinning;
-      39          13 : }
-      40             : 
-      41          33 : void EMPairProduction::initRate(std::string filename) {
-      42          33 :         std::ifstream infile(filename.c_str());
-      43             : 
-      44          33 :         if (!infile.good())
-      45           0 :                 throw std::runtime_error("EMPairProduction: could not open file " + filename);
-      46             : 
-      47             :         // clear previously loaded interaction rates
-      48          33 :         tabEnergy.clear();
-      49          33 :         tabRate.clear();
-      50             : 
-      51        7510 :         while (infile.good()) {
-      52        7477 :                 if (infile.peek() != '#') {
-      53             :                         double a, b;
-      54             :                         infile >> a >> b;
-      55        7345 :                         if (infile) {
-      56        7312 :                                 tabEnergy.push_back(pow(10, a) * eV);
-      57        7312 :                                 tabRate.push_back(b / Mpc);
-      58             :                         }
-      59             :                 }
-      60        7477 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      61             :         }
-      62          33 :         infile.close();
-      63          33 : }
-      64             : 
-      65          33 : void EMPairProduction::initCumulativeRate(std::string filename) {
-      66          33 :         std::ifstream infile(filename.c_str());
-      67             : 
-      68          33 :         if (!infile.good())
-      69           0 :                 throw std::runtime_error("EMPairProduction: could not open file " + filename);
-      70             : 
-      71             :         // clear previously loaded tables
-      72          33 :         tabE.clear();
-      73          33 :         tabs.clear();
-      74          33 :         tabCDF.clear();
-      75             :         
-      76             :         // skip header
-      77         165 :         while (infile.peek() == '#')
-      78         132 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      79             : 
-      80             :         // read s values in first line
-      81             :         double a;
-      82             :         infile >> a; // skip first value
-      83        3663 :         while (infile.good() and (infile.peek() != '\n')) {
-      84             :                 infile >> a;
-      85        3630 :                 tabs.push_back(pow(10, a) * eV * eV);
-      86             :         }
-      87             : 
-      88             :         // read all following lines: E, cdf values
-      89        7345 :         while (infile.good()) {
-      90             :                 infile >> a;
-      91        7345 :                 if (!infile)
-      92             :                         break;  // end of file
-      93        7312 :                 tabE.push_back(pow(10, a) * eV);
-      94             :                 std::vector<double> cdf;
-      95      811632 :                 for (int i = 0; i < tabs.size(); i++) {
-      96             :                         infile >> a;
-      97      804320 :                         cdf.push_back(a / Mpc);
-      98             :                 }
-      99        7312 :                 tabCDF.push_back(cdf);
-     100             :         }
-     101          33 :         infile.close();
-     102          33 : }
-     103             : 
-     104             : // Hold an data array to interpolate the energy distribution on
-     105             : class PPSecondariesEnergyDistribution {
-     106             :         private:
-     107             :                 std::vector<double> tab_s;
-     108             :                 std::vector< std::vector<double> > data;
-     109             :                 size_t N;
-     110             : 
-     111             :         public:
-     112             :                 // differential cross section for pair production for x = Epositron/Egamma, compare Lee 96 arXiv:9604098
-     113             :                 double dSigmadE_PPx(double x, double beta) {
-     114     1000000 :                         double A = (x / (1. - x) + (1. - x) / x );
-     115     1000000 :                         double B =  (1. / x + 1. / (1. - x) );
-     116        1000 :                         double y = (1 - beta * beta);
-     117     1000000 :                         return A + y * B - y * y / 4 * B * B;
-     118             :                 }
-     119             : 
-     120           1 :                 PPSecondariesEnergyDistribution() {
-     121           1 :                         N = 1000;
-     122             :                         size_t Ns = 1000;
-     123             :                         double s_min = 4 * mec2 * mec2;
-     124             :                         double s_max = 1e23 * eV * eV;
-     125             :                         double dls = log(s_max / s_min) / Ns;
-     126           1 :                         data = std::vector< std::vector<double> >(Ns, std::vector<double>(N));
-     127           1 :                         tab_s = std::vector<double>(Ns + 1);
-     128             : 
-     129        1002 :                         for (size_t i = 0; i < Ns + 1; ++i)
-     130        1001 :                                 tab_s[i] = s_min * exp(i*dls); // tabulate s bin borders
-     131             : 
-     132        1001 :                         for (size_t i = 0; i < Ns; i++) {
-     133        1000 :                                 double s = s_min * exp(i*dls + 0.5*dls);
-     134        1000 :                                 double beta = sqrt(1 - s_min/s);
-     135        1000 :                                 double x0 = (1 - beta) / 2;
-     136        1000 :                                 double dx = log((1 + beta) / (1 - beta)) / N;
-     137             : 
-     138             :                                 // cumulative midpoint integration
-     139        1000 :                                 std::vector<double> data_i(1000);
-     140        1000 :                                 data_i[0] = dSigmadE_PPx(x0, beta) * expm1(dx);
-     141     1000000 :                                 for (size_t j = 1; j < N; j++) {
-     142      999000 :                                         double x = x0 * exp(j*dx + 0.5*dx);
-     143      999000 :                                         double binWidth = exp((j+1)*dx)-exp(j*dx);
-     144      999000 :                                         data_i[j] = dSigmadE_PPx(x, beta) * binWidth + data_i[j-1];
-     145             :                                 }
-     146        1000 :                                 data[i] = data_i;
-     147             :                         }
-     148           1 :                 }
-     149             : 
-     150             :                 // sample positron energy from cdf(E, s_kin)
-     151         563 :                 double sample(double E0, double s) {
-     152             :                         // get distribution for given s
-     153         563 :                         size_t idx = std::lower_bound(tab_s.begin(), tab_s.end(), s) - tab_s.begin();
-     154         563 :                         if (idx > data.size())
-     155             :                                 return NAN;
-     156             :                                 
-     157         563 :                         std::vector<double> s0 = data[idx];
-     158             : 
-     159             :                         // draw random bin
-     160         563 :                         Random &random = Random::instance();
-     161         563 :                         size_t j = random.randBin(s0) + 1;
-     162             : 
-     163             :                         double s_min = 4. * mec2 * mec2;
-     164         563 :                         double beta = sqrtl(1. - s_min / s);
-     165         563 :                         double x0 = (1. - beta) / 2.;
-     166         563 :                         double dx = log((1 + beta) / (1 - beta)) / N;
-     167         563 :                         double binWidth = x0 * (exp(j*dx) - exp((j-1)*dx));
-     168         563 :                         if (random.rand() < 0.5)
-     169         290 :                                 return E0 * (x0 * exp((j-1) * dx) + binWidth);
-     170             :                         else
-     171         273 :                                 return E0 * (1 - (x0 * exp((j-1) * dx) + binWidth));
-     172             :                 }
-     173             : };
-     174             : 
-     175         563 : void EMPairProduction::performInteraction(Candidate *candidate) const {
-     176             :         // scale particle energy instead of background photon energy
-     177         563 :         double z = candidate->getRedshift();
-     178         563 :         double E = candidate->current.getEnergy() * (1 + z);
-     179             : 
-     180             :         // check if secondary electron pair needs to be produced
-     181         563 :         if (not haveElectrons)
-     182           0 :                 return;
-     183             : 
-     184             :         // check if in tabulated energy range
-     185         563 :         if (E < tabE.front() or (E > tabE.back()))
-     186             :                 return;
-     187             : 
-     188             :         // sample the value of s
-     189         563 :         Random &random = Random::instance();
-     190         563 :         size_t i = closestIndex(E, tabE);  // find closest tabulation point
-     191         563 :         size_t j = random.randBin(tabCDF[i]);
-     192        1092 :         double lo = std::max(4 * mec2 * mec2, tabs[j-1]);  // first s-tabulation point below min(s_kin) = (2 me c^2)^2; ensure physical value
-     193         563 :         double hi = tabs[j];
-     194         563 :         double s = lo + random.rand() * (hi - lo);
-     195             : 
-     196             :         // sample electron / positron energy
-     197         563 :         static PPSecondariesEnergyDistribution interpolation;
-     198         563 :         double Ee = interpolation.sample(E, s);
-     199         563 :         double Ep = E - Ee;
-     200         563 :         double f = Ep / E;
-     201             : 
-     202             :         // for some backgrounds Ee=nan due to precision limitations.
-     203         563 :         if (not std::isfinite(Ee) || not std::isfinite(Ep))
-     204             :                 return;
-     205             : 
-     206             :         // photon is lost after interacting
-     207         563 :         candidate->setActive(false);
-     208             : 
-     209             :         // sample random position along current step
-     210         563 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     211             :         // apply sampling
-     212         563 :         if (random.rand() < pow(f, thinning)) {
-     213         563 :                 double w = 1. / pow(f, thinning);
-     214         563 :                 candidate->addSecondary(11, Ep / (1 + z), pos, w, interactionTag);
-     215             :         }
-     216         563 :         if (random.rand() < pow(1 - f, thinning)){
-     217         563 :                 double w = 1. / pow(1 - f, thinning);
-     218         563 :                 candidate->addSecondary(-11, Ee / (1 + z), pos, w, interactionTag);  
-     219             :         }
-     220             : }
-     221             : 
-     222       16965 : void EMPairProduction::process(Candidate *candidate) const {
-     223             :         // check if photon
-     224       16965 :         if (candidate->current.getId() != 22)
-     225             :                 return;
-     226             : 
-     227             :         // scale particle energy instead of background photon energy
-     228         841 :         double z = candidate->getRedshift();
-     229         841 :         double E = candidate->current.getEnergy() * (1 + z);
-     230             : 
-     231             :         // check if in tabulated energy range
-     232         841 :         if ((E < tabEnergy.front()) or (E > tabEnergy.back()))
-     233             :                 return;
-     234             : 
-     235             :         // interaction rate
-     236         651 :         double rate = interpolate(E, tabEnergy, tabRate);
-     237         651 :         rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
-     238             : 
-     239             :         // run this loop at least once to limit the step size 
-     240         651 :         double step = candidate->getCurrentStep();
-     241         651 :         Random &random = Random::instance();
-     242             :         do {
-     243         651 :                 double randDistance = -log(random.rand()) / rate;
-     244             :                 // check for interaction; if it doesn't ocurr, limit next step
-     245         651 :                 if (step < randDistance) { 
-     246          89 :                         candidate->limitNextStep(limit / rate);
-     247             :                 } else {
-     248         562 :                         performInteraction(candidate);
-     249         562 :                         return;
-     250             :                 }
-     251          89 :                 step -= randDistance; 
-     252          89 :         } while (step > 0.);
-     253             : 
-     254             : }
-     255             : 
-     256           1 : void EMPairProduction::setInteractionTag(std::string tag) {
-     257           1 :         interactionTag = tag;
-     258           1 : }
-     259             : 
-     260           2 : std::string EMPairProduction::getInteractionTag() const {
-     261           2 :         return interactionTag;
-     262             : }
-     263             : 
-     264             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html deleted file mode 100644 index bfb861b6b..000000000 --- a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func-sort-c.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMTripletPairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMTripletPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9410094.0 %
Date:2024-04-08 14:58:22Functions:1111100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa23EMTripletPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa23EMTripletPairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa23EMTripletPairProduction7processEPNS_9CandidateE1
_ZNK7crpropa23EMTripletPairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa23EMTripletPairProduction11setThinningEd3
_ZN7crpropa23EMTripletPairProduction8setLimitEd3
_ZN7crpropa23EMTripletPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZN7crpropa23EMTripletPairProduction16setHaveElectronsEb4
_ZN7crpropa23EMTripletPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa23EMTripletPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa23EMTripletPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html deleted file mode 100644 index bfa5c293f..000000000 --- a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.func.html +++ /dev/null @@ -1,116 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMTripletPairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMTripletPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9410094.0 %
Date:2024-04-08 14:58:22Functions:1111100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa23EMTripletPairProduction11setThinningEd3
_ZN7crpropa23EMTripletPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE15
_ZN7crpropa23EMTripletPairProduction16setHaveElectronsEb4
_ZN7crpropa23EMTripletPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa23EMTripletPairProduction18initCumulativeRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa23EMTripletPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE15
_ZN7crpropa23EMTripletPairProduction8setLimitEd3
_ZN7crpropa23EMTripletPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbdd3
_ZNK7crpropa23EMTripletPairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa23EMTripletPairProduction18performInteractionEPNS_9CandidateE1
_ZNK7crpropa23EMTripletPairProduction7processEPNS_9CandidateE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html b/doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html deleted file mode 100644 index a959e6b81..000000000 --- a/doc/coverageReport/src/module/EMTripletPairProduction.cpp.gcov.html +++ /dev/null @@ -1,263 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/EMTripletPairProduction.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - EMTripletPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9410094.0 %
Date:2024-04-08 14:58:22Functions:1111100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/EMTripletPairProduction.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #include <fstream>
-       6             : #include <limits>
-       7             : #include <stdexcept>
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11             : static const double mec2 = mass_electron * c_squared;
-      12             : 
-      13           3 : EMTripletPairProduction::EMTripletPairProduction(ref_ptr<PhotonField> photonField, bool haveElectrons, double thinning, double limit) {
-      14           3 :         setPhotonField(photonField);
-      15           3 :         setHaveElectrons(haveElectrons);
-      16           3 :         setLimit(limit);
-      17           3 :         setThinning(thinning);
-      18           3 : }
-      19             : 
-      20          15 : void EMTripletPairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
-      21          15 :         this->photonField = photonField;
-      22          15 :         std::string fname = photonField->getFieldName();
-      23          15 :         setDescription("EMTripletPairProduction: " + fname);
-      24          45 :         initRate(getDataPath("EMTripletPairProduction/rate_" + fname + ".txt"));
-      25          45 :         initCumulativeRate(getDataPath("EMTripletPairProduction/cdf_" + fname + ".txt"));
-      26          15 : }
-      27             : 
-      28           4 : void EMTripletPairProduction::setHaveElectrons(bool haveElectrons) {
-      29           4 :         this->haveElectrons = haveElectrons;
-      30           4 : }
-      31             : 
-      32           3 : void EMTripletPairProduction::setLimit(double limit) {
-      33           3 :         this->limit = limit;
-      34           3 : }
-      35             : 
-      36           3 : void EMTripletPairProduction::setThinning(double thinning) {
-      37           3 :         this->thinning = thinning;
-      38           3 : }
-      39             : 
-      40          15 : void EMTripletPairProduction::initRate(std::string filename) {
-      41          15 :         std::ifstream infile(filename.c_str());
-      42             : 
-      43          15 :         if (!infile.good())
-      44           0 :                 throw std::runtime_error("EMTripletPairProduction: could not open file " + filename);
-      45             : 
-      46             :         // clear previously loaded interaction rates
-      47          15 :         tabEnergy.clear();
-      48          15 :         tabRate.clear();
-      49             : 
-      50        3340 :         while (infile.good()) {
-      51        3325 :                 if (infile.peek() != '#') {
-      52             :                         double a, b;
-      53             :                         infile >> a >> b;
-      54        3265 :                         if (infile) {
-      55        3250 :                                 tabEnergy.push_back(pow(10, a) * eV);
-      56        3250 :                                 tabRate.push_back(b / Mpc);
-      57             :                         }
-      58             :                 }
-      59        3325 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      60             :         }
-      61          15 :         infile.close();
-      62          15 : }
-      63             : 
-      64          15 : void EMTripletPairProduction::initCumulativeRate(std::string filename) {
-      65          15 :         std::ifstream infile(filename.c_str());
-      66             : 
-      67          15 :         if (!infile.good())
-      68           0 :                 throw std::runtime_error(
-      69           0 :                                 "EMTripletPairProduction: could not open file " + filename);
-      70             : 
-      71             :         // clear previously loaded tables
-      72          15 :         tabE.clear();
-      73          15 :         tabs.clear();
-      74          15 :         tabCDF.clear();
-      75             :         
-      76             :         // skip header
-      77          75 :         while (infile.peek() == '#')
-      78          60 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      79             : 
-      80             :         // read s values in first line
-      81             :         double a;
-      82             :         infile >> a; // skip first value
-      83        1590 :         while (infile.good() and (infile.peek() != '\n')) {
-      84             :                 infile >> a;
-      85        1575 :                 tabs.push_back(pow(10, a) * eV * eV);
-      86             :         }
-      87             : 
-      88             :         // read all following lines: E, cdf values
-      89        3265 :         while (infile.good()) {
-      90             :                 infile >> a;
-      91        3265 :                 if (!infile)
-      92             :                         break;  // end of file
-      93        3250 :                 tabE.push_back(pow(10, a) * eV);
-      94             :                 std::vector<double> cdf;
-      95      344500 :                 for (int i = 0; i < tabs.size(); i++) {
-      96             :                         infile >> a;
-      97      341250 :                         cdf.push_back(a / Mpc);
-      98             :                 }
-      99        3250 :                 tabCDF.push_back(cdf);
-     100             :         }
-     101          15 :         infile.close();
-     102          15 : }
-     103             : 
-     104           1 : void EMTripletPairProduction::performInteraction(Candidate *candidate) const {
-     105           1 :         int id = candidate->current.getId();
-     106           1 :         if  (abs(id) != 11)
-     107             :                 return;
-     108             : 
-     109             :         // scale the particle energy instead of background photons
-     110           1 :         double z = candidate->getRedshift();
-     111           1 :         double E = candidate->current.getEnergy() * (1 + z);
-     112             : 
-     113           1 :         if (E < tabE.front() or E > tabE.back())
-     114             :                 return;
-     115             : 
-     116             :         // sample the value of eps
-     117           1 :         Random &random = Random::instance();
-     118           1 :         size_t i = closestIndex(E, tabE);
-     119           1 :         size_t j = random.randBin(tabCDF[i]);
-     120           1 :         double s_kin = pow(10, log10(tabs[j]) + (random.rand() - 0.5) * 0.1);
-     121           1 :         double eps = s_kin / 4. / E; // random background photon energy
-     122             : 
-     123             :         // Use approximation from A. Mastichiadis et al., Astroph. Journ. 300:178-189 (1986), eq. 30.
-     124             :         // This approx is valid only for alpha >=100 where alpha = p0*eps*costheta - E0*eps
-     125             :         // For our purposes, me << E0 --> p0~E0 --> alpha = E0*eps*(costheta - 1) >= 100
-     126           1 :         double Epp = 5.7e-1 * pow(eps / mec2, -0.56) * pow(E / mec2, 0.44) * mec2;
-     127             : 
-     128           1 :         double f = Epp / E;
-     129             : 
-     130           1 :         if (haveElectrons) {
-     131           1 :                 Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     132           1 :                 if (random.rand() < pow(1 - f, thinning)) {
-     133           1 :                         double w = 1. / pow(1 - f, thinning);
-     134           1 :                         candidate->addSecondary(11, Epp / (1 + z), pos, w, interactionTag);
-     135             :                 }
-     136           1 :                 if (random.rand() < pow(f, thinning)) {
-     137           1 :                         double w = 1. / pow(f, thinning);
-     138           1 :                         candidate->addSecondary(-11, Epp / (1 + z), pos, w, interactionTag);
-     139             :                 }
-     140             :         }
-     141             :         // Update the primary particle energy.
-     142             :         // This is done after adding the secondaries to correctly set the secondaries parent
-     143           1 :         candidate->current.setEnergy((E - 2 * Epp) / (1. + z));
-     144             : }
-     145             : 
-     146           1 : void EMTripletPairProduction::process(Candidate *candidate) const {
-     147             :         // check if electron / positron
-     148           1 :         int id = candidate->current.getId();
-     149           1 :         if (abs(id) != 11)
-     150             :                 return;
-     151             : 
-     152             :         // scale the particle energy instead of background photons
-     153           1 :         double z = candidate->getRedshift();
-     154           1 :         double E = (1 + z) * candidate->current.getEnergy();
-     155             : 
-     156             :         // check if in tabulated energy range
-     157           1 :         if ((E < tabEnergy.front()) or (E > tabEnergy.back()))
-     158             :                 return;
-     159             : 
-     160             :         // cosmological scaling of interaction distance (comoving)
-     161           1 :         double scaling = pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);
-     162           1 :         double rate = scaling * interpolate(E, tabEnergy, tabRate);
-     163             : 
-     164             :         // run this loop at least once to limit the step size
-     165           1 :         double step = candidate->getCurrentStep();
-     166           1 :         Random &random = Random::instance();
-     167             :         do {
-     168           1 :                 double randDistance = -log(random.rand()) / rate;
-     169             :                 // check for interaction; if it doesn't occur, limit next step
-     170           1 :                 if (step < randDistance) { 
-     171           1 :                         candidate->limitNextStep(limit / rate);
-     172           1 :                         return;
-     173             :                 }
-     174           0 :                 performInteraction(candidate);
-     175           0 :                 step -= randDistance; 
-     176           0 :         } while (step > 0.);
-     177             : }
-     178             : 
-     179           1 : void EMTripletPairProduction::setInteractionTag(std::string tag) {
-     180           1 :         interactionTag = tag;
-     181           1 : }
-     182             : 
-     183           2 : std::string EMTripletPairProduction::getInteractionTag() const {
-     184           2 :         return interactionTag;
-     185             : }
-     186             : 
-     187             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html b/doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html deleted file mode 100644 index 222b6680f..000000000 --- a/doc/coverageReport/src/module/ElasticScattering.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ElasticScattering.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ElasticScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:637090.0 %
Date:2024-04-08 14:58:22Functions:5771.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ElasticScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZNK7crpropa17ElasticScattering17getInteractionTagB5cxx11Ev0
_ZNK7crpropa17ElasticScattering7processEPNS_9CandidateE1
_ZN7crpropa17ElasticScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEE2
_ZN7crpropa17ElasticScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE4
_ZN7crpropa17ElasticScattering7initCDFENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
_ZN7crpropa17ElasticScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ElasticScattering.cpp.func.html b/doc/coverageReport/src/module/ElasticScattering.cpp.func.html deleted file mode 100644 index 8ecf24e21..000000000 --- a/doc/coverageReport/src/module/ElasticScattering.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ElasticScattering.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ElasticScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:637090.0 %
Date:2024-04-08 14:58:22Functions:5771.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ElasticScattering14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE4
_ZN7crpropa17ElasticScattering17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa17ElasticScattering7initCDFENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
_ZN7crpropa17ElasticScattering8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE4
_ZN7crpropa17ElasticScatteringC2ENS_7ref_ptrINS_11PhotonFieldEEE2
_ZNK7crpropa17ElasticScattering17getInteractionTagB5cxx11Ev0
_ZNK7crpropa17ElasticScattering7processEPNS_9CandidateE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html b/doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html deleted file mode 100644 index f5b2d7a8c..000000000 --- a/doc/coverageReport/src/module/ElasticScattering.cpp.gcov.html +++ /dev/null @@ -1,212 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ElasticScattering.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ElasticScattering.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:637090.0 %
Date:2024-04-08 14:58:22Functions:5771.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/ElasticScattering.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/ParticleMass.h"
-       5             : #include "crpropa/Random.h"
-       6             : 
-       7             : #include <cmath>
-       8             : #include <limits>
-       9             : #include <sstream>
-      10             : #include <fstream>
-      11             : #include <stdexcept>
-      12             : 
-      13             : namespace crpropa {
-      14             : 
-      15             : const double ElasticScattering::lgmin = 6.;  // minimum log10(Lorentz-factor)
-      16             : const double ElasticScattering::lgmax = 14.; // maximum log10(Lorentz-factor)
-      17             : const size_t ElasticScattering::nlg = 201;   // number of Lorentz-factor steps
-      18             : const double ElasticScattering::epsmin = log10(2 * eV) + 3;    // log10 minimum photon background energy in nucleus rest frame for elastic scattering
-      19             : const double ElasticScattering::epsmax = log10(2 * eV) + 8.12; // log10 maximum photon background energy in nucleus rest frame for elastic scattering
-      20             : const size_t ElasticScattering::neps = 513; // number of photon background energies in nucleus rest frame
-      21             : 
-      22           2 : ElasticScattering::ElasticScattering(ref_ptr<PhotonField> f) {
-      23           2 :         setPhotonField(f);
-      24           2 : }
-      25             : 
-      26           4 : void ElasticScattering::setPhotonField(ref_ptr<PhotonField> photonField) {
-      27           4 :         this->photonField = photonField;
-      28           4 :         std::string fname = photonField->getFieldName();
-      29           4 :         setDescription("ElasticScattering: " + fname);
-      30          12 :         initRate(getDataPath("ElasticScattering/rate_" + fname.substr(0,3) + ".txt"));
-      31          12 :         initCDF(getDataPath("ElasticScattering/cdf_" + fname.substr(0,3) + ".txt"));
-      32           4 : }
-      33             : 
-      34           4 : void ElasticScattering::initRate(std::string filename) {
-      35           4 :         std::ifstream infile(filename.c_str());
-      36           4 :         if (not infile.good())
-      37           0 :                 throw std::runtime_error("ElasticScattering: could not open file " + filename);
-      38             : 
-      39           4 :         tabRate.clear();
-      40             : 
-      41         824 :         while (infile.good()) {
-      42         824 :                 if (infile.peek() == '#') {
-      43          16 :                         infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-      44          16 :                         continue;
-      45             :                 }
-      46             :                 double r;
-      47             :                 infile >> r;
-      48         808 :                 if (!infile)
-      49             :                         break;
-      50         804 :                 tabRate.push_back(r / Mpc);
-      51             :         }
-      52             : 
-      53           4 :         infile.close();
-      54           4 : }
-      55             : 
-      56           4 : void ElasticScattering::initCDF(std::string filename) {
-      57           4 :         std::ifstream infile(filename.c_str());
-      58           4 :         if (not infile.good())
-      59           0 :                 throw std::runtime_error("ElasticScattering: could not open file " + filename);
-      60             : 
-      61           4 :         tabCDF.clear();
-      62             :         std::string line;
-      63             :         double a;
-      64         820 :         while (std::getline(infile, line)) {
-      65         816 :                 if (line[0] == '#')
-      66          12 :                         continue;
-      67             : 
-      68         804 :                 std::stringstream lineStream(line);
-      69             :                 lineStream >> a;
-      70             : 
-      71         804 :                 std::vector<double> cdf(neps);
-      72      413256 :                 for (size_t i = 0; i < neps; i++) {
-      73             :                         lineStream >> a;
-      74      412452 :                         cdf[i] = a;
-      75             :                 }
-      76         804 :                 tabCDF.push_back(cdf);
-      77         804 :         }
-      78             : 
-      79           4 :         infile.close();
-      80           4 : }
-      81             : 
-      82           1 : void ElasticScattering::process(Candidate *candidate) const {
-      83           1 :         int id = candidate->current.getId();
-      84           1 :         double z = candidate->getRedshift();
-      85             : 
-      86           1 :         if (not isNucleus(id))
-      87             :                 return;
-      88             : 
-      89           1 :         double lg = log10(candidate->current.getLorentzFactor() * (1 + z));
-      90           1 :         if ((lg < lgmin) or (lg > lgmax))
-      91             :                 return;
-      92             : 
-      93           1 :         int A = massNumber(id);
-      94           1 :         int Z = chargeNumber(id);
-      95           1 :         int N = A - Z;
-      96             : 
-      97           1 :         double step = candidate->getCurrentStep();
-      98           8 :         while (step > 0) {
-      99             : 
-     100           8 :                 double rate = interpolateEquidistant(lg, lgmin, lgmax, tabRate);
-     101           8 :                 rate *= Z * N / double(A);  // TRK scaling
-     102           8 :                 rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z);  // cosmological scaling
-     103             : 
-     104             :                 // check for interaction
-     105           8 :                 Random &random = Random::instance();
-     106           8 :                 double randDist = -log(random.rand()) / rate;
-     107           8 :                 if (step < randDist)
-     108           1 :                         return;
-     109             : 
-     110             :                 // draw random background photon energy from CDF
-     111           7 :                 size_t i = floor((lg - lgmin) / (lgmax - lgmin) * (nlg - 1)); // index of closest gamma tabulation point
-     112           7 :                 size_t j = random.randBin(tabCDF[i]) - 1; // index of next lower tabulated eps value
-     113             :                 double binWidth = (epsmax - epsmin) / (neps - 1); // logarithmic bin width
-     114           7 :                 double eps = pow(10, epsmin + (j + random.rand()) * binWidth);
-     115             : 
-     116             :                 // boost to lab frame
-     117           7 :                 double cosTheta = 2 * random.rand() - 1;
-     118           7 :                 double E = eps * candidate->current.getLorentzFactor() * (1. - cosTheta);
-     119             : 
-     120           7 :                 Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     121           7 :                 candidate->addSecondary(22, E, pos, 1., interactionTag);
-     122             : 
-     123             :                 // repeat with remaining step
-     124           7 :                 step -= randDist;
-     125             :         }
-     126             : }
-     127             : 
-     128           0 : void ElasticScattering::setInteractionTag(std::string tag) {
-     129           0 :         this -> interactionTag = tag;
-     130           0 : }
-     131             : 
-     132           0 : std::string ElasticScattering::getInteractionTag() const {
-     133           0 :         return interactionTag;
-     134             : }
-     135             : 
-     136             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html deleted file mode 100644 index 03ac203cf..000000000 --- a/doc/coverageReport/src/module/ElectronPairProduction.cpp.func-sort-c.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ElectronPairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ElectronPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859292.4 %
Date:2024-04-08 14:58:22Functions:91090.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ElectronPairProduction8setLimitEd0
_ZN7crpropa22ElectronPairProduction12initSpectrumENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22ElectronPairProduction16setHaveElectronsEb1
_ZN7crpropa22ElectronPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa22ElectronPairProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa22ElectronPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbd10
_ZN7crpropa22ElectronPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE19
_ZN7crpropa22ElectronPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE19
_ZNK7crpropa22ElectronPairProduction10lossLengthEidd15446
_ZNK7crpropa22ElectronPairProduction7processEPNS_9CandidateE15447
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html b/doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html deleted file mode 100644 index 5da0c6c27..000000000 --- a/doc/coverageReport/src/module/ElectronPairProduction.cpp.func.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ElectronPairProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ElectronPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859292.4 %
Date:2024-04-08 14:58:22Functions:91090.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa22ElectronPairProduction12initSpectrumENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22ElectronPairProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE19
_ZN7crpropa22ElectronPairProduction16setHaveElectronsEb1
_ZN7crpropa22ElectronPairProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa22ElectronPairProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE19
_ZN7crpropa22ElectronPairProduction8setLimitEd0
_ZN7crpropa22ElectronPairProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbd10
_ZNK7crpropa22ElectronPairProduction10lossLengthEidd15446
_ZNK7crpropa22ElectronPairProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa22ElectronPairProduction7processEPNS_9CandidateE15447
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html b/doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html deleted file mode 100644 index 5204a21c0..000000000 --- a/doc/coverageReport/src/module/ElectronPairProduction.cpp.gcov.html +++ /dev/null @@ -1,233 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ElectronPairProduction.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ElectronPairProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859292.4 %
Date:2024-04-08 14:58:22Functions:91090.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/ElectronPairProduction.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/ParticleMass.h"
-       5             : #include "crpropa/Random.h"
-       6             : 
-       7             : #include <fstream>
-       8             : #include <limits>
-       9             : #include <stdexcept>
-      10             : 
-      11             : namespace crpropa {
-      12             : 
-      13          10 : ElectronPairProduction::ElectronPairProduction(ref_ptr<PhotonField> photonField,
-      14          10 :                 bool haveElectrons, double limit) {
-      15          10 :         this->haveElectrons = haveElectrons;
-      16          10 :         this->limit = limit;
-      17          10 :         setPhotonField(photonField);
-      18          10 : }
-      19             : 
-      20          19 : void ElectronPairProduction::setPhotonField(ref_ptr<PhotonField> photonField) {
-      21          19 :         this->photonField = photonField;
-      22          19 :         std::string fname = photonField->getFieldName();
-      23          19 :         setDescription("ElectronPairProduction: " + fname);
-      24          57 :         initRate(getDataPath("ElectronPairProduction/lossrate_" + fname + ".txt"));
-      25          19 :         if (haveElectrons) { // Load secondary spectra only if electrons should be produced
-      26           0 :                 initSpectrum(getDataPath("ElectronPairProduction/spectrum_" + fname.substr(0,3) + ".txt"));
-      27             :         }
-      28          19 : }
-      29             : 
-      30           1 : void ElectronPairProduction::setHaveElectrons(bool haveElectrons) {
-      31           1 :         this->haveElectrons = haveElectrons;
-      32           1 :         if (haveElectrons) { // Load secondary spectra in case haveElectrons was changed to true
-      33           1 :                 std::string fname = photonField->getFieldName();
-      34           3 :                 initSpectrum(getDataPath("ElectronPairProduction/spectrum_" + fname.substr(0,3) + ".txt"));
-      35             :         }
-      36           1 : }
-      37             : 
-      38           0 : void ElectronPairProduction::setLimit(double limit) {
-      39           0 :         this->limit = limit;
-      40           0 : }
-      41             : 
-      42          19 : void ElectronPairProduction::initRate(std::string filename) {
-      43          19 :         std::ifstream infile(filename.c_str());
-      44             : 
-      45          19 :         if (!infile.good())
-      46           0 :                 throw std::runtime_error("ElectronPairProduction: could not open file " + filename);
-      47             : 
-      48             :         // clear previously loaded interaction rates
-      49          19 :         tabLorentzFactor.clear();
-      50          19 :         tabLossRate.clear();
-      51             : 
-      52        2853 :         while (infile.good()) {
-      53        2834 :                 if (infile.peek() != '#') {
-      54             :                         double a, b;
-      55             :                         infile >> a >> b;
-      56        2777 :                         if (infile) {
-      57        2758 :                                 tabLorentzFactor.push_back(pow(10, a));
-      58        2758 :                                 tabLossRate.push_back(b / Mpc);
-      59             :                         }
-      60             :                 }
-      61        2834 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-      62             :         }
-      63          19 :         infile.close();
-      64          19 : }
-      65             : 
-      66           1 : void ElectronPairProduction::initSpectrum(std::string filename) {
-      67           1 :         std::ifstream infile(filename.c_str());
-      68           1 :         if (!infile.good())
-      69           0 :                 throw std::runtime_error("ElectronPairProduction: could not open file " + filename);
-      70             : 
-      71             :         double dNdE;
-      72           1 :         tabSpectrum.resize(70);
-      73          71 :         for (size_t i = 0; i < 70; i++) {
-      74          70 :                 tabSpectrum[i].resize(170);
-      75       11970 :                 for (size_t j = 0; j < 170; j++) {
-      76             :                         infile >> dNdE;
-      77       11900 :                         tabSpectrum[i][j] = dNdE * pow(10, (7 + 0.1 * j)); // read electron distribution pdf(Ee) ~ dN/dEe * Ee
-      78             :                 }
-      79       11900 :                 for (size_t j = 1; j < 170; j++) {
-      80       11830 :                         tabSpectrum[i][j] += tabSpectrum[i][j - 1]; // cdf(Ee), unnormalized
-      81             :                 }
-      82             :         }
-      83           1 :         infile.close();
-      84           1 : }
-      85             : 
-      86       15446 : double ElectronPairProduction::lossLength(int id, double lf, double z) const {
-      87       15446 :         double Z = chargeNumber(id);
-      88       15446 :         if (Z == 0)
-      89             :                 return std::numeric_limits<double>::max(); // no pair production on uncharged particles
-      90             : 
-      91       14944 :         lf *= (1 + z);
-      92       14944 :         if (lf < tabLorentzFactor.front())
-      93             :                 return std::numeric_limits<double>::max(); // below energy threshold
-      94             : 
-      95             :         double rate;
-      96       14921 :         if (lf < tabLorentzFactor.back())
-      97       14921 :                 rate = interpolate(lf, tabLorentzFactor, tabLossRate); // interpolation
-      98             :         else
-      99           0 :                 rate = tabLossRate.back() * pow(lf / tabLorentzFactor.back(), -0.6); // extrapolation
-     100             : 
-     101       14921 :         double A = nuclearMass(id) / mass_proton; // more accurate than massNumber(Id)
-     102       14921 :         rate *= Z * Z / A * pow_integer<3>(1 + z) * photonField->getRedshiftScaling(z);
-     103       14921 :         return 1. / rate;
-     104             : }
-     105             : 
-     106       15447 : void ElectronPairProduction::process(Candidate *c) const {
-     107       15447 :         int id = c->current.getId();
-     108       15447 :         if (not (isNucleus(id)))
-     109             :                 return; // only nuclei
-     110             : 
-     111       15446 :         double lf = c->current.getLorentzFactor();
-     112       15446 :         double z = c->getRedshift();
-     113       15446 :         double losslen = lossLength(id, lf, z);  // energy loss length
-     114       15446 :         if (losslen >= std::numeric_limits<double>::max())
-     115             :                 return;
-     116             : 
-     117       14921 :         double step = c->getCurrentStep() / (1 + z); // step size in local frame
-     118       14921 :         double loss = step / losslen;  // relative energy loss
-     119             : 
-     120       14921 :         if (haveElectrons) {
-     121           1 :                 double dE = c->current.getEnergy() * loss;  // energy loss
-     122           1 :                 int i = round((log10(lf) - 6.05) * 10);  // find closest cdf(Ee|log10(gamma))
-     123           1 :                 i = std::min(std::max(i, 0), 69);
-     124           1 :                 Random &random = Random::instance();
-     125             : 
-     126             :                 // draw pairs as long as their energy is smaller than the pair production energy loss
-     127        6534 :                 while (dE > 0) {
-     128        6534 :                         size_t j = random.randBin(tabSpectrum[i]);
-     129        6534 :                         double Ee = pow(10, 6.95 + (j + random.rand()) * 0.1) * eV;
-     130        6534 :                         double Epair = 2 * Ee; // NOTE: electron and positron in general don't have same lab frame energy, but averaged over many draws the result is consistent
-     131             :                         // if the remaining energy is not sufficient check for random accepting
-     132        6534 :                         if (Epair > dE)
-     133           1 :                                 if (random.rand() > (dE / Epair))
-     134             :                                         break; // not accepted
-     135             : 
-     136             :                         // create pair and repeat with remaining energy
-     137        6533 :                         dE -= Epair;
-     138        6533 :                         Vector3d pos = random.randomInterpolatedPosition(c->previous.getPosition(), c->current.getPosition());
-     139        6533 :                         c->addSecondary( 11, Ee, pos, 1., interactionTag);
-     140        6533 :                         c->addSecondary(-11, Ee, pos, 1., interactionTag);
-     141             :                 }
-     142             :         }
-     143             : 
-     144       14921 :         c->current.setLorentzFactor(lf * (1 - loss));
-     145       14921 :         c->limitNextStep(limit * losslen);
-     146             : }
-     147             : 
-     148           1 : void ElectronPairProduction::setInteractionTag(std::string tag) {
-     149           1 :         interactionTag = tag;
-     150           1 : }
-     151             : 
-     152           2 : std::string ElectronPairProduction::getInteractionTag() const {
-     153           2 :         return interactionTag;
-     154             : }
-     155             : 
-     156             : 
-     157             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html b/doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html deleted file mode 100644 index 7c1102518..000000000 --- a/doc/coverageReport/src/module/HDF5Output.cpp.func-sort-c.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/HDF5Output.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - HDF5Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:122415.0 %
Date:2024-04-08 14:58:22Functions:41428.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10HDF5Output13setFlushLimitEj0
_ZN7crpropa10HDF5Output21insertDoubleAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKd0
_ZN7crpropa10HDF5Output21insertStringAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES8_0
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE0
_ZN7crpropa10HDF5OutputD0Ev0
_ZN7crpropa23variantTypeToH5T_NATIVEENS_7Variant4TypeE0
_ZNK7crpropa10HDF5Output14getDescriptionB5cxx11Ev0
_ZNK7crpropa10HDF5Output5flushEv0
_ZNK7crpropa10HDF5Output7processEPNS_9CandidateE0
_ZN7crpropa10HDF5Output4openERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa10HDF5Output5closeEv1
_ZN7crpropa10HDF5OutputC2Ev1
_ZN7crpropa10HDF5OutputD2Ev1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/HDF5Output.cpp.func.html b/doc/coverageReport/src/module/HDF5Output.cpp.func.html deleted file mode 100644 index 23798cfed..000000000 --- a/doc/coverageReport/src/module/HDF5Output.cpp.func.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/HDF5Output.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - HDF5Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:122415.0 %
Date:2024-04-08 14:58:22Functions:41428.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10HDF5Output13setFlushLimitEj0
_ZN7crpropa10HDF5Output21insertDoubleAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKd0
_ZN7crpropa10HDF5Output21insertStringAttributeERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES8_0
_ZN7crpropa10HDF5Output4openERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa10HDF5Output5closeEv1
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa10HDF5OutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE0
_ZN7crpropa10HDF5OutputC2Ev1
_ZN7crpropa10HDF5OutputD0Ev0
_ZN7crpropa10HDF5OutputD2Ev1
_ZN7crpropa23variantTypeToH5T_NATIVEENS_7Variant4TypeE0
_ZNK7crpropa10HDF5Output14getDescriptionB5cxx11Ev0
_ZNK7crpropa10HDF5Output5flushEv0
_ZNK7crpropa10HDF5Output7processEPNS_9CandidateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/HDF5Output.cpp.gcov.html b/doc/coverageReport/src/module/HDF5Output.cpp.gcov.html deleted file mode 100644 index 653ba85ea..000000000 --- a/doc/coverageReport/src/module/HDF5Output.cpp.gcov.html +++ /dev/null @@ -1,468 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/HDF5Output.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - HDF5Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:122415.0 %
Date:2024-04-08 14:58:22Functions:41428.6 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #ifdef CRPROPA_HAVE_HDF5
-       2             : 
-       3             : #include "crpropa/module/HDF5Output.h"
-       4             : #include "crpropa/Version.h"
-       5             : #include "crpropa/Random.h"
-       6             : #include "kiss/logger.h"
-       7             : 
-       8             : #include <hdf5.h>
-       9             : #include <cstring>
-      10             : 
-      11             : const hsize_t RANK = 1;
-      12             : const hsize_t BUFFER_SIZE = 1024 * 16;
-      13             : 
-      14             : namespace crpropa {
-      15             : 
-      16             : // map variant types to H5T_NATIVE
-      17           0 : hid_t variantTypeToH5T_NATIVE(Variant::Type type) {
-      18             :         if (type == Variant::TYPE_INT64)
-      19           0 :                 return H5T_NATIVE_INT64;
-      20             :         else if(type == Variant::TYPE_BOOL)
-      21           0 :                 return H5T_NATIVE_HBOOL;
-      22             :         else if(type == Variant::TYPE_CHAR)
-      23           0 :                 return H5T_NATIVE_CHAR;
-      24             :         else if(type == Variant::TYPE_UCHAR)
-      25           0 :                 return H5T_NATIVE_UCHAR;
-      26             :         else if(type == Variant::TYPE_INT16)
-      27           0 :                 return H5T_NATIVE_INT16;
-      28             :         else if(type == Variant::TYPE_UINT16)
-      29           0 :                 return H5T_NATIVE_UINT16;
-      30             :         else if(type == Variant::TYPE_INT32)
-      31           0 :                 return H5T_NATIVE_INT32;
-      32             :         else if(type == Variant::TYPE_UINT32)
-      33           0 :                 return H5T_NATIVE_UINT32;
-      34             :         else if(type == Variant::TYPE_INT64)
-      35             :                 return H5T_NATIVE_INT64;
-      36             :         else if(type == Variant::TYPE_UINT64)
-      37           0 :                 return H5T_NATIVE_UINT64;
-      38             :         else if(type == Variant::TYPE_FLOAT)
-      39           0 :                 return H5T_NATIVE_FLOAT;
-      40             :         else if(type == Variant::TYPE_DOUBLE)
-      41           0 :                 return H5T_NATIVE_DOUBLE;
-      42             :         else if(type == Variant::TYPE_STRING)
-      43           0 :                 return H5T_C_S1;
-      44             :         else
-      45             :         {
-      46           0 :                 KISS_LOG_ERROR << "variantTypeToH5T_NATIVE:: Type: " << Variant::getTypeName(type) << " unknown.";
-      47           0 :                 throw std::runtime_error("No matching HDF type for Variant type");
-      48             :         }
-      49             : }
-      50             : 
-      51           1 : HDF5Output::HDF5Output() :  Output(), filename(), file(-1), sid(-1), dset(-1), dataspace(-1), candidatesSinceFlush(0), flushLimit(std::numeric_limits<unsigned int>::max()) {
-      52           1 : }
-      53             : 
-      54           0 : HDF5Output::HDF5Output(const std::string& filename) :  Output(), filename(filename), file(-1), sid(-1), dset(-1), dataspace(-1), candidatesSinceFlush(0), flushLimit(std::numeric_limits<unsigned int>::max()) {
-      55           0 : }
-      56             : 
-      57           0 : HDF5Output::HDF5Output(const std::string& filename, OutputType outputtype) :  Output(outputtype), filename(filename), file(-1), sid(-1), dset(-1), dataspace(-1), candidatesSinceFlush(0), flushLimit(std::numeric_limits<unsigned int>::max()) {
-      58             :         outputtype = outputtype;
-      59           0 : }
-      60             : 
-      61           1 : HDF5Output::~HDF5Output() {
-      62           1 :         close();
-      63           2 : }
-      64             : 
-      65           0 : herr_t HDF5Output::insertStringAttribute(const std::string &key, const std::string &value){
-      66             :         hid_t   strtype, attr_space, version_attr;
-      67           0 :         hsize_t dims = 0;
-      68             :         herr_t  status;
-      69             : 
-      70           0 :         strtype = H5Tcopy(H5T_C_S1);
-      71           0 :         status = H5Tset_size(strtype, value.size());
-      72             : 
-      73           0 :         attr_space = H5Screate_simple(0, &dims, NULL);
-      74           0 :         version_attr = H5Acreate2(dset, key.c_str(), strtype, attr_space, H5P_DEFAULT, H5P_DEFAULT);
-      75           0 :         status = H5Awrite(version_attr, strtype, value.c_str());
-      76           0 :         status = H5Aclose(version_attr);
-      77           0 :         status = H5Sclose(attr_space);
-      78             : 
-      79           0 :         return status;
-      80             : }
-      81             : 
-      82           0 : herr_t HDF5Output::insertDoubleAttribute(const std::string &key, const double &value){
-      83             :         hid_t   type, attr_space, version_attr;
-      84           0 :         hsize_t dims = 0;
-      85             :         herr_t  status;
-      86             : 
-      87           0 :         type = H5Tcopy(H5T_NATIVE_DOUBLE);
-      88             : 
-      89           0 :         attr_space = H5Screate_simple(0, &dims, NULL);
-      90           0 :         version_attr = H5Acreate2(dset, key.c_str(), type, attr_space, H5P_DEFAULT, H5P_DEFAULT);
-      91           0 :         status = H5Awrite(version_attr, type, &value);
-      92           0 :         status = H5Aclose(version_attr);
-      93           0 :         status = H5Sclose(attr_space);
-      94             : 
-      95           0 :         return status;
-      96             : }
-      97             : 
-      98             : 
-      99             : 
-     100           1 : void HDF5Output::open(const std::string& filename) {
-     101           1 :         file = H5Fcreate(filename.c_str(), H5F_ACC_TRUNC, H5P_DEFAULT, H5P_DEFAULT);
-     102           1 :         if (file < 0)
-     103           2 :                 throw std::runtime_error(std::string("Cannot create file: ") + filename);
-     104             : 
-     105             : 
-     106           0 :         sid = H5Tcreate(H5T_COMPOUND, sizeof(OutputRow));
-     107           0 :         if (fields.test(TrajectoryLengthColumn))
-     108           0 :                 H5Tinsert(sid, "D", HOFFSET(OutputRow, D), H5T_NATIVE_DOUBLE);
-     109           0 :         if (fields.test(RedshiftColumn))
-     110           0 :                 H5Tinsert(sid, "z", HOFFSET(OutputRow, z), H5T_NATIVE_DOUBLE);
-     111           0 :         if (fields.test(SerialNumberColumn))
-     112           0 :                 H5Tinsert(sid, "SN", HOFFSET(OutputRow, SN), H5T_NATIVE_UINT64);
-     113           0 :         if (fields.test(CurrentIdColumn))
-     114           0 :                 H5Tinsert(sid, "ID", HOFFSET(OutputRow, ID), H5T_NATIVE_INT32);
-     115           0 :         if (fields.test(CurrentEnergyColumn))
-     116           0 :                 H5Tinsert(sid, "E", HOFFSET(OutputRow, E), H5T_NATIVE_DOUBLE);
-     117           0 :         if (fields.test(CurrentPositionColumn) && oneDimensional)
-     118           0 :                 H5Tinsert(sid, "X", HOFFSET(OutputRow, X), H5T_NATIVE_DOUBLE);
-     119           0 :         if (fields.test(CurrentPositionColumn) && not oneDimensional) {
-     120           0 :                 H5Tinsert(sid, "X", HOFFSET(OutputRow, X), H5T_NATIVE_DOUBLE);
-     121           0 :                 H5Tinsert(sid, "Y", HOFFSET(OutputRow, Y), H5T_NATIVE_DOUBLE);
-     122           0 :                 H5Tinsert(sid, "Z", HOFFSET(OutputRow, Z), H5T_NATIVE_DOUBLE);
-     123             :         }
-     124           0 :         if (fields.test(CurrentDirectionColumn) && not oneDimensional) {
-     125           0 :                 H5Tinsert(sid, "Px", HOFFSET(OutputRow, Px), H5T_NATIVE_DOUBLE);
-     126           0 :                 H5Tinsert(sid, "Py", HOFFSET(OutputRow, Py), H5T_NATIVE_DOUBLE);
-     127           0 :                 H5Tinsert(sid, "Pz", HOFFSET(OutputRow, Pz), H5T_NATIVE_DOUBLE);
-     128             :         }
-     129           0 :         if (fields.test(SerialNumberColumn))
-     130           0 :                 H5Tinsert(sid, "SN0", HOFFSET(OutputRow, SN0), H5T_NATIVE_UINT64);
-     131           0 :         if (fields.test(SourceIdColumn))
-     132           0 :                 H5Tinsert(sid, "ID0", HOFFSET(OutputRow, ID0), H5T_NATIVE_INT32);
-     133           0 :         if (fields.test(SourceEnergyColumn))
-     134           0 :                 H5Tinsert(sid, "E0", HOFFSET(OutputRow, E0), H5T_NATIVE_DOUBLE);
-     135           0 :         if (fields.test(SourcePositionColumn) && oneDimensional)
-     136           0 :                 H5Tinsert(sid, "X0", HOFFSET(OutputRow, X0), H5T_NATIVE_DOUBLE);
-     137           0 :         if (fields.test(SourcePositionColumn) && not oneDimensional){
-     138           0 :                 H5Tinsert(sid, "X0", HOFFSET(OutputRow, X0), H5T_NATIVE_DOUBLE);
-     139           0 :                 H5Tinsert(sid, "Y0", HOFFSET(OutputRow, Y0), H5T_NATIVE_DOUBLE);
-     140           0 :                 H5Tinsert(sid, "Z0", HOFFSET(OutputRow, Z0), H5T_NATIVE_DOUBLE);
-     141             :         }
-     142           0 :         if (fields.test(SourceDirectionColumn) && not oneDimensional) {
-     143           0 :                 H5Tinsert(sid, "P0x", HOFFSET(OutputRow, P0x), H5T_NATIVE_DOUBLE);
-     144           0 :                 H5Tinsert(sid, "P0y", HOFFSET(OutputRow, P0y), H5T_NATIVE_DOUBLE);
-     145           0 :                 H5Tinsert(sid, "P0z", HOFFSET(OutputRow, P0z), H5T_NATIVE_DOUBLE);
-     146             :         }
-     147           0 :         if (fields.test(SerialNumberColumn))
-     148           0 :                 H5Tinsert(sid, "SN1", HOFFSET(OutputRow, SN1), H5T_NATIVE_UINT64);
-     149           0 :         if (fields.test(CreatedIdColumn))
-     150           0 :                 H5Tinsert(sid, "ID1", HOFFSET(OutputRow, ID1), H5T_NATIVE_INT32);
-     151           0 :         if (fields.test(CreatedEnergyColumn))
-     152           0 :                 H5Tinsert(sid, "E1", HOFFSET(OutputRow, E1), H5T_NATIVE_DOUBLE);
-     153           0 :         if (fields.test(CreatedPositionColumn) && oneDimensional)
-     154           0 :                 H5Tinsert(sid, "X1", HOFFSET(OutputRow, X1), H5T_NATIVE_DOUBLE);
-     155           0 :         if (fields.test(CreatedPositionColumn) && not oneDimensional) {
-     156           0 :                 H5Tinsert(sid, "X1", HOFFSET(OutputRow, X1), H5T_NATIVE_DOUBLE);
-     157           0 :                 H5Tinsert(sid, "Y1", HOFFSET(OutputRow, Y1), H5T_NATIVE_DOUBLE);
-     158           0 :                 H5Tinsert(sid, "Z1", HOFFSET(OutputRow, Z1), H5T_NATIVE_DOUBLE);
-     159             :         }
-     160           0 :         if (fields.test(CreatedDirectionColumn) && not oneDimensional) {
-     161           0 :                 H5Tinsert(sid, "P1x", HOFFSET(OutputRow, P1x), H5T_NATIVE_DOUBLE);
-     162           0 :                 H5Tinsert(sid, "P1y", HOFFSET(OutputRow, P1y), H5T_NATIVE_DOUBLE);
-     163           0 :                 H5Tinsert(sid, "P1z", HOFFSET(OutputRow, P1z), H5T_NATIVE_DOUBLE);
-     164             :         }
-     165           0 :         if (fields.test(WeightColumn))
-     166           0 :                 H5Tinsert(sid, "W", HOFFSET(OutputRow, weight), H5T_NATIVE_DOUBLE);
-     167             :         
-     168           0 :         if (fields.test(CandidateTagColumn)) 
-     169           0 :                 H5Tinsert(sid, "tag", HOFFSET(OutputRow, tag), H5T_C_S1);
-     170             : 
-     171           0 :         size_t pos = 0;
-     172           0 :         for(std::vector<Output::Property>::const_iterator iter = properties.begin();
-     173           0 :                         iter != properties.end(); ++iter)
-     174             :         {
-     175           0 :                         hid_t type = variantTypeToH5T_NATIVE((*iter).defaultValue.getType());
-     176           0 :                         if (type == H5T_C_S1)
-     177             :                         { // set size of string field to size of default value!
-     178           0 :                                 type = H5Tcopy(H5T_C_S1);
-     179           0 :                                 H5Tset_size(type, (*iter).defaultValue.toString().size());
-     180             :                         }
-     181             : 
-     182           0 :                         H5Tinsert(sid, (*iter).name.c_str(), HOFFSET(OutputRow, propertyBuffer) + pos, type);
-     183           0 :                   pos += (*iter).defaultValue.getSize();
-     184             :         }
-     185           0 :         if (pos >= propertyBufferSize)
-     186             :         {
-     187           0 :                 KISS_LOG_ERROR << "Using " << pos << " bytes for properties output. Maximum is " << propertyBufferSize << " bytes.";
-     188           0 :                 throw std::runtime_error("Size of property buffer exceeded");
-     189             :         }
-     190             : 
-     191             :         // chunked prop
-     192           0 :         hid_t plist = H5Pcreate(H5P_DATASET_CREATE);
-     193           0 :         H5Pset_layout(plist, H5D_CHUNKED);
-     194           0 :         hsize_t chunk_dims[RANK] = {BUFFER_SIZE};
-     195           0 :         H5Pset_chunk(plist, RANK, chunk_dims);
-     196           0 :         H5Pset_deflate(plist, 5);
-     197             : 
-     198           0 :         hsize_t dims[RANK] = {0};
-     199           0 :         hsize_t max_dims[RANK] = {H5S_UNLIMITED};
-     200           0 :         dataspace = H5Screate_simple(RANK, dims, max_dims);
-     201             : 
-     202           0 :         dset = H5Dcreate2(file, "CRPROPA3", sid, dataspace, H5P_DEFAULT, plist, H5P_DEFAULT);
-     203             : 
-     204           0 :         insertStringAttribute("OutputType", outputName);
-     205           0 :         insertStringAttribute("Version", g_GIT_DESC);
-     206           0 :         insertDoubleAttribute("LengthScale", this->lengthScale);
-     207           0 :         insertDoubleAttribute("EnergyScale", this->energyScale);
-     208             : 
-     209             :         // add ranom seeds
-     210           0 :         std::vector< std::vector<uint32_t> > seeds = Random::getSeedThreads();
-     211           0 :         for (size_t i = 0; i < seeds.size(); i++)
-     212             :         {
-     213             :                 hid_t   type, attr_space, version_attr;
-     214             :                 herr_t  status;
-     215           0 :                 hsize_t dims[] = {1, 0};
-     216           0 :                 dims[1] = seeds[i].size();
-     217             : 
-     218           0 :                 type = H5Tarray_create(H5T_NATIVE_ULONG, 2, dims);
-     219             : 
-     220           0 :                 attr_space = H5Screate_simple(0, dims, NULL);
-     221             :                 char nameBuffer[256];
-     222             :                 sprintf(nameBuffer, "SEED_%03lu", i);
-     223           0 :                 KISS_LOG_DEBUG << "Creating HDF5 attribute: " << nameBuffer << " with dimensions " << dims[0] << "x" << dims[1] ;
-     224             : 
-     225           0 :                 version_attr = H5Acreate2(dset, nameBuffer, type, attr_space, H5P_DEFAULT, H5P_DEFAULT);
-     226           0 :                 status = H5Awrite(version_attr, type, &seeds[i][0]);
-     227           0 :                 status = H5Aclose(version_attr);
-     228           0 :                 status = H5Sclose(attr_space);
-     229             : 
-     230             :         }
-     231             : 
-     232             : 
-     233           0 :         H5Pclose(plist);
-     234             : 
-     235           0 :         buffer.reserve(BUFFER_SIZE);
-     236           0 :         time(&lastFlush);
-     237           0 : }
-     238             : 
-     239           1 : void HDF5Output::close() {
-     240           1 :         if (file >= 0) {
-     241           0 :                 flush();
-     242           0 :                 H5Dclose(dset);
-     243           0 :                 H5Tclose(sid);
-     244           0 :                 H5Sclose(dataspace);
-     245           0 :                 H5Fclose(file);
-     246           0 :                 file = -1;
-     247             :         }
-     248           1 : }
-     249             : 
-     250           0 : void HDF5Output::process(Candidate* candidate) const {
-     251           0 :         #pragma omp critical
-     252             :         {
-     253           0 :         if (file == -1)
-     254             :                 // This is ugly, but necesary as otherwise the user has to manually open the
-     255             :                 // file before processing the first candidate
-     256           0 :                 const_cast<HDF5Output*>(this)->open(filename);
-     257             :         }
-     258             : 
-     259             :         OutputRow r;
-     260           0 :         r.D = candidate->getTrajectoryLength() / lengthScale;
-     261           0 :         r.z = candidate->getRedshift();
-     262             : 
-     263           0 :         r.SN = candidate->getSerialNumber();
-     264           0 :         r.ID = candidate->current.getId();
-     265           0 :         r.E = candidate->current.getEnergy() / energyScale;
-     266           0 :         Vector3d v = candidate->current.getPosition() / lengthScale;
-     267           0 :         r.X = v.x;
-     268           0 :         r.Y = v.y;
-     269           0 :         r.Z = v.z;
-     270           0 :         v = candidate->current.getDirection();
-     271           0 :         r.Px = v.x;
-     272           0 :         r.Py = v.y;
-     273           0 :         r.Pz = v.z;
-     274             : 
-     275           0 :         r.SN0 = candidate->getSourceSerialNumber();
-     276           0 :         r.ID0 = candidate->source.getId();
-     277           0 :         r.E0 = candidate->source.getEnergy() / energyScale;
-     278           0 :         v = candidate->source.getPosition() / lengthScale;
-     279           0 :         r.X0 = v.x;
-     280           0 :         r.Y0 = v.y;
-     281           0 :         r.Z0 = v.z;
-     282           0 :         v = candidate->source.getDirection();
-     283           0 :         r.P0x = v.x;
-     284           0 :         r.P0y = v.y;
-     285           0 :         r.P0z = v.z;
-     286             : 
-     287           0 :         r.SN1 = candidate->getCreatedSerialNumber();
-     288           0 :         r.ID1 = candidate->created.getId();
-     289           0 :         r.E1 = candidate->created.getEnergy() / energyScale;
-     290           0 :         v = candidate->created.getPosition() / lengthScale;
-     291           0 :         r.X1 = v.x;
-     292           0 :         r.Y1 = v.y;
-     293           0 :         r.Z1 = v.z;
-     294           0 :         v = candidate->created.getDirection();
-     295           0 :         r.P1x = v.x;
-     296           0 :         r.P1y = v.y;
-     297           0 :         r.P1z = v.z;
-     298             : 
-     299           0 :         r.weight= candidate->getWeight();
-     300             : 
-     301           0 :         r.tag = candidate->getTagOrigin();
-     302             : 
-     303             :         size_t pos = 0;
-     304           0 :         for(std::vector<Output::Property>::const_iterator iter = properties.begin();
-     305           0 :                         iter != properties.end(); ++iter)
-     306             :         {
-     307           0 :                   Variant v;
-     308           0 :                         if (candidate->hasProperty((*iter).name))
-     309             :                         {
-     310           0 :                                 v = candidate->getProperty((*iter).name);
-     311             :                         }
-     312             :                         else
-     313             :                         {
-     314           0 :                                 v = (*iter).defaultValue;
-     315             :                         }
-     316           0 :                         pos += v.copyToBuffer(&r.propertyBuffer[pos]);
-     317           0 :         }
-     318             : 
-     319           0 :         #pragma omp critical
-     320             :         {
-     321           0 :                 const_cast<HDF5Output*>(this)->candidatesSinceFlush++;
-     322           0 :                 Output::process(candidate);
-     323             : 
-     324           0 :                 buffer.push_back(r);
-     325             : 
-     326             : 
-     327           0 :                 if (buffer.size() >= buffer.capacity())
-     328             :                 {
-     329           0 :                         KISS_LOG_DEBUG << "HDF5Output: Flush due to buffer capacity exceeded";
-     330           0 :                         flush();
-     331             :                 }
-     332           0 :                 else if (candidatesSinceFlush >= flushLimit)
-     333             :                 {
-     334           0 :                         KISS_LOG_DEBUG << "HDF5Output: Flush due to number of candidates";
-     335           0 :                         flush();
-     336             :                 }
-     337           0 :                 else if (difftime(time(NULL), lastFlush) > 60*10)
-     338             :                 {
-     339           0 :                         KISS_LOG_DEBUG << "HDF5Output: Flush due to time exceeded";
-     340           0 :                         flush();
-     341             :                 }
-     342             :         }
-     343           0 : }
-     344             : 
-     345           0 : void HDF5Output::flush() const {
-     346           0 :         const_cast<HDF5Output*>(this)->lastFlush = time(NULL);
-     347           0 :         const_cast<HDF5Output*>(this)->candidatesSinceFlush = 0;
-     348             : 
-     349             :         hsize_t n = buffer.size();
-     350             : 
-     351           0 :         if (n == 0)
-     352           0 :                 return;
-     353             : 
-     354           0 :         hid_t file_space = H5Dget_space(dset);
-     355           0 :         hsize_t count = H5Sget_simple_extent_npoints(file_space);
-     356             : 
-     357             :         // resize dataset
-     358           0 :         hsize_t new_size[RANK] = {count + n};
-     359           0 :         H5Dset_extent(dset, new_size);
-     360             : 
-     361             :         // get updated filespace
-     362           0 :         H5Sclose(file_space);
-     363           0 :         file_space = H5Dget_space(dset);
-     364             : 
-     365           0 :         hsize_t offset[RANK] = {count};
-     366           0 :         hsize_t cnt[RANK] = {n};
-     367             : 
-     368           0 :         H5Sselect_hyperslab(file_space, H5S_SELECT_SET, offset, NULL, cnt, NULL);
-     369           0 :         hid_t mspace_id = H5Screate_simple(RANK, cnt, NULL);
-     370             : 
-     371           0 :         H5Dwrite(dset, sid, mspace_id, file_space, H5P_DEFAULT, buffer.data());
-     372             : 
-     373           0 :         H5Sclose(mspace_id);
-     374           0 :         H5Sclose(file_space);
-     375             : 
-     376           0 :         buffer.clear();
-     377             : 
-     378           0 :         H5Fflush(file, H5F_SCOPE_GLOBAL);
-     379             : }
-     380             : 
-     381           0 : std::string HDF5Output::getDescription() const  {
-     382           0 :         return "HDF5Output";
-     383             : }
-     384             : 
-     385           0 : void HDF5Output::setFlushLimit(unsigned int N)
-     386             : {
-     387           0 :         flushLimit = N;
-     388           0 : }
-     389             : 
-     390             : } // namespace crpropa
-     391             : 
-     392             : #endif // CRPROPA_HAVE_HDF5
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html b/doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html deleted file mode 100644 index 8f9c1026b..000000000 --- a/doc/coverageReport/src/module/MomentumDiffusion.cpp.func-sort-c.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/MomentumDiffusion.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - MomentumDiffusion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:114524.4 %
Date:2024-04-08 14:58:22Functions:31030.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa25ConstantMomentumDiffusionC2Edd0
_ZNK7crpropa25ConstantMomentumDiffusion14getDescriptionB5cxx11Ev0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateAScalarEd0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateBScalarEv0
_ZNK7crpropa25ConstantMomentumDiffusion6getDppEv0
_ZNK7crpropa25ConstantMomentumDiffusion7processEPNS_9CandidateE0
_ZNK7crpropa25ConstantMomentumDiffusion8getLimitEv0
_ZN7crpropa25ConstantMomentumDiffusion6setDppEd1
_ZN7crpropa25ConstantMomentumDiffusionC2Ed1
_ZN7crpropa25ConstantMomentumDiffusion8setLimitEd2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html b/doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html deleted file mode 100644 index 377203fb6..000000000 --- a/doc/coverageReport/src/module/MomentumDiffusion.cpp.func.html +++ /dev/null @@ -1,112 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/MomentumDiffusion.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - MomentumDiffusion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:114524.4 %
Date:2024-04-08 14:58:22Functions:31030.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa25ConstantMomentumDiffusion6setDppEd1
_ZN7crpropa25ConstantMomentumDiffusion8setLimitEd2
_ZN7crpropa25ConstantMomentumDiffusionC2Ed1
_ZN7crpropa25ConstantMomentumDiffusionC2Edd0
_ZNK7crpropa25ConstantMomentumDiffusion14getDescriptionB5cxx11Ev0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateAScalarEd0
_ZNK7crpropa25ConstantMomentumDiffusion16calculateBScalarEv0
_ZNK7crpropa25ConstantMomentumDiffusion6getDppEv0
_ZNK7crpropa25ConstantMomentumDiffusion7processEPNS_9CandidateE0
_ZNK7crpropa25ConstantMomentumDiffusion8getLimitEv0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html b/doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html deleted file mode 100644 index 926f0af54..000000000 --- a/doc/coverageReport/src/module/MomentumDiffusion.cpp.gcov.html +++ /dev/null @@ -1,147 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/MomentumDiffusion.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - MomentumDiffusion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:114524.4 %
Date:2024-04-08 14:58:22Functions:31030.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/MomentumDiffusion.h"
-       2             : 
-       3             : using namespace crpropa;
-       4             : 
-       5           1 : ConstantMomentumDiffusion::ConstantMomentumDiffusion(double Dpp) {
-       6           1 :         setLimit(0.1);
-       7           1 :         setDpp(Dpp);
-       8           1 : }
-       9             : 
-      10           0 : ConstantMomentumDiffusion::ConstantMomentumDiffusion(double Dpp, double limit) {
-      11           0 :         setLimit(limit);
-      12           0 :         setDpp(Dpp);
-      13           0 : }
-      14             : 
-      15           0 : void ConstantMomentumDiffusion::process(Candidate *c) const {
-      16           0 :         double rig = c->current.getRigidity();
-      17           0 :         if (std::isinf(rig)) {
-      18             :                 return; // Only charged particles
-      19             :         }
-      20             :         
-      21           0 :         double p = c->current.getEnergy() / c_light; // Note we use E=p/c (relativistic limit)
-      22           0 :         double dt = c->getCurrentStep() / c_light;
-      23             :         
-      24           0 :         double eta =  Random::instance().randNorm();
-      25           0 :         double domega = eta * sqrt(dt);
-      26             :         
-      27           0 :         double AScal = calculateAScalar(p);
-      28           0 :         double BScal = calculateBScalar();
-      29             : 
-      30           0 :         double dp = AScal * dt + BScal * domega;
-      31           0 :         c->current.setEnergy((p + dp) * c_light);
-      32             :         
-      33           0 :         c->limitNextStep(limit * p / AScal * c_light);
-      34             : }
-      35             : 
-      36           0 : double ConstantMomentumDiffusion::calculateAScalar(double p) const {
-      37           0 :         double a = + 2. / p * Dpp;
-      38           0 :         return a; 
-      39             : }
-      40             : 
-      41           0 : double ConstantMomentumDiffusion::calculateBScalar() const {
-      42           0 :         double b = sqrt(2 * Dpp);
-      43           0 :         return b;
-      44             : }
-      45             : 
-      46           1 : void ConstantMomentumDiffusion::setDpp(double d) {
-      47           1 :         if (d < 0 )
-      48           0 :                 throw std::runtime_error(
-      49           0 :                                 "ConstantMomentumDiffusion: Dpp must be non-negative");
-      50           1 :         Dpp = d;
-      51           1 : }
-      52             : 
-      53           2 : void ConstantMomentumDiffusion::setLimit(double l) {
-      54           2 :         limit = l;
-      55           2 : }
-      56             : 
-      57           0 : double ConstantMomentumDiffusion::getDpp() const {
-      58           0 :         return Dpp;
-      59             : }
-      60             : 
-      61           0 : double ConstantMomentumDiffusion::getLimit() const {
-      62           0 :         return limit;
-      63             : }
-      64             : 
-      65           0 : std::string ConstantMomentumDiffusion::getDescription() const {
-      66           0 :         std::stringstream s;
-      67           0 :         s << "limit: " << limit << "\n";
-      68           0 :         s << "Dpp: " << Dpp / (meter * meter / second) << " m^2/s";
-      69             : 
-      70           0 :         return s.str();
-      71           0 : }
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html b/doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html deleted file mode 100644 index dde7b40eb..000000000 --- a/doc/coverageReport/src/module/NuclearDecay.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/NuclearDecay.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - NuclearDecay.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13716881.5 %
Date:2024-04-08 14:58:22Functions:111384.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12NuclearDecay12meanFreePathEid0
_ZN7crpropa12NuclearDecay8setLimitEd0
_ZN7crpropa12NuclearDecay14setHavePhotonsEb1
_ZN7crpropa12NuclearDecay16setHaveNeutrinosEb1
_ZN7crpropa12NuclearDecay17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa12NuclearDecay16setHaveElectronsEb2
_ZNK7crpropa12NuclearDecay17getInteractionTagB5cxx11Ev2
_ZN7crpropa12NuclearDecayC2Ebbbd9
_ZNK7crpropa12NuclearDecay13gammaEmissionEPNS_9CandidateEi11
_ZNK7crpropa12NuclearDecay9betaDecayEPNS_9CandidateEb499
_ZNK7crpropa12NuclearDecay15nucleonEmissionEPNS_9CandidateEii699
_ZNK7crpropa12NuclearDecay18performInteractionEPNS_9CandidateEi984
_ZNK7crpropa12NuclearDecay7processEPNS_9CandidateE7647
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/NuclearDecay.cpp.func.html b/doc/coverageReport/src/module/NuclearDecay.cpp.func.html deleted file mode 100644 index 2adf42079..000000000 --- a/doc/coverageReport/src/module/NuclearDecay.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/NuclearDecay.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - NuclearDecay.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13716881.5 %
Date:2024-04-08 14:58:22Functions:111384.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa12NuclearDecay12meanFreePathEid0
_ZN7crpropa12NuclearDecay14setHavePhotonsEb1
_ZN7crpropa12NuclearDecay16setHaveElectronsEb2
_ZN7crpropa12NuclearDecay16setHaveNeutrinosEb1
_ZN7crpropa12NuclearDecay17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa12NuclearDecay8setLimitEd0
_ZN7crpropa12NuclearDecayC2Ebbbd9
_ZNK7crpropa12NuclearDecay13gammaEmissionEPNS_9CandidateEi11
_ZNK7crpropa12NuclearDecay15nucleonEmissionEPNS_9CandidateEii699
_ZNK7crpropa12NuclearDecay17getInteractionTagB5cxx11Ev2
_ZNK7crpropa12NuclearDecay18performInteractionEPNS_9CandidateEi984
_ZNK7crpropa12NuclearDecay7processEPNS_9CandidateE7647
_ZNK7crpropa12NuclearDecay9betaDecayEPNS_9CandidateEb499
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html b/doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html deleted file mode 100644 index a9a87ffa4..000000000 --- a/doc/coverageReport/src/module/NuclearDecay.cpp.gcov.html +++ /dev/null @@ -1,395 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/NuclearDecay.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - NuclearDecay.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:13716881.5 %
Date:2024-04-08 14:58:22Functions:111384.6 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/NuclearDecay.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/ParticleMass.h"
-       5             : #include "crpropa/Random.h"
-       6             : 
-       7             : #include <fstream>
-       8             : #include <limits>
-       9             : #include <cmath>
-      10             : #include <stdexcept>
-      11             : 
-      12             : #include "kiss/logger.h"
-      13             : 
-      14             : namespace crpropa {
-      15             : 
-      16           9 : NuclearDecay::NuclearDecay(bool electrons, bool photons, bool neutrinos, double l) {
-      17           9 :         haveElectrons = electrons;
-      18           9 :         havePhotons = photons;
-      19           9 :         haveNeutrinos = neutrinos;
-      20           9 :         limit = l;
-      21           9 :         setDescription("NuclearDecay");
-      22             : 
-      23             :         // load decay table
-      24          18 :         std::string filename = getDataPath("nuclear_decay.txt");
-      25           9 :         std::ifstream infile(filename.c_str());
-      26           9 :         if (!infile.good())
-      27           0 :                 throw std::runtime_error(
-      28           0 :                                 "crpropa::NuclearDecay: could not open file " + filename);
-      29             : 
-      30           9 :         decayTable.resize(27 * 31);
-      31             :         std::string line;
-      32        8550 :         while (std::getline(infile,line)) {
-      33        8541 :                 std::stringstream stream(line);
-      34        8541 :                 if (stream.peek() == '#')
-      35             :                         continue;
-      36             :                 DecayMode decay;
-      37             :                 int Z, N;
-      38             :                 double lifetime;
-      39        8523 :                 stream >> Z >> N >> decay.channel >> lifetime;
-      40        8523 :                 decay.rate = 1. / lifetime / c_light; // decay rate in [1/m]
-      41             :                 std::vector<double> gamma;
-      42             :                 double val;
-      43       34227 :                 while (stream >> val)
-      44       25704 :                         gamma.push_back(val);
-      45       21375 :                 for (int i = 0; i < gamma.size(); i += 2) {
-      46       12852 :                         decay.energy.push_back(gamma[i] * keV);
-      47       12852 :                         decay.intensity.push_back(gamma[i+1]);
-      48             :                 }
-      49        8523 :                 if (infile)
-      50        8523 :                         decayTable[Z * 31 + N].push_back(decay);
-      51        8541 :         }
-      52           9 :         infile.close();
-      53          18 : }
-      54             : 
-      55           2 : void NuclearDecay::setHaveElectrons(bool b) {
-      56           2 :         haveElectrons = b;
-      57           2 : }
-      58             : 
-      59           1 : void NuclearDecay::setHavePhotons(bool b) {
-      60           1 :         havePhotons = b;
-      61           1 : }
-      62             : 
-      63           1 : void NuclearDecay::setHaveNeutrinos(bool b) {
-      64           1 :         haveNeutrinos = b;
-      65           1 : }
-      66             : 
-      67           0 : void NuclearDecay::setLimit(double l) {
-      68           0 :         limit = l;
-      69           0 : }
-      70             : 
-      71        7647 : void NuclearDecay::process(Candidate *candidate) const {
-      72             :         // the loop should be processed at least once for limiting the next step
-      73        7647 :         double step = candidate->getCurrentStep();
-      74        7647 :         double z = candidate->getRedshift();
-      75             :         do {
-      76             :                 // check if nucleus
-      77        7672 :                 int id = candidate->current.getId();
-      78        7672 :                 if (not (isNucleus(id)))
-      79             :                         return;
-      80             : 
-      81        7671 :                 int A = massNumber(id);
-      82        7671 :                 int Z = chargeNumber(id);
-      83        7671 :                 int N = A - Z;
-      84             : 
-      85             :                 // check if particle can decay
-      86        7671 :                 const std::vector<DecayMode> &decays = decayTable[Z * 31 + N];
-      87        7671 :                 if (decays.size() == 0)
-      88             :                         return;
-      89             : 
-      90             :                 // find interaction mode with minimum random decay distance
-      91         328 :                 Random &random = Random::instance();
-      92             :                 double randDistance = std::numeric_limits<double>::max();
-      93             :                 int channel;
-      94             :                 double totalRate = 0;
-      95             : 
-      96         656 :                 for (size_t i = 0; i < decays.size(); i++) {
-      97         328 :                         double rate = decays[i].rate;
-      98         328 :                         rate /= candidate->current.getLorentzFactor();  // relativistic time dilation
-      99         328 :                         rate /= (1 + z);  // rate per light travel distance -> rate per comoving distance
-     100         328 :                         totalRate += rate;
-     101         328 :                         double d = -log(random.rand()) / rate;
-     102         328 :                         if (d > randDistance)
-     103           0 :                                 continue;
-     104             :                         randDistance = d;
-     105         328 :                         channel = decays[i].channel;
-     106             :                 }
-     107             : 
-     108             :                 // check if interaction doesn't happen
-     109         328 :                 if (step < randDistance) {
-     110             :                         // limit next step to a fraction of the mean free path
-     111         303 :                         candidate->limitNextStep(limit / totalRate);
-     112         303 :                         return;
-     113             :                 }
-     114             : 
-     115             :                 // interact and repeat with remaining step
-     116          25 :                 performInteraction(candidate, channel);
-     117          25 :                 step -= randDistance;
-     118          25 :         } while (step > 0);
-     119             : }
-     120             : 
-     121         984 : void NuclearDecay::performInteraction(Candidate *candidate, int channel) const {
-     122             :         // interpret decay channel
-     123             :         int nBetaMinus = digit(channel, 10000);
-     124             :         int nBetaPlus = digit(channel, 1000);
-     125             :         int nAlpha = digit(channel, 100);
-     126             :         int nProton = digit(channel, 10);
-     127             :         int nNeutron = digit(channel, 1);
-     128             : 
-     129             :         // perform decays
-     130         984 :         if (havePhotons)
-     131          11 :                 gammaEmission(candidate,channel);
-     132        1314 :         for (size_t i = 0; i < nBetaMinus; i++)
-     133         330 :                 betaDecay(candidate, false);
-     134        1153 :         for (size_t i = 0; i < nBetaPlus; i++)
-     135         169 :                 betaDecay(candidate, true);
-     136        1008 :         for (size_t i = 0; i < nAlpha; i++)
-     137          24 :                 nucleonEmission(candidate, 4, 2);
-     138        1319 :         for (size_t i = 0; i < nProton; i++)
-     139         335 :                 nucleonEmission(candidate, 1, 1);
-     140        1324 :         for (size_t i = 0; i < nNeutron; i++)
-     141         340 :                 nucleonEmission(candidate, 1, 0);
-     142         984 : }
-     143             : 
-     144          11 : void NuclearDecay::gammaEmission(Candidate *candidate, int channel) const {
-     145          11 :         int id = candidate->current.getId();
-     146          11 :         int Z = chargeNumber(id);
-     147          11 :         int N = massNumber(id) - Z;
-     148             : 
-     149             :         // get photon energies and emission probabilities for decay channel
-     150          11 :         const std::vector<DecayMode> &decays = decayTable[Z * 31 + N];
-     151             :         size_t idecay = decays.size();
-     152          21 :         while (idecay-- != 0) {
-     153          21 :                 if (decays[idecay].channel == channel)
-     154             :                         break;
-     155             :         }
-     156             : 
-     157             :         const std::vector<double> &energy = decays[idecay].energy;
-     158             :         const std::vector<double> &intensity = decays[idecay].intensity;
-     159             : 
-     160             :         // check if photon emission available
-     161          11 :         if (energy.size() == 0)
-     162           0 :                 return;
-     163             : 
-     164          11 :         Random &random = Random::instance();
-     165          11 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     166             : 
-     167          26 :         for (int i = 0; i < energy.size(); ++i) {
-     168             :                 // check if photon of specific energy is emitted
-     169          15 :                 if (random.rand() > intensity[i])
-     170           5 :                         continue;
-     171             :                 // create secondary photon; boost to lab frame
-     172          10 :                 double cosTheta = 2 * random.rand() - 1;
-     173          10 :                 double E = energy[i] * candidate->current.getLorentzFactor() * (1. - cosTheta);
-     174          10 :                 candidate->addSecondary(22, E, pos, 1., interactionTag);
-     175             :         }
-     176             : }
-     177             : 
-     178         499 : void NuclearDecay::betaDecay(Candidate *candidate, bool isBetaPlus) const {
-     179         499 :         double gamma = candidate->current.getLorentzFactor();
-     180         499 :         int id = candidate->current.getId();
-     181         499 :         int A = massNumber(id);
-     182         499 :         int Z = chargeNumber(id);
-     183             : 
-     184             :         // beta- decay
-     185             :         int electronId = 11; // electron
-     186             :         int neutrinoId = -12; // anti-electron neutrino
-     187             :         int dZ = 1;
-     188             :         // beta+ decay
-     189         499 :         if (isBetaPlus) {
-     190             :                 electronId = -11; // positron
-     191             :                 neutrinoId = 12; // electron neutrino
-     192             :                 dZ = -1;
-     193             :         }
-     194             : 
-     195             :         // update candidate, nuclear recoil negligible
-     196             :         try
-     197             :         {
-     198         499 :                 candidate->current.setId(nucleusId(A, Z + dZ));
-     199             :         }
-     200           0 :         catch (std::runtime_error &e)
-     201             :         {
-     202           0 :                 KISS_LOG_ERROR<< "Something went wrong in the NuclearDecay\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
-     203           0 :                 throw;
-     204           0 :         }
-     205             : 
-     206         499 :         candidate->current.setLorentzFactor(gamma);
-     207             : 
-     208         499 :         if (not (haveElectrons or haveNeutrinos))
-     209         487 :                 return;
-     210             : 
-     211             :         // Q-value of the decay, subtract total energy of emitted photons
-     212          12 :         double m1 = nuclearMass(A, Z);
-     213          12 :         double m2 = nuclearMass(A, Z+dZ);
-     214          12 :         double Q = (m1 - m2 - mass_electron) * c_squared;
-     215             : 
-     216             :         // generate cdf of electron energy, neglecting Coulomb correction
-     217             :         // see Basdevant, Fundamentals in Nuclear Physics, eq. (4.92)
-     218             :         // This leads to deviations from theoretical expectations at low 
-     219             :         // primary energies.
-     220             :         std::vector<double> energies;
-     221             :         std::vector<double> densities; // cdf(E), unnormalized
-     222             : 
-     223          12 :         energies.reserve(51);
-     224          12 :         densities.reserve(51);
-     225             : 
-     226             :         double me = mass_electron * c_squared;
-     227          12 :         double cdf = 0;
-     228         624 :         for (int i = 0; i <= 50; i++) {
-     229         612 :                 double E = me + i / 50. * Q;
-     230         612 :                 cdf += E * sqrt(E * E - me * me) * pow(Q + me - E, 2);
-     231         612 :                 energies.push_back(E);
-     232         612 :                 densities.push_back(cdf);
-     233             :         }
-     234             : 
-     235             :         // draw random electron energy and angle
-     236             :         // assumption of ultra-relativistic particles 
-     237             :         // leads to deviations from theoretical predictions
-     238             :         // is not problematic for usual CRPropa energies E>~TeV
-     239          12 :         Random &random = Random::instance();
-     240          12 :         double E = interpolate(random.rand() * cdf, densities, energies);
-     241          12 :         double p = sqrt(E * E - me * me);  // p*c
-     242          12 :         double cosTheta = 2 * random.rand() - 1;
-     243             : 
-     244             :         // boost to lab frame
-     245          12 :         double Ee = gamma * (E - p * cosTheta);
-     246          12 :         double Enu = gamma * (Q + me - E) * (1 + cosTheta);  // pnu*c ~ Enu
-     247             : 
-     248          12 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     249          12 :         if (haveElectrons)
-     250          12 :                 candidate->addSecondary(electronId, Ee, pos, 1., interactionTag);
-     251          12 :         if (haveNeutrinos)
-     252          10 :                 candidate->addSecondary(neutrinoId, Enu, pos, 1., interactionTag);
-     253             : }
-     254             : 
-     255         699 : void NuclearDecay::nucleonEmission(Candidate *candidate, int dA, int dZ) const {
-     256         699 :         Random &random = Random::instance();
-     257         699 :         int id = candidate->current.getId();
-     258         699 :         int A = massNumber(id);
-     259         699 :         int Z = chargeNumber(id);
-     260         699 :         double EpA = candidate->current.getEnergy() / double(A);
-     261             : 
-     262             :         try
-     263             :         {
-     264         699 :                 candidate->current.setId(nucleusId(A - dA, Z - dZ));
-     265             :         }
-     266           0 :         catch (std::runtime_error &e)
-     267             :         {
-     268           0 :                 KISS_LOG_ERROR<< "Something went wrong in the NuclearDecay\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
-     269           0 :                 throw;
-     270           0 :         }
-     271             : 
-     272         699 :         candidate->current.setEnergy(EpA * (A - dA));
-     273         699 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(),candidate->current.getPosition());
-     274             : 
-     275             :         try
-     276             :         {
-     277         699 :                 candidate->addSecondary(nucleusId(dA, dZ), EpA * dA, pos, 1., interactionTag);
-     278             :         }
-     279           0 :         catch (std::runtime_error &e)
-     280             :         {
-     281           0 :                 KISS_LOG_ERROR<< "Something went wrong in the NuclearDecay\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
-     282           0 :                 throw;
-     283           0 :         }
-     284             : 
-     285         699 : }
-     286             : 
-     287           0 : double NuclearDecay::meanFreePath(int id, double gamma) {
-     288           0 :         if (not (isNucleus(id)))
-     289             :                 return std::numeric_limits<double>::max();
-     290             : 
-     291           0 :         int A = massNumber(id);
-     292           0 :         int Z = chargeNumber(id);
-     293           0 :         int N = A - Z;
-     294             : 
-     295             :         // check if particle can decay
-     296           0 :         const std::vector<DecayMode> &decays = decayTable[Z * 31 + N];
-     297           0 :         if (decays.size() == 0)
-     298             :                 return std::numeric_limits<double>::max();
-     299             : 
-     300             :         double totalRate = 0;
-     301             : 
-     302           0 :         for (size_t i = 0; i < decays.size(); i++) {
-     303           0 :                 double rate = decays[i].rate;
-     304           0 :                 rate /= gamma;
-     305           0 :                 totalRate += rate;
-     306             :         }
-     307             : 
-     308           0 :         return 1. / totalRate;
-     309             : }
-     310             : 
-     311           1 : void NuclearDecay::setInteractionTag(std::string tag) {
-     312           1 :         interactionTag = tag;
-     313           1 : }
-     314             : 
-     315           2 : std::string NuclearDecay::getInteractionTag() const {
-     316           2 :         return interactionTag;
-     317             : }
-     318             : 
-     319             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Observer.cpp.func-sort-c.html b/doc/coverageReport/src/module/Observer.cpp.func-sort-c.html deleted file mode 100644 index 7bf409276..000000000 --- a/doc/coverageReport/src/module/Observer.cpp.func-sort-c.html +++ /dev/null @@ -1,248 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Observer.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Observer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8018044.4 %
Date:2024-04-08 14:58:22Functions:164436.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16ObserverTrackingC2ENS_7Vector3IdEEdd0
_ZN7crpropa21ObserverTimeEvolutionC2Ev0
_ZN7crpropa22ObserverParticleIdVetoC2Ei0
_ZN7crpropa22ObserverRedshiftWindowC2Edd0
_ZNK7crpropa10Observer1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverFeature14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa15ObserverFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverSurface14getDescriptionB5cxx11Ev0
_ZNK7crpropa16ObserverTracking14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa16ObserverTracking14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ObserverDetectAll14getDescriptionB5cxx11Ev0
_ZNK7crpropa18ObserverPhotonVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa18ObserverPhotonVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ObserverNucleusVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa19ObserverNucleusVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverElectronVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverElectronVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverInactiveVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverInactiveVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverNeutrinoVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverNeutrinoVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution8getTimesEv0
_ZNK7crpropa22ObserverParticleIdVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverParticleIdVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa22ObserverRedshiftWindow14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverRedshiftWindow14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Observer14getDescriptionB5cxx11Ev0
_ZN7crpropa21ObserverTimeEvolutionC2Eddd1
_ZN7crpropa21ObserverTimeEvolutionC2Edddb1
_ZN7crpropa15ObserverSurfaceC2EPNS_7SurfaceE2
_ZN7crpropa21ObserverTimeEvolution12addTimeRangeEdddb2
_ZN7crpropa8Observer11onDetectionEPNS_6ModuleEb2
_ZN7crpropa8Observer24setDeactivateOnDetectionEb2
_ZN7crpropa8Observer7setFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_2
_ZNK7crpropa17ObserverDetectAll14checkDetectionEPNS_9CandidateE2
_ZN7crpropa21ObserverTimeEvolution7addTimeERKd4
_ZNK7crpropa15ObserverSurface14checkDetectionEPNS_9CandidateE4
_ZNK7crpropa21ObserverTimeEvolution14checkDetectionEPNS_9CandidateE6
_ZN7crpropa8Observer3addEPNS_15ObserverFeatureE10
_ZN7crpropa8ObserverC2Ev10
_ZNK7crpropa15ObserverFeature11onDetectionEPNS_9CandidateE52
_ZNK7crpropa10Observer1D14checkDetectionEPNS_9CandidateE7664
_ZNK7crpropa8Observer7processEPNS_9CandidateE7681
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Observer.cpp.func.html b/doc/coverageReport/src/module/Observer.cpp.func.html deleted file mode 100644 index d3bea8de7..000000000 --- a/doc/coverageReport/src/module/Observer.cpp.func.html +++ /dev/null @@ -1,248 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Observer.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Observer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8018044.4 %
Date:2024-04-08 14:58:22Functions:164436.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa15ObserverSurfaceC2EPNS_7SurfaceE2
_ZN7crpropa16ObserverTrackingC2ENS_7Vector3IdEEdd0
_ZN7crpropa21ObserverTimeEvolution12addTimeRangeEdddb2
_ZN7crpropa21ObserverTimeEvolution7addTimeERKd4
_ZN7crpropa21ObserverTimeEvolutionC2Eddd1
_ZN7crpropa21ObserverTimeEvolutionC2Edddb1
_ZN7crpropa21ObserverTimeEvolutionC2Ev0
_ZN7crpropa22ObserverParticleIdVetoC2Ei0
_ZN7crpropa22ObserverRedshiftWindowC2Edd0
_ZN7crpropa8Observer11onDetectionEPNS_6ModuleEb2
_ZN7crpropa8Observer24setDeactivateOnDetectionEb2
_ZN7crpropa8Observer3addEPNS_15ObserverFeatureE10
_ZN7crpropa8Observer7setFlagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEES6_2
_ZN7crpropa8ObserverC2Ev10
_ZNK7crpropa10Observer1D14checkDetectionEPNS_9CandidateE7664
_ZNK7crpropa10Observer1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverFeature11onDetectionEPNS_9CandidateE52
_ZNK7crpropa15ObserverFeature14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa15ObserverFeature14getDescriptionB5cxx11Ev0
_ZNK7crpropa15ObserverSurface14checkDetectionEPNS_9CandidateE4
_ZNK7crpropa15ObserverSurface14getDescriptionB5cxx11Ev0
_ZNK7crpropa16ObserverTracking14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa16ObserverTracking14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ObserverDetectAll14checkDetectionEPNS_9CandidateE2
_ZNK7crpropa17ObserverDetectAll14getDescriptionB5cxx11Ev0
_ZNK7crpropa18ObserverPhotonVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa18ObserverPhotonVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ObserverNucleusVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa19ObserverNucleusVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverElectronVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverElectronVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverInactiveVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverInactiveVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa20ObserverNeutrinoVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa20ObserverNeutrinoVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution14checkDetectionEPNS_9CandidateE6
_ZNK7crpropa21ObserverTimeEvolution14getDescriptionB5cxx11Ev0
_ZNK7crpropa21ObserverTimeEvolution8getTimesEv0
_ZNK7crpropa22ObserverParticleIdVeto14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverParticleIdVeto14getDescriptionB5cxx11Ev0
_ZNK7crpropa22ObserverRedshiftWindow14checkDetectionEPNS_9CandidateE0
_ZNK7crpropa22ObserverRedshiftWindow14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Observer14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Observer7processEPNS_9CandidateE7681
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Observer.cpp.gcov.html b/doc/coverageReport/src/module/Observer.cpp.gcov.html deleted file mode 100644 index e54a180c9..000000000 --- a/doc/coverageReport/src/module/Observer.cpp.gcov.html +++ /dev/null @@ -1,427 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Observer.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Observer.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8018044.4 %
Date:2024-04-08 14:58:22Functions:164436.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/Observer.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/Cosmology.h"
-       5             : 
-       6             : #include "kiss/logger.h"
-       7             : 
-       8             : #include <iostream>
-       9             : #include <cmath>
-      10             : 
-      11             : namespace crpropa {
-      12             : 
-      13             : // Observer -------------------------------------------------------------------
-      14          10 : Observer::Observer() :
-      15          10 :                 makeInactive(true), clone(false) {
-      16          10 : }
-      17             : 
-      18          10 : void Observer::add(ObserverFeature *feature) {
-      19          10 :         features.push_back(feature);
-      20          10 : }
-      21             : 
-      22           2 : void Observer::onDetection(Module *action, bool clone_) {
-      23           2 :         detectionAction = action;
-      24           2 :         clone = clone_;
-      25           2 : }
-      26             : 
-      27        7681 : void Observer::process(Candidate *candidate) const {
-      28             :         // loop over all features and have them check the particle
-      29             :         DetectionState state = NOTHING;
-      30       15362 :         for (int i = 0; i < features.size(); i++) {
-      31        7681 :                 DetectionState s = features[i]->checkDetection(candidate);
-      32        7681 :                 if (s == VETO)
-      33             :                         state = VETO;
-      34        7681 :                 else if ((s == DETECTED) && (state != VETO))
-      35             :                         state = DETECTED;
-      36             :         }
-      37             : 
-      38        7681 :         if (state == DETECTED) {
-      39         104 :                 for (int i = 0; i < features.size(); i++) {
-      40          52 :                         features[i]->onDetection(candidate);
-      41             :                 }
-      42             : 
-      43          52 :                 if (detectionAction.valid()) {
-      44          38 :                         if (clone)
-      45           0 :                                 detectionAction->process(candidate->clone(false));
-      46             :                         else
-      47          38 :                                 detectionAction->process(candidate);
-      48             :                 }
-      49             : 
-      50          52 :                 if (!flagKey.empty())
-      51           4 :                         candidate->setProperty(flagKey, flagValue);
-      52             : 
-      53          52 :                 if (makeInactive)
-      54          48 :                         candidate->setActive(false);
-      55             :         }
-      56        7681 : }
-      57             : 
-      58           2 : void Observer::setFlag(std::string key, std::string value) {
-      59           2 :         flagKey = key;
-      60           2 :         flagValue = value;
-      61           2 : }
-      62             : 
-      63           0 : std::string Observer::getDescription() const {
-      64           0 :         std::stringstream ss;
-      65           0 :         ss << "Observer";
-      66           0 :         for (int i = 0; i < features.size(); i++)
-      67           0 :                 ss << "\n    " << features[i]->getDescription() << "\n";
-      68           0 :         ss << "    Flag: '" << flagKey << "' -> '" << flagValue << "'\n";
-      69           0 :         ss << "    MakeInactive: " << (makeInactive ? "yes\n" : "no\n");
-      70           0 :         if (detectionAction.valid())
-      71           0 :                 ss << "    Action: " << detectionAction->getDescription() << ", clone: " << (clone ? "yes" : "no");
-      72             : 
-      73           0 :         return ss.str();
-      74           0 : }
-      75             : 
-      76           2 : void Observer::setDeactivateOnDetection(bool deactivate) {
-      77           2 :         makeInactive = deactivate;
-      78           2 : }
-      79             : 
-      80             : // ObserverFeature ------------------------------------------------------------
-      81           0 : DetectionState ObserverFeature::checkDetection(Candidate *candidate) const {
-      82           0 :         return NOTHING;
-      83             : }
-      84             : 
-      85          52 : void ObserverFeature::onDetection(Candidate *candidate) const {
-      86          52 : }
-      87             : 
-      88           0 : std::string ObserverFeature::getDescription() const {
-      89           0 :         return description;
-      90             : }
-      91             : 
-      92             : // ObserverDetectAll ----------------------------------------------------------
-      93           2 : DetectionState ObserverDetectAll::checkDetection(Candidate *candidate) const {
-      94           2 :         return DETECTED;
-      95             : }
-      96             : 
-      97           0 : std::string ObserverDetectAll::getDescription() const {
-      98           0 :         return description;
-      99             : }
-     100             : 
-     101             : // ObserverTracking --------------------------------------------------------
-     102           0 : ObserverTracking::ObserverTracking(Vector3d center, double radius, double stepSize) :
-     103           0 :                 center(center), radius(radius), stepSize(stepSize) {
-     104             :         if (stepSize == 0) {
-     105             :                 stepSize = radius / 10.;
-     106             :         }
-     107           0 : }
-     108             : 
-     109           0 : DetectionState ObserverTracking::checkDetection(Candidate *candidate) const {
-     110             :         // current distance to observer sphere center
-     111           0 :         double d = (candidate->current.getPosition() - center).getR();
-     112             : 
-     113             :         // no detection if outside of observer sphere
-     114           0 :         if (d > radius) {
-     115             :                 // conservatively limit next step to prevent overshooting
-     116           0 :                 candidate->limitNextStep(fabs(d - radius));
-     117             : 
-     118           0 :                 return NOTHING;
-     119             :         } else {
-     120             :                 // limit next step
-     121           0 :                 candidate->limitNextStep(stepSize);
-     122             : 
-     123           0 :                 return DETECTED;
-     124             :         }
-     125             : }
-     126             : 
-     127           0 : std::string ObserverTracking::getDescription() const {
-     128           0 :         std::stringstream ss;
-     129           0 :         ss << "ObserverTracking: ";
-     130           0 :         ss << "center = " << center / Mpc << " Mpc, ";
-     131           0 :         ss << "radius = " << radius / Mpc << " Mpc";
-     132           0 :         ss << "stepSize = " << stepSize / Mpc << " Mpc";
-     133           0 :         return ss.str();
-     134           0 : }
-     135             : 
-     136             : // Observer1D --------------------------------------------------------------
-     137        7664 : DetectionState Observer1D::checkDetection(Candidate *candidate) const {
-     138        7664 :         double x = candidate->current.getPosition().x;
-     139        7664 :         if (x > 0) {
-     140             :                 // Limits the next step size to prevent candidates from overshooting in case of non-detection
-     141        7625 :                 candidate->limitNextStep(x);
-     142        7625 :                 return NOTHING;
-     143             :         }
-     144             :         // Detects particles when reaching x = 0
-     145             :         return DETECTED;
-     146             : }
-     147             : 
-     148           0 : std::string Observer1D::getDescription() const {
-     149           0 :         return "Observer1D: observer at x = 0";
-     150             : }
-     151             : 
-     152             : // ObserverRedshiftWindow -----------------------------------------------------
-     153           0 : ObserverRedshiftWindow::ObserverRedshiftWindow(double zmin, double zmax) :
-     154           0 :                 zmin(zmin), zmax(zmax) {
-     155           0 : }
-     156             : 
-     157           0 : DetectionState ObserverRedshiftWindow::checkDetection(
-     158             :                 Candidate *candidate) const {
-     159           0 :         double z = candidate->getRedshift();
-     160           0 :         if (z > zmax)
-     161             :                 return VETO;
-     162           0 :         if (z < zmin)
-     163           0 :                 return VETO;
-     164             :         return NOTHING;
-     165             : }
-     166             : 
-     167           0 : std::string ObserverRedshiftWindow::getDescription() const {
-     168           0 :         std::stringstream ss;
-     169           0 :         ss << "ObserverRedshiftWindow: z = " << zmin << " - " << zmax;
-     170           0 :         return ss.str();
-     171           0 : }
-     172             : 
-     173             : // ObserverInactiveVeto -------------------------------------------------------
-     174           0 : DetectionState ObserverInactiveVeto::checkDetection(Candidate *c) const {
-     175           0 :         if (not(c->isActive()))
-     176           0 :                 return VETO;
-     177             :         return NOTHING;
-     178             : }
-     179             : 
-     180           0 : std::string ObserverInactiveVeto::getDescription() const {
-     181           0 :         return "ObserverInactiveVeto";
-     182             : }
-     183             : 
-     184             : // ObserverNucleusVeto --------------------------------------------------------
-     185           0 : DetectionState ObserverNucleusVeto::checkDetection(Candidate *c) const {
-     186           0 :         if (isNucleus(c->current.getId()))
-     187           0 :                 return VETO;
-     188             :         return NOTHING;
-     189             : }
-     190             : 
-     191           0 : std::string ObserverNucleusVeto::getDescription() const {
-     192           0 :         return "ObserverNucleusVeto";
-     193             : }
-     194             : 
-     195             : // ObserverNeutrinoVeto -------------------------------------------------------
-     196           0 : DetectionState ObserverNeutrinoVeto::checkDetection(Candidate *c) const {
-     197           0 :         int id = abs(c->current.getId());
-     198           0 :         if ((id == 12) or (id == 14) or (id == 16))
-     199           0 :                 return VETO;
-     200             :         return NOTHING;
-     201             : }
-     202             : 
-     203           0 : std::string ObserverNeutrinoVeto::getDescription() const {
-     204           0 :         return "ObserverNeutrinoVeto";
-     205             : }
-     206             : 
-     207             : // ObserverPhotonVeto ---------------------------------------------------------
-     208           0 : DetectionState ObserverPhotonVeto::checkDetection(Candidate *c) const {
-     209           0 :         if (c->current.getId() == 22)
-     210           0 :                 return VETO;
-     211             :         return NOTHING;
-     212             : }
-     213             : 
-     214           0 : std::string ObserverPhotonVeto::getDescription() const {
-     215           0 :         return "ObserverPhotonVeto";
-     216             : }
-     217             : 
-     218             : // ObserverElectronVeto ---------------------------------------------------------
-     219           0 : DetectionState ObserverElectronVeto::checkDetection(Candidate *c) const {
-     220           0 :         if (abs(c->current.getId()) == 11)
-     221           0 :                 return VETO;
-     222             :         return NOTHING;
-     223             : }
-     224             : 
-     225           0 : std::string ObserverElectronVeto::getDescription() const {
-     226           0 :         return "ObserverElectronVeto";
-     227             : }
-     228             : 
-     229             : // ObserverCustomVeto -------------------------------------------------------
-     230           0 : ObserverParticleIdVeto::ObserverParticleIdVeto(int pId) {
-     231           0 :         vetoParticleId = pId;
-     232           0 : }
-     233             : 
-     234           0 : DetectionState ObserverParticleIdVeto::checkDetection(Candidate *c) const {
-     235           0 :         if (c->current.getId() == vetoParticleId)
-     236           0 :                 return VETO;
-     237             :         return NOTHING;
-     238             : }
-     239             : 
-     240           0 : std::string ObserverParticleIdVeto::getDescription() const {
-     241           0 :         return "ObserverParticleIdVeto";
-     242             : }
-     243             : 
-     244             : 
-     245             : // ObserverTimeEvolution --------------------------------------------------------
-     246           0 : ObserverTimeEvolution::ObserverTimeEvolution() {}
-     247             : 
-     248           1 : ObserverTimeEvolution::ObserverTimeEvolution(double min, double dist, double numb) {
-     249           1 :         double max = min + numb * dist;
-     250             :         bool log = false;
-     251           1 :         addTimeRange(min, max, numb, log);
-     252           1 : }
-     253             : 
-     254           1 : ObserverTimeEvolution::ObserverTimeEvolution(double min, double max, double numb, bool log) {
-     255           1 :         addTimeRange(min, max, numb, log);
-     256           1 : }
-     257             : 
-     258             : 
-     259           6 : DetectionState ObserverTimeEvolution::checkDetection(Candidate *c) const {
-     260             : 
-     261           6 :         if (detList.size()) {
-     262           6 :                 double length = c->getTrajectoryLength();
-     263             :                 size_t index;
-     264           6 :                 const std::string DI = "DetectionIndex";
-     265             :                 std::string value;
-     266             : 
-     267             :                 // Load the last detection index
-     268           6 :                 if (c->hasProperty(DI)) {
-     269           4 :                         index = c->getProperty(DI).asUInt64();
-     270             :                 }
-     271             :                 else {
-     272             :                         index = 0;
-     273             :                 }
-     274             : 
-     275             :                 // Break if the particle has been detected once for all detList entries.
-     276           6 :                 if (index > detList.size()) {
-     277             :                         return NOTHING;
-     278             :                 }
-     279             : 
-     280             :                 // Calculate the distance to next detection
-     281           6 :                 double distance = length - detList[index];
-     282             : 
-     283             :                 // Limit next step and detect candidate.
-     284             :                 // Increase the index by one in case of detection
-     285           6 :                 if (distance < 0.) {
-     286           2 :                         c->limitNextStep(-distance);
-     287             :                         return NOTHING;
-     288             :                 }
-     289             :                 else {
-     290             : 
-     291           4 :                         if (index < detList.size()-1) {
-     292           2 :                                 c->limitNextStep(detList[index+1]-length);
-     293             :                         }
-     294           4 :                         c->setProperty(DI, Variant::fromUInt64(index+1));
-     295             : 
-     296           4 :                         return DETECTED;
-     297             :                 }
-     298             :         }
-     299             :         return NOTHING;
-     300             : }
-     301             : 
-     302           4 : void ObserverTimeEvolution::addTime(const double& t) {
-     303           4 :         detList.push_back(t);
-     304           4 : }
-     305             : 
-     306           2 : void ObserverTimeEvolution::addTimeRange(double min, double max, double numb, bool log) {
-     307           6 :         for (size_t i = 0; i < numb; i++) {
-     308           4 :                 if (log == true) {
-     309           2 :                         addTime(min * pow(max / min, i / (numb - 1.0)));
-     310             :                 } else {
-     311           2 :                         addTime(min + i * (max - min) / numb);
-     312             :                 }
-     313             :         }
-     314           2 : }
-     315             : 
-     316           0 : const std::vector<double>& ObserverTimeEvolution::getTimes() const {
-     317           0 :         return detList;
-     318             : }
-     319             : 
-     320           0 : std::string ObserverTimeEvolution::getDescription() const {
-     321           0 :         std::stringstream s;
-     322           0 :         s << "List of Detection lengths in kpc";
-     323           0 :         for (size_t i = 0; i < detList.size(); i++)
-     324           0 :           s << "  - " << detList[i] / kpc;
-     325           0 :         return s.str();
-     326           0 : }
-     327             : 
-     328             : // ObserverSurface--------------------------------------------------------------
-     329           2 : ObserverSurface::ObserverSurface(Surface* _surface) : surface(_surface) { }
-     330             : 
-     331           4 : DetectionState ObserverSurface::checkDetection(Candidate *candidate) const
-     332             : {
-     333           4 :                 double currentDistance = surface->distance(candidate->current.getPosition());
-     334           4 :                 double previousDistance = surface->distance(candidate->previous.getPosition());
-     335           4 :                 candidate->limitNextStep(fabs(currentDistance));
-     336             : 
-     337           4 :                 if (currentDistance * previousDistance > 0)
-     338             :                         return NOTHING;
-     339           2 :                 else if (previousDistance == 0)
-     340             :                         return NOTHING;
-     341             :                 else
-     342           2 :                         return DETECTED;
-     343             : }
-     344             : 
-     345           0 : std::string ObserverSurface::getDescription() const {
-     346           0 :         std::stringstream ss;
-     347           0 :         ss << "ObserverSurface: << " << surface->getDescription();
-     348           0 :         return ss.str();
-     349           0 : }
-     350             : 
-     351             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Output.cpp.func-sort-c.html b/doc/coverageReport/src/module/Output.cpp.func-sort-c.html deleted file mode 100644 index 8aa2d21bc..000000000 --- a/doc/coverageReport/src/module/Output.cpp.func-sort-c.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Output.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:889889.8 %
Date:2024-04-08 14:58:22Functions:141687.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Output14setEnergyScaleEd0
_ZN7crpropa6Output14setLengthScaleEd0
_ZN7crpropa6Output10disableAllEv1
_ZN7crpropa6Output14enablePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantES8_1
_ZN7crpropa6Output7disableENS0_12OutputColumnE1
_ZNK7crpropa6Output4sizeEv1
_ZN7crpropa6Output6enableENS0_12OutputColumnE2
_ZN7crpropa6OutputC2Ev4
_ZN7crpropa6Output9enableAllEv5
_ZN7crpropa6Output13setOutputTypeENS0_10OutputTypeE8
_ZN7crpropa6OutputC2ENS0_10OutputTypeE8
_ZN7crpropa6Output5set1DEb9
_ZN7crpropa6Output14OutputTypeNameB5cxx11ENS0_10OutputTypeE12
_ZN7crpropa6Output3setENS0_12OutputColumnEb38
_ZNK7crpropa6Output7processEPNS_9CandidateE59
_ZN7crpropa6Output6modifyEv65
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Output.cpp.func.html b/doc/coverageReport/src/module/Output.cpp.func.html deleted file mode 100644 index e967462c5..000000000 --- a/doc/coverageReport/src/module/Output.cpp.func.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Output.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:889889.8 %
Date:2024-04-08 14:58:22Functions:141687.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa6Output10disableAllEv1
_ZN7crpropa6Output13setOutputTypeENS0_10OutputTypeE8
_ZN7crpropa6Output14OutputTypeNameB5cxx11ENS0_10OutputTypeE12
_ZN7crpropa6Output14enablePropertyERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEERKNS_7VariantES8_1
_ZN7crpropa6Output14setEnergyScaleEd0
_ZN7crpropa6Output14setLengthScaleEd0
_ZN7crpropa6Output3setENS0_12OutputColumnEb38
_ZN7crpropa6Output5set1DEb9
_ZN7crpropa6Output6enableENS0_12OutputColumnE2
_ZN7crpropa6Output6modifyEv65
_ZN7crpropa6Output7disableENS0_12OutputColumnE1
_ZN7crpropa6Output9enableAllEv5
_ZN7crpropa6OutputC2ENS0_10OutputTypeE8
_ZN7crpropa6OutputC2Ev4
_ZNK7crpropa6Output4sizeEv1
_ZNK7crpropa6Output7processEPNS_9CandidateE59
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Output.cpp.gcov.html b/doc/coverageReport/src/module/Output.cpp.gcov.html deleted file mode 100644 index d08f567ad..000000000 --- a/doc/coverageReport/src/module/Output.cpp.gcov.html +++ /dev/null @@ -1,210 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Output.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Output.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:889889.8 %
Date:2024-04-08 14:58:22Functions:141687.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/Output.h"
-       2             : #include "crpropa/Units.h"
-       3             : 
-       4             : #include <stdexcept>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           4 : Output::Output() : outputName(OutputTypeName(Everything)), lengthScale(Mpc), energyScale(EeV), oneDimensional(false), count(0) {
-       9           4 :         enableAll();
-      10           4 : }
-      11             : 
-      12           8 : Output::Output(OutputType outputType) : outputName(OutputTypeName(outputType)), lengthScale(Mpc), energyScale(EeV), oneDimensional(false), count(0) {
-      13           8 :         setOutputType(outputType);
-      14           8 : }
-      15             : 
-      16          12 : std::string Output::OutputTypeName(OutputType outputType) {
-      17          12 :         if (outputType == Trajectory1D)
-      18           1 :                 return "Trajectory1D";
-      19          11 :         if (outputType == Event1D)
-      20           4 :                 return "Event1D";
-      21           7 :         if (outputType == Trajectory3D)
-      22           1 :                 return "Trajectory3D";
-      23           6 :         if (outputType == Event3D)
-      24           1 :                 return "Event3D";
-      25           5 :         return "Everything";
-      26             : }
-      27             : 
-      28          65 : void Output::modify() {
-      29          65 :         if (count > 0)
-      30           0 :                 throw std::runtime_error("Output: cannot change Output parameters after data has been written to file.");
-      31          65 : }
-      32             : 
-      33          59 : void Output::process(Candidate *c) const {
-      34          59 :         count++;
-      35          59 : }
-      36             : 
-      37           8 : void Output::setOutputType(OutputType outputtype) {
-      38           8 :         modify();
-      39           8 :         if (outputtype == Trajectory1D) {
-      40             :                 // X, ID, E
-      41           1 :                 set(CurrentPositionColumn, true);
-      42           1 :                 set(CurrentIdColumn, true);
-      43           1 :                 set(CurrentEnergyColumn, true);
-      44           1 :                 set1D(true);
-      45           7 :         } else if (outputtype == Event1D) {
-      46             :                 // D, ID, E, ID0, E0
-      47           4 :                 set(TrajectoryLengthColumn, true);
-      48           4 :                 set(CurrentIdColumn, true);
-      49           4 :                 set(CurrentEnergyColumn, true);
-      50           4 :                 set(SourceIdColumn, true);
-      51           4 :                 set(SourceEnergyColumn, true);
-      52           4 :                 set1D(true);
-      53           3 :         } else if (outputtype == Trajectory3D) {
-      54             :                 // D, ID, E, X, Y, Z, Px, Py, Pz
-      55           1 :                 set(TrajectoryLengthColumn, true);
-      56           1 :                 set(CurrentIdColumn, true);
-      57           1 :                 set(CurrentEnergyColumn, true);
-      58           1 :                 set(CurrentPositionColumn, true);
-      59           1 :                 set(CurrentDirectionColumn, true);
-      60           1 :                 set1D(false);
-      61           2 :         } else if (outputtype == Event3D) {
-      62             :                 // D, ID, E, X, Y, Z, Px, Py, Pz, ID0, E0, X0, Y0, Z0, P0x, P0y, P0z
-      63           1 :                 set(TrajectoryLengthColumn, true);
-      64           1 :                 set(CurrentIdColumn, true);
-      65           1 :                 set(CurrentEnergyColumn, true);
-      66           1 :                 set(CurrentPositionColumn, true);
-      67           1 :                 set(CurrentDirectionColumn, true);
-      68           1 :                 set(SourceIdColumn, true);
-      69           1 :                 set(SourceEnergyColumn, true);
-      70           1 :                 set(SourcePositionColumn, true);
-      71           1 :                 set(SourceDirectionColumn, true);
-      72           1 :                 set1D(false);
-      73           1 :         } else if (outputtype == Everything) {
-      74           1 :                 enableAll();
-      75           1 :                 set1D(false);
-      76             :         } else {
-      77           0 :                 throw std::runtime_error("Output: unknown output type");
-      78             :         }
-      79           8 : }
-      80             : 
-      81           0 : void Output::setEnergyScale(double scale) {
-      82           0 :         modify();
-      83           0 :         energyScale = scale;
-      84           0 : }
-      85             : 
-      86           0 : void Output::setLengthScale(double scale) {
-      87           0 :         modify();
-      88           0 :         lengthScale = scale;
-      89           0 : }
-      90             : 
-      91           9 : void Output::set1D(bool value) {
-      92           9 :         modify();
-      93           9 :         oneDimensional = value;
-      94           9 : }
-      95             : 
-      96           2 : void Output::enable(OutputColumn field) {
-      97           2 :         modify();
-      98           2 :         fields.set(field, true);
-      99           2 : }
-     100             : 
-     101           1 : void Output::disable(OutputColumn field) {
-     102           1 :         modify();
-     103           1 :         fields.set(field, false);
-     104           1 : }
-     105             : 
-     106          38 : void Output::set(OutputColumn field, bool value) {
-     107          38 :         modify();
-     108          38 :         fields.set(field, value);
-     109          38 : }
-     110             : 
-     111           5 : void Output::enableAll() {
-     112           5 :         modify();
-     113             :         fields.set();
-     114           5 : }
-     115             : 
-     116           1 : void Output::disableAll() {
-     117           1 :         modify();
-     118             :         fields.reset();
-     119           1 : }
-     120             : 
-     121           1 : size_t Output::size() const {
-     122           1 :         return count;
-     123             : }
-     124             : 
-     125           1 : void Output::enableProperty(const std::string &property, const Variant &defaultValue, const std::string &comment) {
-     126           1 :         modify();
-     127           1 :         Property prop;
-     128             :         prop.name = property;
-     129             :         prop.comment = comment;
-     130           1 :         prop.defaultValue = defaultValue;
-     131           1 :         properties.push_back(prop);
-     132           1 : };
-     133             : 
-     134             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html b/doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html deleted file mode 100644 index 98f8d83aa..000000000 --- a/doc/coverageReport/src/module/OutputShell.cpp.func-sort-c.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/OutputShell.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - OutputShell.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa11ShellOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ShellOutput7processEPNS_9CandidateE0
_ZNK7crpropa13ShellOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ShellOutput1D7processEPNS_9CandidateE0
_ZNK7crpropa19ShellPropertyOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ShellPropertyOutput7processEPNS_9CandidateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/OutputShell.cpp.func.html b/doc/coverageReport/src/module/OutputShell.cpp.func.html deleted file mode 100644 index 2ba776c67..000000000 --- a/doc/coverageReport/src/module/OutputShell.cpp.func.html +++ /dev/null @@ -1,96 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/OutputShell.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - OutputShell.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa11ShellOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa11ShellOutput7processEPNS_9CandidateE0
_ZNK7crpropa13ShellOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa13ShellOutput1D7processEPNS_9CandidateE0
_ZNK7crpropa19ShellPropertyOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa19ShellPropertyOutput7processEPNS_9CandidateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/OutputShell.cpp.gcov.html b/doc/coverageReport/src/module/OutputShell.cpp.gcov.html deleted file mode 100644 index 5ac2e949a..000000000 --- a/doc/coverageReport/src/module/OutputShell.cpp.gcov.html +++ /dev/null @@ -1,134 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/OutputShell.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - OutputShell.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0270.0 %
Date:2024-04-08 14:58:22Functions:060.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/OutputShell.h"
-       2             : #include "crpropa/Units.h"
-       3             : 
-       4             : #include <iomanip>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8           0 : void ShellOutput::process(Candidate* c) const {
-       9           0 : #pragma omp critical
-      10             :         {
-      11             :                 std::cout << std::fixed << std::showpoint << std::setprecision(3)
-      12             :                                 << std::setw(6);
-      13           0 :                 std::cout << c->getTrajectoryLength() / Mpc << " Mpc,  ";
-      14           0 :                 std::cout << c->getRedshift() << ",  ";
-      15           0 :                 std::cout << c->current.getId() << ",  ";
-      16           0 :                 std::cout << c->current.getEnergy() / EeV << " EeV,  ";
-      17           0 :                 std::cout << c->current.getPosition() / Mpc << " Mpc,  ";
-      18           0 :                 std::cout << c->current.getDirection();
-      19             :                 std::cout << std::endl;
-      20             :         }
-      21           0 : }
-      22             : 
-      23           0 : std::string ShellOutput::getDescription() const {
-      24           0 :         return "Shell output";
-      25             : }
-      26             : 
-      27           0 : void ShellOutput1D::process(Candidate* c) const {
-      28           0 : #pragma omp critical
-      29             :         {
-      30             :                 std::cout << std::fixed << std::showpoint << std::setprecision(3)
-      31             :                                 << std::setw(6);
-      32           0 :                 std::cout << c->current.getPosition().x / Mpc << " Mpc,  ";
-      33           0 :                 std::cout << c->getRedshift() << ",  ";
-      34           0 :                 std::cout << c->current.getId() << ",  ";
-      35           0 :                 std::cout << c->current.getEnergy() / EeV << " EeV";
-      36             :                 std::cout << std::endl;
-      37             :         }
-      38           0 : }
-      39             : 
-      40           0 : std::string ShellOutput1D::getDescription() const {
-      41           0 :         return "Shell output for 1D";
-      42             : }
-      43             : 
-      44           0 : void ShellPropertyOutput::process(Candidate* c) const {
-      45             :         Candidate::PropertyMap::const_iterator i = c->properties.begin();
-      46           0 : #pragma omp critical
-      47             :         {
-      48           0 :                 for ( ; i != c->properties.end(); i++) {
-      49           0 :                         std::cout << "  " << i->first << ", " << i->second << std::endl;
-      50             :                 }
-      51             :         }
-      52           0 : }
-      53             : 
-      54           0 : std::string ShellPropertyOutput::getDescription() const {
-      55           0 :         return "Shell property output";
-      56             : }
-      57             : 
-      58             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html b/doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html deleted file mode 100644 index 066818d57..000000000 --- a/doc/coverageReport/src/module/ParticleCollector.cpp.func-sort-c.html +++ /dev/null @@ -1,168 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ParticleCollector.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ParticleCollector.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:547275.0 %
Date:2024-04-08 14:58:22Functions:172470.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ParticleCollectorC2Em0
_ZN7crpropa17ParticleCollectorC2Emb0
_ZN7crpropa17ParticleCollectorC2Embb0
_ZNK7crpropa17ParticleCollector14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ParticleCollector3endEv0
_ZNK7crpropa17ParticleCollector5beginEv0
_ZNK7crpropa17ParticleCollector8getCloneEv0
_ZN7crpropa17ParticleCollector4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17ParticleCollector13getTrajectoryENS_7ref_ptrINS_10ModuleListEEEmNS1_INS_6ModuleEEE1
_ZNK7crpropa17ParticleCollector13getTrajectoryEPNS_10ModuleListEmPNS_6ModuleE1
_ZNK7crpropa17ParticleCollector4dumpERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa17ParticleCollector8setCloneEb2
_ZNK7crpropa17ParticleCollector12getContainerEv2
_ZNK7crpropa17ParticleCollector9reprocessEPNS_6ModuleE2
_ZN7crpropa17ParticleCollector5beginEv5
_ZNK7crpropa17ParticleCollector4sizeEv6
_ZN7crpropa17ParticleCollectorD0Ev8
_ZNK7crpropa17ParticleCollectorixEm8
_ZN7crpropa17ParticleCollector14clearContainerEv14
_ZN7crpropa17ParticleCollectorC2Ev14
_ZN7crpropa17ParticleCollectorD2Ev14
_ZN7crpropa17ParticleCollector3endEv30
_ZNK7crpropa17ParticleCollector7processENS_7ref_ptrINS_9CandidateEEE30
_ZNK7crpropa17ParticleCollector7processEPNS_9CandidateE3206
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ParticleCollector.cpp.func.html b/doc/coverageReport/src/module/ParticleCollector.cpp.func.html deleted file mode 100644 index a393ca64a..000000000 --- a/doc/coverageReport/src/module/ParticleCollector.cpp.func.html +++ /dev/null @@ -1,168 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ParticleCollector.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ParticleCollector.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:547275.0 %
Date:2024-04-08 14:58:22Functions:172470.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17ParticleCollector14clearContainerEv14
_ZN7crpropa17ParticleCollector3endEv30
_ZN7crpropa17ParticleCollector4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa17ParticleCollector5beginEv5
_ZN7crpropa17ParticleCollector8setCloneEb2
_ZN7crpropa17ParticleCollectorC2Em0
_ZN7crpropa17ParticleCollectorC2Emb0
_ZN7crpropa17ParticleCollectorC2Embb0
_ZN7crpropa17ParticleCollectorC2Ev14
_ZN7crpropa17ParticleCollectorD0Ev8
_ZN7crpropa17ParticleCollectorD2Ev14
_ZNK7crpropa17ParticleCollector12getContainerEv2
_ZNK7crpropa17ParticleCollector13getTrajectoryENS_7ref_ptrINS_10ModuleListEEEmNS1_INS_6ModuleEEE1
_ZNK7crpropa17ParticleCollector13getTrajectoryEPNS_10ModuleListEmPNS_6ModuleE1
_ZNK7crpropa17ParticleCollector14getDescriptionB5cxx11Ev0
_ZNK7crpropa17ParticleCollector3endEv0
_ZNK7crpropa17ParticleCollector4dumpERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa17ParticleCollector4sizeEv6
_ZNK7crpropa17ParticleCollector5beginEv0
_ZNK7crpropa17ParticleCollector7processENS_7ref_ptrINS_9CandidateEEE30
_ZNK7crpropa17ParticleCollector7processEPNS_9CandidateE3206
_ZNK7crpropa17ParticleCollector8getCloneEv0
_ZNK7crpropa17ParticleCollector9reprocessEPNS_6ModuleE2
_ZNK7crpropa17ParticleCollectorixEm8
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html b/doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html deleted file mode 100644 index b881f5f25..000000000 --- a/doc/coverageReport/src/module/ParticleCollector.cpp.gcov.html +++ /dev/null @@ -1,194 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/ParticleCollector.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - ParticleCollector.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:547275.0 %
Date:2024-04-08 14:58:22Functions:172470.8 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/ParticleCollector.h"
-       2             : #include "crpropa/module/TextOutput.h"
-       3             : #include "crpropa/Units.h"
-       4             : 
-       5             : namespace crpropa {
-       6             : 
-       7          14 : ParticleCollector::ParticleCollector() : nBuffer(10e6), clone(false), recursive(false)  {
-       8          14 :         container.reserve(nBuffer); // for 1e6 candidates ~ 500MB of RAM
-       9          14 : }
-      10             : 
-      11           0 : ParticleCollector::ParticleCollector(const std::size_t nBuffer) : clone(false), recursive(false)  {
-      12           0 :         container.reserve(nBuffer);
-      13           0 : }
-      14             : 
-      15           0 : ParticleCollector::ParticleCollector(const std::size_t nBuffer, const bool clone) : recursive(false) {
-      16           0 :         container.reserve(nBuffer);
-      17           0 : }
-      18             : 
-      19           0 : ParticleCollector::ParticleCollector(const std::size_t nBuffer, const bool clone, const bool recursive) {
-      20           0 :         container.reserve(nBuffer);
-      21           0 : }
-      22             : 
-      23        3206 : void ParticleCollector::process(Candidate *c) const {
-      24        6412 : #pragma omp critical
-      25             :         {
-      26        3206 :                 if(clone)
-      27          50 :                         container.push_back(c->clone(recursive));
-      28             :                 else
-      29        6362 :                         container.push_back(c);
-      30             :         }
-      31        3206 : }
-      32             : 
-      33          30 : void ParticleCollector::process(ref_ptr<Candidate> c) const {
-      34          30 :         ParticleCollector::process((Candidate*) c);
-      35          30 : }
-      36             : 
-      37           2 : void ParticleCollector::reprocess(Module *action) const {
-      38          14 :         for (ParticleCollector::iterator itr = container.begin(); itr != container.end(); ++itr){
-      39          12 :                 if (clone)
-      40           0 :                         action->process((*(itr->get())).clone(false));
-      41             :                 else
-      42          12 :                         action->process(itr->get());
-      43             :         }
-      44           2 : }
-      45             : 
-      46           1 : void ParticleCollector::dump(const std::string &filename) const {
-      47           1 :         TextOutput output(filename.c_str(), Output::Everything);
-      48           1 :         reprocess(&output);
-      49           1 :         output.close();
-      50           1 : }
-      51             : 
-      52           1 : void ParticleCollector::load(const std::string &filename){
-      53           1 :         TextOutput::load(filename.c_str(), this);
-      54           1 : }
-      55             : 
-      56          22 : ParticleCollector::~ParticleCollector() {
-      57          14 :         clearContainer();
-      58          22 : }
-      59             : 
-      60           6 : std::size_t ParticleCollector::size() const {
-      61           6 :         return container.size();
-      62             : }
-      63             : 
-      64           8 : ref_ptr<Candidate> ParticleCollector::operator[](const std::size_t i) const {
-      65           8 :         return container[i];
-      66             : }
-      67             : 
-      68          14 : void ParticleCollector::clearContainer() {
-      69          14 :         container.clear();
-      70          14 : }
-      71             : 
-      72           2 : std::vector<ref_ptr<Candidate> >& ParticleCollector::getContainer() const {
-      73           2 :         return container;
-      74             : }
-      75             : 
-      76           2 : void ParticleCollector::setClone(bool b) {
-      77           2 :         clone = b;
-      78           2 : }
-      79             : 
-      80           0 : bool ParticleCollector::getClone() const {
-      81           0 :         return clone;
-      82             : }
-      83             : 
-      84           0 : std::string ParticleCollector::getDescription() const {
-      85           0 :         return "ParticleCollector";
-      86             : }
-      87             : 
-      88           5 : ParticleCollector::iterator ParticleCollector::begin() {
-      89           5 :         return container.begin();
-      90             : }
-      91             : 
-      92           0 : ParticleCollector::const_iterator ParticleCollector::begin() const {
-      93           0 :         return container.begin();
-      94             : }
-      95             : 
-      96          30 : ParticleCollector::iterator ParticleCollector::end() {
-      97          30 :         return container.end();
-      98             : }
-      99             : 
-     100           0 : ParticleCollector::const_iterator ParticleCollector::end() const {
-     101           0 :         return container.end();
-     102             : }
-     103             : 
-     104           1 : void ParticleCollector::getTrajectory(ModuleList* mlist, std::size_t i, Module *output) const {
-     105           1 :         ref_ptr<Candidate> c_tmp = container[i]->clone();
-     106             : 
-     107           1 :         c_tmp->restart();
-     108             : 
-     109           1 :         mlist->add(output);
-     110           1 :         mlist->run(c_tmp);
-     111           1 :         mlist->remove(mlist->size()-1);
-     112           1 : }
-     113             : 
-     114           1 : void ParticleCollector::getTrajectory(ref_ptr<ModuleList> mlist, std::size_t i, ref_ptr<Module> output) const {
-     115           1 :         ParticleCollector::getTrajectory((ModuleList*) mlist, i, (Module*) output);
-     116           1 : }
-     117             : 
-     118             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html b/doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html deleted file mode 100644 index 3a3f0982b..000000000 --- a/doc/coverageReport/src/module/PhotoDisintegration.cpp.func-sort-c.html +++ /dev/null @@ -1,120 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotoDisintegration.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotoDisintegration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:14017580.0 %
Date:2024-04-08 14:58:22Functions:101283.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoDisintegration10lossLengthEidd0
_ZN7crpropa19PhotoDisintegration8setLimitEd0
_ZN7crpropa19PhotoDisintegration14setHavePhotonsEb1
_ZN7crpropa19PhotoDisintegration17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa19PhotoDisintegration17getInteractionTagB5cxx11Ev2
_ZN7crpropa19PhotoDisintegrationC2ENS_7ref_ptrINS_11PhotonFieldEEEbd11
_ZN7crpropa19PhotoDisintegration13initBranchingENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoDisintegration18initPhotonEmissionENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZNK7crpropa19PhotoDisintegration18performInteractionEPNS_9CandidateEi265
_ZNK7crpropa19PhotoDisintegration7processEPNS_9CandidateE16849
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html b/doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html deleted file mode 100644 index 7207f6b5b..000000000 --- a/doc/coverageReport/src/module/PhotoDisintegration.cpp.func.html +++ /dev/null @@ -1,120 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotoDisintegration.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotoDisintegration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:14017580.0 %
Date:2024-04-08 14:58:22Functions:101283.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoDisintegration10lossLengthEidd0
_ZN7crpropa19PhotoDisintegration13initBranchingENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration14setHavePhotonsEb1
_ZN7crpropa19PhotoDisintegration14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoDisintegration17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa19PhotoDisintegration18initPhotonEmissionENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoDisintegration8setLimitEd0
_ZN7crpropa19PhotoDisintegrationC2ENS_7ref_ptrINS_11PhotonFieldEEEbd11
_ZNK7crpropa19PhotoDisintegration17getInteractionTagB5cxx11Ev2
_ZNK7crpropa19PhotoDisintegration18performInteractionEPNS_9CandidateEi265
_ZNK7crpropa19PhotoDisintegration7processEPNS_9CandidateE16849
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html b/doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html deleted file mode 100644 index 9d6164c97..000000000 --- a/doc/coverageReport/src/module/PhotoDisintegration.cpp.gcov.html +++ /dev/null @@ -1,406 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotoDisintegration.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotoDisintegration.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:14017580.0 %
Date:2024-04-08 14:58:22Functions:101283.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/PhotoDisintegration.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/ParticleMass.h"
-       5             : #include "crpropa/Random.h"
-       6             : #include "kiss/logger.h"
-       7             : 
-       8             : #include <cmath>
-       9             : #include <limits>
-      10             : #include <sstream>
-      11             : #include <fstream>
-      12             : #include <stdexcept>
-      13             : 
-      14             : namespace crpropa {
-      15             : 
-      16             : const double PhotoDisintegration::lgmin = 6;  // minimum log10(Lorentz-factor)
-      17             : const double PhotoDisintegration::lgmax = 14; // maximum log10(Lorentz-factor)
-      18             : const size_t PhotoDisintegration::nlg = 201;  // number of Lorentz-factor steps
-      19             : 
-      20          11 : PhotoDisintegration::PhotoDisintegration(ref_ptr<PhotonField> f, bool havePhotons, double limit) {
-      21          11 :         setPhotonField(f);
-      22          11 :         this->havePhotons = havePhotons;
-      23          11 :         this->limit = limit;
-      24          11 : }
-      25             : 
-      26          22 : void PhotoDisintegration::setPhotonField(ref_ptr<PhotonField> photonField) {
-      27          22 :         this->photonField = photonField;
-      28          22 :         std::string fname = photonField->getFieldName();
-      29          22 :         setDescription("PhotoDisintegration: " + fname);
-      30          66 :         initRate(getDataPath("Photodisintegration/rate_" + fname + ".txt"));
-      31          66 :         initBranching(getDataPath("Photodisintegration/branching_" + fname + ".txt"));
-      32          66 :         initPhotonEmission(getDataPath("Photodisintegration/photon_emission_" + fname.substr(0,3) + ".txt"));
-      33          22 : }
-      34             : 
-      35           1 : void PhotoDisintegration::setHavePhotons(bool havePhotons) {
-      36           1 :         this->havePhotons = havePhotons;
-      37           1 : }
-      38             : 
-      39           0 : void PhotoDisintegration::setLimit(double limit) {
-      40           0 :         this->limit = limit;
-      41           0 : }
-      42             : 
-      43          22 : void PhotoDisintegration::initRate(std::string filename) {
-      44          22 :         std::ifstream infile(filename.c_str());
-      45          22 :         if (not infile.good())
-      46           0 :                 throw std::runtime_error("PhotoDisintegration: could not open file " + filename);
-      47             : 
-      48             :         // clear previously loaded interaction rates
-      49          22 :         pdRate.clear();
-      50          22 :         pdRate.resize(27 * 31);
-      51             : 
-      52             :         std::string line;
-      53        4158 :         while (std::getline(infile, line)) {
-      54        4136 :                 if (line[0] == '#')
-      55          66 :                         continue;
-      56        4070 :                 std::stringstream lineStream(line);
-      57             : 
-      58             :                 int Z, N;
-      59        4070 :                 lineStream >> Z;
-      60        4070 :                 lineStream >> N;
-      61             : 
-      62             :                 double r;
-      63      822140 :                 for (size_t i = 0; i < nlg; i++) {
-      64             :                         lineStream >> r;
-      65      818070 :                         pdRate[Z * 31 + N].push_back(r / Mpc);
-      66             :                 }
-      67        4070 :         }
-      68          22 :         infile.close();
-      69          22 : }
-      70             : 
-      71          22 : void PhotoDisintegration::initBranching(std::string filename) {
-      72          22 :         std::ifstream infile(filename.c_str());
-      73          22 :         if (not infile.good())
-      74           0 :                 throw std::runtime_error("PhotoDisintegration: could not open file " + filename);
-      75             : 
-      76             :         // clear previously loaded interaction rates
-      77          22 :         pdBranch.clear();
-      78          22 :         pdBranch.resize(27 * 31);
-      79             : 
-      80             :         std::string line;
-      81       48532 :         while (std::getline(infile, line)) {
-      82       48510 :                 if (line[0] == '#')
-      83          66 :                         continue;
-      84             : 
-      85       48444 :                 std::stringstream lineStream(line);
-      86             : 
-      87             :                 int Z, N;
-      88       48444 :                 lineStream >> Z;
-      89       48444 :                 lineStream >> N;
-      90             : 
-      91             :                 Branch branch;
-      92       48444 :                 lineStream >> branch.channel;
-      93             : 
-      94             :                 double r;
-      95     9785688 :                 for (size_t i = 0; i < nlg; i++) {
-      96             :                         lineStream >> r;
-      97     9737244 :                         branch.branchingRatio.push_back(r);
-      98             :                 }
-      99             : 
-     100       48444 :                 pdBranch[Z * 31 + N].push_back(branch);
-     101       48444 :         }
-     102             : 
-     103          22 :         infile.close();
-     104          22 : }
-     105             : 
-     106          22 : void PhotoDisintegration::initPhotonEmission(std::string filename) {
-     107          22 :         std::ifstream infile(filename.c_str());
-     108          22 :         if (not infile.good())
-     109           0 :                 throw std::runtime_error("PhotoDisintegration: could not open file " + filename);
-     110             : 
-     111             :         // clear previously loaded emission probabilities
-     112          22 :         pdPhoton.clear();
-     113             : 
-     114             :         std::string line;
-     115      209154 :         while (std::getline(infile, line)) {
-     116      209132 :                 if (line[0] == '#')
-     117          66 :                         continue;
-     118             : 
-     119      209066 :                 std::stringstream lineStream(line);
-     120             : 
-     121             :                 int Z, N, Zd, Nd;
-     122      209066 :                 lineStream >> Z;
-     123      209066 :                 lineStream >> N;
-     124      209066 :                 lineStream >> Zd;
-     125      209066 :                 lineStream >> Nd;
-     126             : 
-     127             :                 PhotonEmission em;
-     128             :                 lineStream >> em.energy;
-     129      209066 :                 em.energy *= eV;
-     130             : 
-     131             :                 double r;
-     132    42231332 :                 for (size_t i = 0; i < nlg; i++) {
-     133             :                         lineStream >> r;
-     134    42022266 :                         em.emissionProbability.push_back(r);
-     135             :                 }
-     136             : 
-     137      209066 :                 int key = Z * 1000000 + N * 10000 + Zd * 100 + Nd;
-     138      209066 :                 if (pdPhoton.find(key) == pdPhoton.end()) {
-     139             :                         std::vector<PhotonEmission> emissions;
-     140       41096 :                         pdPhoton[key] = emissions;
-     141       41096 :                 }
-     142      209066 :                 pdPhoton[key].push_back(em);
-     143      209066 :         }
-     144             : 
-     145          22 :         infile.close();
-     146          22 : }
-     147             : 
-     148       16849 : void PhotoDisintegration::process(Candidate *candidate) const {
-     149             :         // execute the loop at least once for limiting the next step
-     150       16849 :         double step = candidate->getCurrentStep();
-     151             :         do {
-     152             :                 // check if nucleus
-     153       17112 :                 int id = candidate->current.getId();
-     154       17112 :                 if (not isNucleus(id))
-     155             :                         return;
-     156             : 
-     157       17111 :                 int A = massNumber(id);
-     158       17111 :                 int Z = chargeNumber(id);
-     159       17111 :                 int N = A - Z;
-     160       17111 :                 size_t idx = Z * 31 + N;
-     161             : 
-     162             :                 // check if disintegration data available
-     163       17111 :                 if ((Z > 26) or (N > 30))
-     164             :                         return;
-     165       17111 :                 if (pdRate[idx].size() == 0)
-     166             :                         return;
-     167             : 
-     168             :                 // check if in tabulated energy range
-     169        1517 :                 double z = candidate->getRedshift();
-     170        1517 :                 double lg = log10(candidate->current.getLorentzFactor() * (1 + z));
-     171        1517 :                 if ((lg <= lgmin) or (lg >= lgmax))
-     172             :                         return;
-     173             : 
-     174        1517 :                 double rate = interpolateEquidistant(lg, lgmin, lgmax, pdRate[idx]);
-     175        1517 :                 rate *= pow_integer<2>(1 + z) * photonField->getRedshiftScaling(z); // cosmological scaling, rate per comoving distance
-     176             : 
-     177             :                 // check if interaction occurs in this step
-     178             :                 // otherwise limit next step to a fraction of the mean free path
-     179        1517 :                 Random &random = Random::instance();
-     180        1517 :                 double randDist = -log(random.rand()) / rate;
-     181        1517 :                 if (step < randDist) {
-     182        1254 :                         candidate->limitNextStep(limit / rate);
-     183        1254 :                         return;
-     184             :                 }
-     185             : 
-     186             :                 // select channel and interact
-     187             :                 const std::vector<Branch> &branches = pdBranch[idx];
-     188         263 :                 double cmp = random.rand();
-     189         263 :                 int l = round((lg - lgmin) / (lgmax - lgmin) * (nlg - 1)); // index of closest tabulation point
-     190             :                 size_t i = 0;
-     191        2133 :                 while ((i < branches.size()) and (cmp > 0)) {
-     192        1870 :                         cmp -= branches[i].branchingRatio[l];
-     193        1870 :                         i++;
-     194             :                 }
-     195         263 :                 performInteraction(candidate, branches[i-1].channel);
-     196             : 
-     197             :                 // repeat with remaining step
-     198         263 :                 step -= randDist;
-     199         263 :         } while (step > 0);
-     200             : }
-     201             : 
-     202         265 : void PhotoDisintegration::performInteraction(Candidate *candidate, int channel) const {
-     203         265 :         KISS_LOG_DEBUG << "Photodisintegration::performInteraction. Channel " <<  channel << " on candidate " << candidate->getDescription(); 
-     204             :         // parse disintegration channel
-     205             :         int nNeutron = digit(channel, 100000);
-     206             :         int nProton = digit(channel, 10000);
-     207             :         int nH2 = digit(channel, 1000);
-     208             :         int nH3 = digit(channel, 100);
-     209             :         int nHe3 = digit(channel, 10);
-     210             :         int nHe4 = digit(channel, 1);
-     211             : 
-     212         265 :         int dA = -nNeutron - nProton - 2 * nH2 - 3 * nH3 - 3 * nHe3 - 4 * nHe4;
-     213         265 :         int dZ = -nProton - nH2 - nH3 - 2 * nHe3 - 2 * nHe4;
-     214             : 
-     215         265 :         int id = candidate->current.getId();
-     216         265 :         int A = massNumber(id);
-     217         265 :         int Z = chargeNumber(id);
-     218         265 :         double EpA = candidate->current.getEnergy() / A;
-     219             : 
-     220             :         // create secondaries
-     221         265 :         Random &random = Random::instance();
-     222         265 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     223             :         try
-     224             :         {
-     225         458 :                 for (size_t i = 0; i < nNeutron; i++)
-     226         193 :                         candidate->addSecondary(nucleusId(1, 0), EpA, pos, 1., interactionTag);
-     227         379 :                 for (size_t i = 0; i < nProton; i++)
-     228         114 :                         candidate->addSecondary(nucleusId(1, 1), EpA, pos, 1., interactionTag);
-     229         265 :                 for (size_t i = 0; i < nH2; i++)
-     230           0 :                         candidate->addSecondary(nucleusId(2, 1), EpA * 2, pos, 1., interactionTag);
-     231         267 :                 for (size_t i = 0; i < nH3; i++)
-     232           2 :                         candidate->addSecondary(nucleusId(3, 1), EpA * 3, pos, 1., interactionTag);
-     233         265 :                 for (size_t i = 0; i < nHe3; i++)
-     234           0 :                         candidate->addSecondary(nucleusId(3, 2), EpA * 3, pos, 1., interactionTag);
-     235         309 :                 for (size_t i = 0; i < nHe4; i++)
-     236          44 :                         candidate->addSecondary(nucleusId(4, 2), EpA * 4, pos, 1., interactionTag);
-     237             : 
-     238             : 
-     239             :         // update particle
-     240             :           candidate->created = candidate->current;
-     241         265 :                 candidate->current.setId(nucleusId(A + dA, Z + dZ));
-     242         265 :                 candidate->current.setEnergy(EpA * (A + dA));
-     243             :         }
-     244           0 :         catch (std::runtime_error &e)
-     245             :         {
-     246           0 :                 KISS_LOG_ERROR << "Something went wrong in the PhotoDisentigration\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
-     247           0 :                 throw;
-     248           0 :         }
-     249             : 
-     250         265 :         if (not havePhotons)
-     251             :                 return;
-     252             : 
-     253             :         // create photons
-     254          32 :         double z = candidate->getRedshift();
-     255          32 :         double lg = log10(candidate->current.getLorentzFactor() * (1 + z));
-     256          32 :         double lf = candidate->current.getLorentzFactor();
-     257             : 
-     258          32 :         int l = round((lg - lgmin) / (lgmax - lgmin) * (nlg - 1));  // index of closest tabulation point
-     259          32 :         int key = Z*1e6 + (A-Z)*1e4 + (Z+dZ)*1e2 + (A+dA) - (Z+dZ);
-     260             : 
-     261         227 :         for (int i = 0; i < pdPhoton[key].size(); i++) {
-     262             :                 // check for random emission
-     263         195 :                 if (random.rand() > pdPhoton[key][i].emissionProbability[l])
-     264         162 :                         continue;
-     265             : 
-     266             :                 // boost to lab frame
-     267          33 :                 double cosTheta = 2 * random.rand() - 1;
-     268          33 :                 double E = pdPhoton[key][i].energy * lf * (1 - cosTheta);
-     269          33 :                 candidate->addSecondary(22, E, pos, 1., interactionTag);
-     270             :         }
-     271             : }
-     272             : 
-     273           0 : double PhotoDisintegration::lossLength(int id, double gamma, double z) {
-     274             :         // check if nucleus
-     275           0 :         if (not (isNucleus(id)))
-     276             :                 return std::numeric_limits<double>::max();
-     277             : 
-     278           0 :         int A = massNumber(id);
-     279           0 :         int Z = chargeNumber(id);
-     280           0 :         int N = A - Z;
-     281           0 :         size_t idx = Z * 31 + N;
-     282             : 
-     283             :         // check if disintegration data available
-     284           0 :         if ((Z > 26) or (N > 30))
-     285             :                 return std::numeric_limits<double>::max();
-     286             :         const std::vector<double> &rate = pdRate[idx];
-     287           0 :         if (rate.size() == 0)
-     288             :                 return std::numeric_limits<double>::max();
-     289             : 
-     290             :         // check if in tabulated energy range
-     291           0 :         double lg = log10(gamma * (1 + z));
-     292           0 :         if ((lg <= lgmin) or (lg >= lgmax))
-     293             :                 return std::numeric_limits<double>::max();
-     294             : 
-     295             :         // total interaction rate
-     296           0 :         double lossRate = interpolateEquidistant(lg, lgmin, lgmax, rate);
-     297             : 
-     298             :         // comological scaling, rate per physical distance
-     299           0 :         lossRate *= pow_integer<3>(1 + z) * photonField->getRedshiftScaling(z);
-     300             : 
-     301             :         // average number of nucleons lost for all disintegration channels
-     302             :         double avg_dA = 0;
-     303             :         const std::vector<Branch> &branches = pdBranch[idx];
-     304           0 :         for (size_t i = 0; i < branches.size(); i++) {
-     305           0 :                 int channel = branches[i].channel;
-     306             :                 int dA = 0;
-     307             :                 dA += 1 * digit(channel, 100000);
-     308           0 :                 dA += 1 * digit(channel, 10000);
-     309           0 :                 dA += 2 * digit(channel, 1000);
-     310           0 :                 dA += 3 * digit(channel, 100);
-     311           0 :                 dA += 3 * digit(channel, 10);
-     312           0 :                 dA += 4 * digit(channel, 1);
-     313             : 
-     314           0 :                 double br = interpolateEquidistant(lg, lgmin, lgmax, branches[i].branchingRatio);
-     315           0 :                 avg_dA += br * dA;
-     316             :         }
-     317             : 
-     318           0 :         lossRate *= avg_dA / A;
-     319           0 :         return 1 / lossRate;
-     320             : }
-     321             : 
-     322           1 : void PhotoDisintegration::setInteractionTag(std::string tag) {
-     323           1 :         interactionTag = tag;
-     324           1 : }
-     325             : 
-     326           2 : std::string PhotoDisintegration::getInteractionTag() const {
-     327           2 :         return interactionTag;
-     328             : }
-     329             : 
-     330             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html b/doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html deleted file mode 100644 index 7b6272449..000000000 --- a/doc/coverageReport/src/module/PhotoPionProduction.cpp.func-sort-c.html +++ /dev/null @@ -1,232 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotoPionProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotoPionProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:24638763.6 %
Date:2024-04-08 14:58:22Functions:244060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoPionProduction10lossLengthEidd0
_ZN7crpropa19PhotoPionProduction12setSampleLogEb0
_ZN7crpropa19PhotoPionProduction16setHaveElectronsEb0
_ZN7crpropa19PhotoPionProduction16setHaveNeutrinosEb0
_ZN7crpropa19PhotoPionProduction19setCorrectionFactorEd0
_ZN7crpropa19PhotoPionProduction19setHaveAntiNucleonsEb0
_ZN7crpropa19PhotoPionProduction25setHaveRedshiftDependenceEb0
_ZN7crpropa19PhotoPionProduction8setLimitEd0
_ZNK7crpropa19PhotoPionProduction11sophiaEventEbdd0
_ZNK7crpropa19PhotoPionProduction12getSampleLogEv0
_ZNK7crpropa19PhotoPionProduction14getHavePhotonsEv0
_ZNK7crpropa19PhotoPionProduction16getHaveElectronsEv0
_ZNK7crpropa19PhotoPionProduction16getHaveNeutrinosEv0
_ZNK7crpropa19PhotoPionProduction19getHaveAntiNucleonsEv0
_ZNK7crpropa19PhotoPionProduction25getHaveRedshiftDependenceEv0
_ZNK7crpropa19PhotoPionProduction8getLimitEv0
_ZN7crpropa19PhotoPionProduction14setHavePhotonsEb1
_ZN7crpropa19PhotoPionProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZNK7crpropa19PhotoPionProduction14getPhotonFieldEv1
_ZNK7crpropa19PhotoPionProduction19getCorrectionFactorEv1
_ZNK7crpropa19PhotoPionProduction17getInteractionTagB5cxx11Ev2
_ZN7crpropa19PhotoPionProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbbbbdb11
_ZN7crpropa19PhotoPionProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoPionProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZNK7crpropa19PhotoPionProduction17epsMinInteractionEbd28
_ZNK7crpropa19PhotoPionProduction18performInteractionEPNS_9CandidateEb28
_ZNK7crpropa19PhotoPionProduction9sampleEpsEbdd28
_ZNK7crpropa19PhotoPionProduction10probEpsMaxEbdddd29
_ZNK7crpropa19PhotoPionProduction7probEpsEdbdd10689
_ZNK7crpropa19PhotoPionProduction8momentumEbd10717
_ZNK7crpropa19PhotoPionProduction7processEPNS_9CandidateE15289
_ZNK7crpropa19PhotoPionProduction10nucleonMFPEddb16206
_ZNK7crpropa19PhotoPionProduction18nucleiModificationEii16206
_ZNK7crpropa19PhotoPionProduction11crossectionEdb170560
_ZNK7crpropa19PhotoPionProduction6functsEdb170560
_ZNK7crpropa19PhotoPionProduction4sMinEv191909
_ZNK7crpropa19PhotoPionProduction2PlEdddd320502
_ZNK7crpropa19PhotoPionProduction11breitwignerEddddb1442259
_ZNK7crpropa19PhotoPionProduction2EfEddd1612819
_ZNK7crpropa19PhotoPionProduction4massEb1815502
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html b/doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html deleted file mode 100644 index 4e52c0c59..000000000 --- a/doc/coverageReport/src/module/PhotoPionProduction.cpp.func.html +++ /dev/null @@ -1,232 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotoPionProduction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotoPionProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:24638763.6 %
Date:2024-04-08 14:58:22Functions:244060.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa19PhotoPionProduction10lossLengthEidd0
_ZN7crpropa19PhotoPionProduction12setSampleLogEb0
_ZN7crpropa19PhotoPionProduction14setHavePhotonsEb1
_ZN7crpropa19PhotoPionProduction14setPhotonFieldENS_7ref_ptrINS_11PhotonFieldEEE22
_ZN7crpropa19PhotoPionProduction16setHaveElectronsEb0
_ZN7crpropa19PhotoPionProduction16setHaveNeutrinosEb0
_ZN7crpropa19PhotoPionProduction17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa19PhotoPionProduction19setCorrectionFactorEd0
_ZN7crpropa19PhotoPionProduction19setHaveAntiNucleonsEb0
_ZN7crpropa19PhotoPionProduction25setHaveRedshiftDependenceEb0
_ZN7crpropa19PhotoPionProduction8initRateENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE22
_ZN7crpropa19PhotoPionProduction8setLimitEd0
_ZN7crpropa19PhotoPionProductionC2ENS_7ref_ptrINS_11PhotonFieldEEEbbbbdb11
_ZNK7crpropa19PhotoPionProduction10nucleonMFPEddb16206
_ZNK7crpropa19PhotoPionProduction10probEpsMaxEbdddd29
_ZNK7crpropa19PhotoPionProduction11breitwignerEddddb1442259
_ZNK7crpropa19PhotoPionProduction11crossectionEdb170560
_ZNK7crpropa19PhotoPionProduction11sophiaEventEbdd0
_ZNK7crpropa19PhotoPionProduction12getSampleLogEv0
_ZNK7crpropa19PhotoPionProduction14getHavePhotonsEv0
_ZNK7crpropa19PhotoPionProduction14getPhotonFieldEv1
_ZNK7crpropa19PhotoPionProduction16getHaveElectronsEv0
_ZNK7crpropa19PhotoPionProduction16getHaveNeutrinosEv0
_ZNK7crpropa19PhotoPionProduction17epsMinInteractionEbd28
_ZNK7crpropa19PhotoPionProduction17getInteractionTagB5cxx11Ev2
_ZNK7crpropa19PhotoPionProduction18nucleiModificationEii16206
_ZNK7crpropa19PhotoPionProduction18performInteractionEPNS_9CandidateEb28
_ZNK7crpropa19PhotoPionProduction19getCorrectionFactorEv1
_ZNK7crpropa19PhotoPionProduction19getHaveAntiNucleonsEv0
_ZNK7crpropa19PhotoPionProduction25getHaveRedshiftDependenceEv0
_ZNK7crpropa19PhotoPionProduction2EfEddd1612819
_ZNK7crpropa19PhotoPionProduction2PlEdddd320502
_ZNK7crpropa19PhotoPionProduction4massEb1815502
_ZNK7crpropa19PhotoPionProduction4sMinEv191909
_ZNK7crpropa19PhotoPionProduction6functsEdb170560
_ZNK7crpropa19PhotoPionProduction7probEpsEdbdd10689
_ZNK7crpropa19PhotoPionProduction7processEPNS_9CandidateE15289
_ZNK7crpropa19PhotoPionProduction8getLimitEv0
_ZNK7crpropa19PhotoPionProduction8momentumEbd10717
_ZNK7crpropa19PhotoPionProduction9sampleEpsEbdd28
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html b/doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html deleted file mode 100644 index 5a80e6b6b..000000000 --- a/doc/coverageReport/src/module/PhotoPionProduction.cpp.gcov.html +++ /dev/null @@ -1,758 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotoPionProduction.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotoPionProduction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:24638763.6 %
Date:2024-04-08 14:58:22Functions:244060.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/PhotoPionProduction.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/Random.h"
-       5             : 
-       6             : #include "kiss/convert.h"
-       7             : #include "kiss/logger.h"
-       8             : #include "sophia.h"
-       9             : 
-      10             : #include <limits>
-      11             : #include <cmath>
-      12             : #include <sstream>
-      13             : #include <fstream>
-      14             : #include <stdexcept>
-      15             : 
-      16             : namespace crpropa {
-      17             : 
-      18          11 : PhotoPionProduction::PhotoPionProduction(ref_ptr<PhotonField> field, bool photons, bool neutrinos, bool electrons, bool antiNucleons, double l, bool redshift) {
-      19          11 :         havePhotons = photons;
-      20          11 :         haveNeutrinos = neutrinos;
-      21          11 :         haveElectrons = electrons;
-      22          11 :         haveAntiNucleons = antiNucleons;
-      23          11 :         haveRedshiftDependence = redshift;
-      24          11 :         limit = l;
-      25          11 :         setPhotonField(field);
-      26          11 : }
-      27             : 
-      28          22 : void PhotoPionProduction::setPhotonField(ref_ptr<PhotonField> field) {
-      29          22 :         photonField = field;
-      30          22 :         std::string fname = photonField->getFieldName();
-      31          22 :         if (haveRedshiftDependence) {
-      32           0 :                 if (photonField->hasRedshiftDependence() == false){
-      33           0 :                         std::cout << "PhotoPionProduction: tabulated redshift dependence not needed for " + fname + ", switching off" << std::endl;
-      34           0 :                         haveRedshiftDependence = false;
-      35             :                 }
-      36             :                 else {
-      37           0 :                         KISS_LOG_WARNING << "PhotoPionProduction: You are using the 2-dimensional tabulated redshift evolution, which is not available for other interactions. To be consistent across all interactions you may deactivate this <setHaveRedshiftDependence(False)>.";
-      38             :                 }
-      39             :         }
-      40             :         
-      41          22 :         setDescription("PhotoPionProduction: " + fname);
-      42          22 :         if (haveRedshiftDependence){
-      43           0 :                 initRate(getDataPath("PhotoPionProduction/rate_" + fname.replace(0, 3, "IRBz") + ".txt"));
-      44             :         }
-      45             :         else
-      46          66 :                 initRate(getDataPath("PhotoPionProduction/rate_" + fname + ".txt"));
-      47          22 : }
-      48             : 
-      49           1 : void PhotoPionProduction::setHavePhotons(bool b) {
-      50           1 :         havePhotons = b;
-      51           1 : }
-      52             :         
-      53           0 : void PhotoPionProduction::setHaveElectrons(bool b) {
-      54           0 :         haveElectrons = b;
-      55           0 : }
-      56             : 
-      57           0 : void PhotoPionProduction::setHaveNeutrinos(bool b) {
-      58           0 :         haveNeutrinos = b;
-      59           0 : }
-      60             : 
-      61           0 : void PhotoPionProduction::setHaveAntiNucleons(bool b) {
-      62           0 :         haveAntiNucleons = b;
-      63           0 : }
-      64             : 
-      65           0 : void PhotoPionProduction::setHaveRedshiftDependence(bool b) {
-      66           0 :         haveRedshiftDependence = b;
-      67           0 :         setPhotonField(photonField);
-      68           0 : }
-      69             : 
-      70           0 : void PhotoPionProduction::setLimit(double l) {
-      71           0 :         limit = l;
-      72           0 : }
-      73             : 
-      74          22 : void PhotoPionProduction::initRate(std::string filename) {
-      75             :         // clear previously loaded tables
-      76          22 :         tabLorentz.clear();
-      77          22 :         tabRedshifts.clear();
-      78          22 :         tabProtonRate.clear();
-      79          22 :         tabNeutronRate.clear();
-      80             : 
-      81          22 :         std::ifstream infile(filename.c_str());
-      82          22 :         if (!infile.good())
-      83           0 :                 throw std::runtime_error("PhotoPionProduction: could not open file " + filename);
-      84             : 
-      85          22 :         if (haveRedshiftDependence) {
-      86             :                 double zOld = -1, aOld = -1;
-      87           0 :                 while (infile.good()) {
-      88           0 :                         if (infile.peek() == '#') {
-      89           0 :                                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-      90           0 :                                 continue;
-      91             :                         }
-      92             :                         double z, a, b, c;
-      93             :                         infile >> z >> a >> b >> c;
-      94           0 :                         if (!infile)
-      95             :                                 break;
-      96           0 :                         if (z > zOld) {
-      97           0 :                                 tabRedshifts.push_back(z);
-      98           0 :                                 zOld = z;
-      99             :                         }
-     100           0 :                         if (a > aOld) {
-     101           0 :                                 tabLorentz.push_back(pow(10, a));
-     102           0 :                                 aOld = a;
-     103             :                         }
-     104           0 :                         tabProtonRate.push_back(b / Mpc);
-     105           0 :                         tabNeutronRate.push_back(c / Mpc);
-     106             :                 }
-     107             :         } else {
-     108        5610 :                 while (infile.good()) {
-     109        5610 :                         if (infile.peek() == '#') {
-     110          66 :                                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-     111          66 :                                 continue;
-     112             :                         }
-     113             :                         double a, b, c;
-     114             :                         infile >> a >> b >> c;
-     115        5544 :                         if (!infile)
-     116             :                                 break;
-     117        5522 :                         tabLorentz.push_back(pow(10, a));
-     118        5522 :                         tabProtonRate.push_back(b / Mpc);
-     119        5522 :                         tabNeutronRate.push_back(c / Mpc);
-     120             :                 }
-     121             :         }
-     122             : 
-     123          22 :         infile.close();
-     124          22 : }
-     125             : 
-     126       16206 : double PhotoPionProduction::nucleonMFP(double gamma, double z, bool onProton) const {
-     127       16206 :         const std::vector<double> &tabRate = (onProton)? tabProtonRate : tabNeutronRate;
-     128             : 
-     129             :         // scale nucleus energy instead of background photon energy
-     130       16206 :         gamma *= (1 + z);
-     131       16206 :         if (gamma < tabLorentz.front() or (gamma > tabLorentz.back()))
-     132             :                 return std::numeric_limits<double>::max();
-     133             : 
-     134             :         double rate;
-     135       16206 :         if (haveRedshiftDependence)
-     136           0 :                 rate = interpolate2d(z, gamma, tabRedshifts, tabLorentz, tabRate);
-     137             :         else
-     138       16206 :                 rate = interpolate(gamma, tabLorentz, tabRate) * photonField->getRedshiftScaling(z);
-     139             : 
-     140             :         // cosmological scaling
-     141       16206 :         rate *= pow_integer<2>(1 + z);
-     142             : 
-     143       16206 :         return 1. / rate;
-     144             : }
-     145             : 
-     146       16206 : double PhotoPionProduction::nucleiModification(int A, int X) const {
-     147       16206 :         if (A == 1)
-     148             :                 return 1.;
-     149        1801 :         if (A <= 8)
-     150         453 :                 return 0.85 * pow(X, 2. / 3.);
-     151        1348 :         return 0.85 * X;
-     152             : }
-     153             : 
-     154       15289 : void PhotoPionProduction::process(Candidate *candidate) const {
-     155       15289 :         double step = candidate->getCurrentStep();
-     156       15289 :         double z = candidate->getRedshift();
-     157             :         // the loop is processed at least once for limiting the next step
-     158             :         do {
-     159             :                 // check if nucleus
-     160       15307 :                 int id = candidate->current.getId();
-     161       15307 :                 if (!isNucleus(id))
-     162             :                         return;
-     163             : 
-     164             :                 // find interaction with minimum random distance
-     165       15306 :                 Random &random = Random::instance();
-     166             :                 double randDistance = std::numeric_limits<double>::max();
-     167             :                 double meanFreePath;
-     168             :                 double totalRate = 0;
-     169             :                 bool onProton = true; // interacting particle: proton or neutron
-     170             : 
-     171       15306 :                 int A = massNumber(id);
-     172       15306 :                 int Z = chargeNumber(id);
-     173       15306 :                 int N = A - Z;
-     174       15306 :                 double gamma = candidate->current.getLorentzFactor();
-     175             : 
-     176             :                 // check for interaction on protons
-     177       15306 :                 if (Z > 0) {
-     178       14758 :                         meanFreePath = nucleonMFP(gamma, z, true) / nucleiModification(A, Z);
-     179       14758 :                         randDistance = -log(random.rand()) * meanFreePath;
-     180       14758 :                         totalRate += 1. / meanFreePath;
-     181             :                 }
-     182             :                 // check for interaction on neutrons
-     183       15306 :                 if (N > 0) {
-     184        1448 :                         meanFreePath = nucleonMFP(gamma, z, false) / nucleiModification(A, N);
-     185        1448 :                         totalRate += 1. / meanFreePath;
-     186        1448 :                         double d = -log(random.rand()) * meanFreePath;
-     187        1448 :                         if (d < randDistance) {
-     188             :                                 randDistance = d;
-     189             :                                 onProton = false;
-     190             :                         }
-     191             :                 }
-     192             : 
-     193             :                 // check if interaction does not happen
-     194       15306 :                 if (step < randDistance) {
-     195       15288 :                         if (totalRate > 0.)
-     196       15288 :                                 candidate->limitNextStep(limit / totalRate);
-     197       15288 :                         return;
-     198             :                 }
-     199             : 
-     200             :                 // interact and repeat with remaining step
-     201          18 :                 performInteraction(candidate, onProton);
-     202          18 :                 step -= randDistance;
-     203          18 :         } while (step > 0);
-     204             : }
-     205             : 
-     206          28 : void PhotoPionProduction::performInteraction(Candidate *candidate, bool onProton) const {
-     207          28 :         int id = candidate->current.getId();
-     208          28 :         int A = massNumber(id);
-     209          28 :         int Z = chargeNumber(id);
-     210          28 :         double E = candidate->current.getEnergy();
-     211          28 :         double EpA = E / A;
-     212          28 :         double z = candidate->getRedshift();
-     213             : 
-     214             :         // SOPHIA simulates interactions only for protons / neutrons.
-     215             :         // For anti-protons / neutrons assume charge symmetry and change all
-     216             :         // interaction products from particle <--> anti-particle (sign)
-     217          28 :         int sign = (id > 0) ? 1 : -1;
-     218             : 
-     219             :         // check if below SOPHIA's energy threshold
-     220          56 :         double E_threshold = (photonField->getFieldName() == "CMB") ? 3.72e18 * eV : 5.83e15 * eV;
-     221          28 :         if (EpA * (1 + z) < E_threshold)
-     222           0 :                 return;
-     223             : 
-     224             :         // SOPHIA - input:
-     225          28 :         int nature = 1 - static_cast<int>(onProton);  // 0=proton, 1=neutron
-     226          28 :         double Ein = EpA / GeV;  // GeV is the SOPHIA standard unit
-     227          28 :         double eps = sampleEps(onProton, EpA, z) / GeV;  // GeV for SOPHIA
-     228             : 
-     229             :         // SOPHIA - output:
-     230             :         double outputEnergy[5][2000];  // [GeV/c, GeV/c, GeV/c, GeV, GeV/c^2]
-     231             :         int outPartID[2000];
-     232             :         int nParticles;
-     233             : 
-     234          56 : #pragma omp critical
-     235             :         {
-     236          28 :                 sophiaevent_(nature, Ein, eps, outputEnergy, outPartID, nParticles);
-     237             :         }
-     238             : 
-     239          28 :         Random &random = Random::instance();
-     240          28 :         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     241             :         std::vector<int> pnType;  // filled with either 13 (proton) or 14 (neutron)
-     242             :         std::vector<double> pnEnergy;  // corresponding energies of proton or neutron
-     243          28 :         if (nParticles == 0)
-     244             :                 return;
-     245         146 :         for (int i = 0; i < nParticles; i++) { // loop over out-going particles
-     246         118 :                 double Eout = outputEnergy[3][i] * GeV; // only the energy is used; could be changed for more detail
-     247         118 :                 int pType = outPartID[i];
-     248         118 :                 switch (pType) {
-     249          28 :                 case 13: // proton
-     250             :                 case 14: // neutron
-     251             :                         // proton and neutron data is taken to determine primary particle in a later step
-     252          28 :                         pnType.push_back(pType);
-     253          28 :                         pnEnergy.push_back(Eout);
-     254             :                         break;
-     255           0 :                 case -13: // anti-proton
-     256             :                 case -14: // anti-neutron
-     257           0 :                         if (haveAntiNucleons)
-     258             :                                 try
-     259             :                                 {
-     260           0 :                                         candidate->addSecondary(-sign * nucleusId(1, 14 + pType), Eout, pos, 1., interactionTag);
-     261             :                                 }
-     262           0 :                                 catch (std::runtime_error &e)
-     263             :                                 {
-     264           0 :                                         KISS_LOG_ERROR<< "Something went wrong in the PhotoPionProduction (anti-nucleon production)\n" << "Something went wrong in the PhotoPionProduction\n"<< "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
-     265           0 :                                         throw;
-     266           0 :                                 }
-     267             :                         break;
-     268          22 :                 case 1: // photon
-     269          22 :                         if (havePhotons)
-     270          14 :                                 candidate->addSecondary(22, Eout, pos, 1., interactionTag);
-     271             :                         break;
-     272          12 :                 case 2: // positron
-     273          12 :                         if (haveElectrons)
-     274           2 :                                 candidate->addSecondary(sign * -11, Eout, pos, 1., interactionTag);
-     275             :                         break;
-     276           5 :                 case 3: // electron
-     277           5 :                         if (haveElectrons)
-     278           2 :                                 candidate->addSecondary(sign * 11, Eout, pos, 1., interactionTag);
-     279             :                         break;
-     280          12 :                 case 15: // nu_e
-     281          12 :                         if (haveNeutrinos)
-     282           2 :                                 candidate->addSecondary(sign * 12, Eout, pos, 1., interactionTag);
-     283             :                         break;
-     284           5 :                 case 16: // anti-nu_e
-     285           5 :                         if (haveNeutrinos)
-     286           2 :                                 candidate->addSecondary(sign * -12, Eout, pos, 1., interactionTag);
-     287             :                         break;
-     288          17 :                 case 17: // nu_mu
-     289          17 :                         if (haveNeutrinos)
-     290           4 :                                 candidate->addSecondary(sign * 14, Eout, pos, 1., interactionTag);
-     291             :                         break;
-     292          17 :                 case 18: // anti-nu_mu
-     293          17 :                         if (haveNeutrinos)
-     294           4 :                                 candidate->addSecondary(sign * -14, Eout, pos, 1., interactionTag);
-     295             :                         break;
-     296           0 :                 default:
-     297           0 :                         throw std::runtime_error("PhotoPionProduction: unexpected particle " + kiss::str(pType));
-     298             :                 }
-     299             :         }
-     300          28 :         double maxEnergy = *std::max_element(pnEnergy.begin(), pnEnergy.end());  // criterion for being declared primary
-     301          56 :         for (int i = 0; i < pnEnergy.size(); ++i) {
-     302          28 :                 if (pnEnergy[i] == maxEnergy) {  // nucleon is primary particle
-     303          28 :                         if (A == 1) {
-     304             :                                 // single interacting nucleon
-     305          25 :                                 candidate->current.setEnergy(pnEnergy[i]);
-     306             :                                 try
-     307             :                                 {
-     308          25 :                                         candidate->current.setId(sign * nucleusId(1, 14 - pnType[i]));
-     309             :                                 }
-     310           0 :                                 catch (std::runtime_error &e)
-     311             :                                 {
-     312           0 :                                         KISS_LOG_ERROR<< "Something went wrong in the PhotoPionProduction (primary particle, A==1)\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
-     313           0 :                                         throw;
-     314           0 :                                 }
-     315             :                         } else {
-     316             :                                 // interacting nucleon is part of nucleus: it is emitted from the nucleus
-     317           3 :                                 candidate->current.setEnergy(E - EpA);
-     318             :                                 try
-     319             :                                 {
-     320           3 :                                         candidate->current.setId(sign * nucleusId(A - 1, Z - int(onProton)));
-     321           3 :                                         candidate->addSecondary(sign * nucleusId(1, 14 - pnType[i]), pnEnergy[i], pos, 1., interactionTag);
-     322             :                                 }
-     323           0 :                                 catch (std::runtime_error &e)
-     324             :                                 {
-     325           0 :                                         KISS_LOG_ERROR<< "Something went wrong in the PhotoPionProduction (primary particle, A!=1)\n" << "Please report this error on https://github.com/CRPropa/CRPropa3/issues including your simulation setup and the following random seed:\n" << Random::instance().getSeed_base64();
-     326           0 :                                         throw;
-     327           0 :                                 }
-     328             :                         }
-     329             :                 } else {  // nucleon is secondary proton or neutron
-     330           0 :                         candidate->addSecondary(sign * nucleusId(1, 14 - pnType[i]), pnEnergy[i], pos, 1., interactionTag);
-     331             :                 }
-     332             :         }
-     333             : }
-     334             : 
-     335           0 : double PhotoPionProduction::lossLength(int id, double gamma, double z) {
-     336           0 :         int A = massNumber(id);
-     337           0 :         int Z = chargeNumber(id);
-     338           0 :         int N = A - Z;
-     339             : 
-     340             :         double lossRate = 0;
-     341           0 :         if (Z > 0)
-     342           0 :                 lossRate += 1 / nucleonMFP(gamma, z, true) * nucleiModification(A, Z);
-     343           0 :         if (N > 0)
-     344           0 :                 lossRate += 1 / nucleonMFP(gamma, z, false) * nucleiModification(A, N);
-     345             : 
-     346             :         // approximate the relative energy loss
-     347             :         // - nucleons keep the fraction of mass to delta-resonance mass
-     348             :         // - nuclei lose the energy 1/A the interacting nucleon is carrying
-     349           0 :         double relativeEnergyLoss = (A == 1) ? 1 - 938. / 1232. : 1. / A;
-     350           0 :         lossRate *= relativeEnergyLoss;
-     351             : 
-     352             :         // scaling factor: interaction rate --> energy loss rate
-     353           0 :         lossRate *= (1 + z);
-     354             : 
-     355           0 :         return 1. / lossRate;
-     356             : }
-     357             : 
-     358           0 : SophiaEventOutput PhotoPionProduction::sophiaEvent(bool onProton, double Ein, double eps) const {
-     359             :         // SOPHIA - input:
-     360           0 :         int nature = 1 - static_cast<int>(onProton);  // 0=proton, 1=neutron
-     361           0 :         Ein /= GeV;  // GeV is the SOPHIA standard unit
-     362           0 :         eps /= GeV;  // GeV for SOPHIA
-     363             : 
-     364             :         // SOPHIA - output:
-     365             :         double outputEnergy[5][2000];  // [Px GeV/c, Py GeV/c, Pz GeV/c, E GeV, m0 GeV/c^2]
-     366             :         int outPartID[2000];
-     367             :         int nParticles;
-     368             : 
-     369           0 :         sophiaevent_(nature, Ein, eps, outputEnergy, outPartID, nParticles);
-     370             : 
-     371             :         // convert SOPHIA IDs to PDG naming convention & create particles
-     372             :         SophiaEventOutput output;
-     373           0 :         output.nParticles = nParticles;
-     374           0 :         for (int i = 0; i < nParticles; ++i) {
-     375           0 :                 int id = 0;
-     376           0 :                 int partType = outPartID[i];
-     377           0 :                 switch (partType) {
-     378           0 :                         case 13:  // proton
-     379             :                         case 14:  // neutron
-     380           0 :                                 id = nucleusId(1, 14 - partType);
-     381           0 :                                 break;
-     382           0 :                         case -13:  // anti-proton
-     383             :                         case -14:  // anti-neutron
-     384           0 :                                 id = -nucleusId(1, 14 + partType);
-     385           0 :                                 break;
-     386           0 :                         case 1:  // photon
-     387           0 :                                 id = 22;
-     388           0 :                                 break;
-     389           0 :                         case 2:  // positron
-     390           0 :                                 id = -11;
-     391           0 :                                 break;
-     392           0 :                         case 3:  // electron
-     393           0 :                                 id = 11;
-     394           0 :                                 break;
-     395           0 :                         case 15:  // nu_e
-     396           0 :                                 id = 12;
-     397           0 :                                 break;
-     398           0 :                         case 16:  // anti-nu_e
-     399           0 :                                 id = -12;
-     400           0 :                                 break;
-     401           0 :                         case 17:  // nu_mu
-     402           0 :                                 id = 14;
-     403           0 :                                 break;
-     404           0 :                         case 18:  // anti-nu_mu
-     405           0 :                                 id = -14;
-     406           0 :                                 break;
-     407           0 :                         default:
-     408           0 :                                 throw std::runtime_error("PhotoPionProduction: unexpected particle " + kiss::str(partType));
-     409             :                 }
-     410           0 :                 output.energy.push_back(outputEnergy[3][i] * GeV); // only the energy is used; could be changed for more detail
-     411           0 :                 output.id.push_back(id);
-     412             :         }
-     413           0 :         return output;
-     414           0 : }
-     415             : 
-     416          28 : double PhotoPionProduction::sampleEps(bool onProton, double E, double z) const {
-     417             :         // sample eps between epsMin ... epsMax
-     418          28 :         double Ein = E / GeV;
-     419          56 :         double epsMin = std::max(photonField -> getMinimumPhotonEnergy(z) / eV, epsMinInteraction(onProton, Ein));
-     420          28 :         double epsMax = photonField -> getMaximumPhotonEnergy(z) / eV;
-     421          28 :         double pEpsMax = probEpsMax(onProton, Ein, z, epsMin, epsMax);
-     422             : 
-     423          28 :         Random &random = Random::instance();
-     424        5034 :         for (int i = 0; i < 1000000; i++) {
-     425        5034 :                 double eps = epsMin + random.rand() * (epsMax - epsMin);
-     426        5034 :                 double pEps = probEps(eps, onProton, Ein, z);
-     427        5034 :                 if (random.rand() * pEpsMax < pEps)
-     428          28 :                         return eps * eV;
-     429             :         }
-     430           0 :         throw std::runtime_error("error: no photon found in sampleEps, please make sure that photon field provides photons for the interaction by adapting the energy range of the tabulated photon field.");
-     431             : }
-     432             : 
-     433          28 : double PhotoPionProduction::epsMinInteraction(bool onProton, double Ein) const {
-     434             :         // labframe energy of least energetic photon where PPP can occur
-     435             :         // this kind-of ties samplingEps to the PPP and SOPHIA
-     436          28 :         const double m = mass(onProton);
-     437          28 :         const double p = momentum(onProton, Ein);
-     438          28 :         double epsMin = 1.e9 * (1.1646 - m * m) / 2. / (Ein + p); // eV
-     439          28 :         return epsMin;
-     440             : }
-     441             : 
-     442          29 : double PhotoPionProduction::probEpsMax(bool onProton, double Ein, double z, double epsMin, double epsMax) const {
-     443             :         // find pEpsMax by testing photon energies (eps) for their interaction
-     444             :         // probabilities (p) in order to find the maximum (max) probability
-     445             :         const int nrSteps = 100;
-     446             :         double pEpsMaxTested = 0.;
-     447             :         double step = 0.;
-     448          29 :         if (sampleLog){
-     449             :                 // sample in logspace with stepsize that is at max Δlog(E/eV) = 0.01 or otherwise dep. on size of energy range with nrSteps+1 steps log. equidis. spaced
-     450          29 :                 step = std::min(0.01, std::log10(epsMax / epsMin) / nrSteps);
-     451             :         } else
-     452           0 :                 step = (epsMax - epsMin) / nrSteps;
-     453             : 
-     454             :         double epsDummy = 0.;
-     455             :         int i = 0;
-     456        5684 :         while (epsDummy < epsMax) {
-     457        5655 :                 if (sampleLog)
-     458        5655 :                         epsDummy = epsMin * pow(10, step * i);
-     459             :                 else
-     460           0 :                         epsDummy = epsMin + step * i;
-     461        5655 :                 double p = probEps(epsDummy, onProton, Ein, z);
-     462        5655 :                 if(p > pEpsMaxTested)
-     463             :                         pEpsMaxTested = p;
-     464        5655 :                 i++;
-     465             :         }
-     466             :         // the following factor corrects for only trying to find the maximum on nrIteration photon energies
-     467             :         // the factor should be determined in convergence tests
-     468          29 :         double pEpsMax = pEpsMaxTested * correctionFactor;
-     469             : 
-     470          29 :         if(pEpsMax == 0) {
-     471           0 :                 KISS_LOG_WARNING << "pEpsMax is 0 in the following configuration: \n"
-     472           0 :                         << "\t" << "onProton: " << onProton << "\n"
-     473           0 :                         << "\t" << "Ein: " << Ein << " [GeV] \n"
-     474           0 :                         << "\t" << "epsRange [eV] " << epsMin << "\t" << epsMax << "\n"
-     475           0 :                         << "\t" << "redshift: " << z << "\n"
-     476           0 :                         << "\t" << "sample Log " << sampleLog << " with step " << step << " [eV] \n";
-     477             :         }
-     478             : 
-     479          29 :         return pEpsMax;
-     480             : }
-     481             : 
-     482       10689 : double PhotoPionProduction::probEps(double eps, bool onProton, double Ein, double z) const {
-     483             :         // probEps returns "probability to encounter a photon of energy eps", given a primary nucleon
-     484             :         // note, probEps does not return a normalized probability [0,...,1]
-     485       10689 :         double photonDensity = photonField->getPhotonDensity(eps * eV, z) * ccm / eps;
-     486       10689 :         if (photonDensity != 0.) {
-     487       10689 :                 const double p = momentum(onProton, Ein);
-     488       10689 :                 const double sMax = mass(onProton) * mass(onProton) + 2. * eps * (Ein + p) / 1.e9;
-     489       10689 :                 if (sMax <= sMin())
-     490             :                         return 0;
-     491       95940 :                 double sIntegr = gaussInt([this, onProton](double s) { return this->functs(s, onProton); }, sMin(), sMax);
-     492       10660 :                 return photonDensity * sIntegr / eps / eps / p / 8. * 1.e18 * 1.e6;
-     493             :         }
-     494             :         return 0;
-     495             : }
-     496             : 
-     497       10717 : double PhotoPionProduction::momentum(bool onProton, double Ein) const {
-     498       10717 :         const double m = mass(onProton);
-     499       10717 :         const double momentumHadron = sqrt(Ein * Ein - m * m);  // GeV/c
-     500       10717 :         return momentumHadron;
-     501             : }
-     502             : 
-     503      170560 : double PhotoPionProduction::crossection(double eps, bool onProton) const {
-     504      170560 :         const double m = mass(onProton);
-     505      170560 :         const double s = m * m + 2. * m * eps;
-     506      170560 :         if (s < sMin())
-     507             :                 return 0.;
-     508             :         double cross_res = 0.;
-     509             :         double cross_dir = 0.;
-     510             :         double cross_dir1 = 0.;
-     511             :         double cross_dir2 = 0.;
-     512             :         double sig_res[9];
-     513             : 
-     514             :         // first half of array: 9x proton resonance data | second half of array 9x neutron resonance data
-     515             :         static const double AMRES[18] = {1.231, 1.440, 1.515, 1.525, 1.675, 1.680, 1.690, 1.895, 1.950, 1.231, 1.440, 1.515, 1.525, 1.675, 1.675, 1.690, 1.895, 1.950};
-     516             :         static const double BGAMMA[18] = {5.6, 0.5, 4.6, 2.5, 1.0, 2.1, 2.0, 0.2, 1.0, 6.1, 0.3, 4.0, 2.5, 0.0, 0.2, 2.0, 0.2, 1.0};
-     517             :         static const double WIDTH[18] = {0.11, 0.35, 0.11, 0.1, 0.16, 0.125, 0.29, 0.35, 0.3, 0.11, 0.35, 0.11, 0.1, 0.16, 0.150, 0.29, 0.35, 0.3};
-     518             :         static const double RATIOJ[18] = {1., 0.5, 1., 0.5, 0.5, 1.5, 1., 1.5, 2., 1., 0.5, 1., 0.5, 0.5, 1.5, 1., 1.5, 2.};
-     519             :         static const double AM2[2] = {0.882792, 0.880351};
-     520             : 
-     521      170560 :         const int idx = onProton? 0 : 9;
-     522             :         double SIG0[9];
-     523     1705600 :         for (int i = 0; i < 9; ++i) {
-     524     1535040 :                 SIG0[i] = 4.893089117 / AM2[int(onProton)] * RATIOJ[i + idx] * BGAMMA[i + idx];
-     525             :         }
-     526      170560 :         if (eps <= 10.) {
-     527      160251 :                 cross_res = breitwigner(SIG0[0], WIDTH[0 + idx], AMRES[0 + idx], eps, onProton) * Ef(eps, 0.152, 0.17);
-     528             :                 sig_res[0] = cross_res;
-     529     1442259 :                 for (int i = 1; i < 9; ++i) {
-     530     1282008 :                         sig_res[i] = breitwigner(SIG0[i], WIDTH[i + idx], AMRES[i + idx], eps, onProton) * Ef(eps, 0.15, 0.38);
-     531     1282008 :                         cross_res += sig_res[i];
-     532             :                 }
-     533             :                 // direct channel
-     534      160251 :                 if ((eps > 0.1) && (eps < 0.6)) {
-     535       66492 :                         cross_dir1 = 92.7 * Pl(eps, 0.152, 0.25, 2.0)  // single pion production
-     536       66492 :                                            + 40. * std::exp(-(eps - 0.29) * (eps - 0.29) / 0.002)
-     537       66492 :                                            - 15. * std::exp(-(eps - 0.37) * (eps - 0.37) / 0.002);
-     538             :                 } else {
-     539       93759 :                         cross_dir1 = 92.7 * Pl(eps, 0.152, 0.25, 2.0);  // single pion production
-     540             :                 }
-     541      160251 :                 cross_dir2 = 37.7 * Pl(eps, 0.4, 0.6, 2.0);  // double pion production
-     542      160251 :                 cross_dir = cross_dir1 + cross_dir2;
-     543             :         }
-     544             :         // fragmentation 2:
-     545      170560 :         double cross_frag2 = onProton? 80.3 : 60.2;
-     546      170560 :         cross_frag2 *= Ef(eps, 0.5, 0.1) * std::pow(s, -0.34);
-     547             :         // multipion production/fragmentation 1 cross section
-     548             :         double cs_multidiff = 0.;
-     549             :         double cs_multi = 0.;
-     550             :         double cross_diffr1 = 0.;
-     551             :         double cross_diffr2 = 0.;
-     552             :         double cross_diffr = 0.;
-     553      170560 :         if (eps > 0.85) {
-     554       92272 :                 double ss1 = (eps - 0.85) / 0.69;
-     555       92272 :                 double ss2 = onProton? 29.3 : 26.4;
-     556       92272 :                 ss2 *= std::pow(s, -0.34) + 59.3 * std::pow(s, 0.095);
-     557       92272 :                 cs_multidiff = (1. - std::exp(-ss1)) * ss2;
-     558       92272 :                 cs_multi = 0.89 * cs_multidiff;
-     559             :                 // diffractive scattering:
-     560             :                 cross_diffr1 = 0.099 * cs_multidiff;
-     561             :                 cross_diffr2 = 0.011 * cs_multidiff;
-     562       92272 :                 cross_diffr = 0.11 * cs_multidiff;
-     563             :                 // **************************************
-     564       92272 :                 ss1 = std::pow(eps - 0.85, 0.75) / 0.64;
-     565       92272 :                 ss2 = 74.1 * std::pow(eps, -0.44) + 62. * std::pow(s, 0.08);
-     566       92272 :                 double cs_tmp = 0.96 * (1. - std::exp(-ss1)) * ss2;
-     567       92272 :                 cross_diffr1 = 0.14 * cs_tmp;
-     568       92272 :                 cross_diffr2 = 0.013 * cs_tmp;
-     569       92272 :                 double cs_delta = cross_frag2 - (cross_diffr1 + cross_diffr2 - cross_diffr);
-     570       92272 :                 if (cs_delta < 0.) {
-     571             :                         cross_frag2 = 0.;
-     572           0 :                         cs_multi += cs_delta;
-     573             :                 } else {
-     574             :                         cross_frag2 = cs_delta;
-     575             :                 }
-     576             :                 cross_diffr = cross_diffr1 + cross_diffr2;
-     577       92272 :                 cs_multidiff = cs_multi + cross_diffr;
-     578             :         // in the original SOPHIA code, here is a switch for the return argument.
-     579             :         // Here, only one case (compare in SOPHIA: NDIR=3) is needed.
-     580             :         }
-     581      170560 :         return cross_res + cross_dir + cs_multidiff + cross_frag2;
-     582             : }
-     583             : 
-     584      320502 : double PhotoPionProduction::Pl(double eps, double epsTh, double epsMax, double alpha) const {
-     585      320502 :         if (epsTh > eps)
-     586             :                 return 0.;
-     587      266687 :         const double a = alpha * epsMax / epsTh;
-     588      266687 :         const double prod1 = std::pow((eps - epsTh) / (epsMax - epsTh), a - alpha);
-     589      266687 :         const double prod2 = std::pow(eps / epsMax, -a);
-     590      266687 :         return prod1 * prod2;
-     591             : }
-     592             : 
-     593     1612819 : double PhotoPionProduction::Ef(double eps, double epsTh, double w) const {
-     594     1612819 :         const double wTh = w + epsTh;
-     595     1612819 :         if (eps <= epsTh) {
-     596             :                 return 0.;
-     597     1551121 :         } else if ((eps > epsTh) && (eps < wTh)) {
-     598      547581 :                 return (eps - epsTh) / w;
-     599     1003540 :         } else if (eps >= wTh) {
-     600             :                 return 1.;
-     601             :         } else {
-     602           0 :                 throw std::runtime_error("error in function Ef");
-     603             :         }
-     604             : }
-     605             : 
-     606     1442259 : double PhotoPionProduction::breitwigner(double sigma0, double gamma, double DMM, double epsPrime, bool onProton) const {
-     607     1442259 :         const double m = mass(onProton);
-     608     1442259 :         const double s = m * m + 2. * m * epsPrime;
-     609     1442259 :         const double gam2s = gamma * gamma * s;
-     610     1442259 :         return sigma0 * (s / epsPrime / epsPrime) * gam2s / ((s - DMM * DMM) * (s - DMM * DMM) + gam2s);
-     611             : }
-     612             : 
-     613      170560 : double PhotoPionProduction::functs(double s, bool onProton) const {
-     614      170560 :         const double m = mass(onProton);
-     615      170560 :         const double factor = s - m * m;
-     616      170560 :         const double epsPrime = factor / 2. / m;
-     617      170560 :         const double sigmaPg = crossection(epsPrime, onProton);
-     618      170560 :         return factor * sigmaPg;
-     619             : }
-     620             : 
-     621     1815502 : double PhotoPionProduction::mass(bool onProton) const {
-     622     1815502 :         const double m =  onProton ? mass_proton : mass_neutron;
-     623     1815502 :         return m / GeV * c_squared;
-     624             : }
-     625             : 
-     626      191909 : double PhotoPionProduction::sMin() const {
-     627      191909 :         return 1.1646; // [GeV^2] head-on collision
-     628             : }
-     629             : 
-     630           0 : void PhotoPionProduction::setSampleLog(bool b) {
-     631           0 :         sampleLog = b;
-     632           0 : }
-     633             : 
-     634           0 : void PhotoPionProduction::setCorrectionFactor(double factor) {
-     635           0 :         correctionFactor = factor;
-     636           0 : }
-     637             : 
-     638           1 : ref_ptr<PhotonField> PhotoPionProduction::getPhotonField() const {
-     639           1 :         return photonField;
-     640             : }
-     641             : 
-     642           0 : bool PhotoPionProduction::getHavePhotons() const {
-     643           0 :         return havePhotons;
-     644             : }
-     645             : 
-     646           0 : bool PhotoPionProduction::getHaveNeutrinos() const {
-     647           0 :         return haveNeutrinos;
-     648             : }
-     649             : 
-     650           0 : bool PhotoPionProduction::getHaveElectrons() const {
-     651           0 :         return haveElectrons;
-     652             : }
-     653             : 
-     654           0 : bool PhotoPionProduction::getHaveAntiNucleons() const {
-     655           0 :         return haveAntiNucleons;
-     656             : }
-     657             : 
-     658           0 : bool PhotoPionProduction::getHaveRedshiftDependence() const {
-     659           0 :         return haveRedshiftDependence;
-     660             : }
-     661             : 
-     662           0 : double PhotoPionProduction::getLimit() const {
-     663           0 :         return limit;
-     664             : }
-     665             : 
-     666           0 : bool PhotoPionProduction::getSampleLog() const {
-     667           0 :         return sampleLog;
-     668             : }
-     669             : 
-     670           1 : double PhotoPionProduction::getCorrectionFactor() const {
-     671           1 :         return correctionFactor;
-     672             : }
-     673             : 
-     674           1 : void PhotoPionProduction::setInteractionTag(std::string tag) {
-     675           1 :         interactionTag = tag;
-     676           1 : }
-     677             : 
-     678           2 : std::string PhotoPionProduction::getInteractionTag() const {
-     679           2 :         return interactionTag;
-     680             : }
-     681             : 
-     682             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html b/doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html deleted file mode 100644 index 20fda8338..000000000 --- a/doc/coverageReport/src/module/PhotonOutput1D.cpp.func-sort-c.html +++ /dev/null @@ -1,108 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotonOutput1D.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotonOutput1D.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0560.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14PhotonOutput1D4gzipEv0
_ZN7crpropa14PhotonOutput1D5closeEv0
_ZN7crpropa14PhotonOutput1DC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa14PhotonOutput1DC2ERSo0
_ZN7crpropa14PhotonOutput1DC2Ev0
_ZN7crpropa14PhotonOutput1DD0Ev0
_ZN7crpropa14PhotonOutput1DD2Ev0
_ZNK7crpropa14PhotonOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa14PhotonOutput1D7processEPNS_9CandidateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html b/doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html deleted file mode 100644 index bb7a35aac..000000000 --- a/doc/coverageReport/src/module/PhotonOutput1D.cpp.func.html +++ /dev/null @@ -1,108 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotonOutput1D.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotonOutput1D.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0560.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14PhotonOutput1D4gzipEv0
_ZN7crpropa14PhotonOutput1D5closeEv0
_ZN7crpropa14PhotonOutput1DC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE0
_ZN7crpropa14PhotonOutput1DC2ERSo0
_ZN7crpropa14PhotonOutput1DC2Ev0
_ZN7crpropa14PhotonOutput1DD0Ev0
_ZN7crpropa14PhotonOutput1DD2Ev0
_ZNK7crpropa14PhotonOutput1D14getDescriptionB5cxx11Ev0
_ZNK7crpropa14PhotonOutput1D7processEPNS_9CandidateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html b/doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html deleted file mode 100644 index 18cb674db..000000000 --- a/doc/coverageReport/src/module/PhotonOutput1D.cpp.gcov.html +++ /dev/null @@ -1,180 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PhotonOutput1D.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PhotonOutput1D.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:0560.0 %
Date:2024-04-08 14:58:22Functions:090.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/PhotonOutput1D.h"
-       2             : #include "crpropa/Units.h"
-       3             : 
-       4             : #include <iostream>
-       5             : #include <sstream>
-       6             : #include <cstdio>
-       7             : #include <stdexcept>
-       8             : 
-       9             : #include "kiss/string.h"
-      10             : #include "kiss/logger.h"
-      11             : 
-      12             : #ifdef CRPROPA_HAVE_ZLIB
-      13             : #include <ozstream.hpp>
-      14             : #endif
-      15             : 
-      16             : using namespace std;
-      17             : 
-      18             : namespace crpropa {
-      19             : 
-      20           0 : PhotonOutput1D::PhotonOutput1D() : out(&std::cout) {
-      21           0 :         KISS_LOG_WARNING << "PhotonOutput1D is deprecated and will be removed in the future. Replace with TextOutput or HDF5Output with features ObserverNucleusVeto + ObserverDetectAll";
-      22           0 : }
-      23             : 
-      24           0 : PhotonOutput1D::PhotonOutput1D(std::ostream &out) : out(&out) {
-      25           0 :         KISS_LOG_WARNING << "PhotonOutput1D is deprecated and will be removed in the future. Replace with TextOutput or HDF5Output with features ObserverNucleusVeto + ObserverDetectAll";
-      26           0 : }
-      27             : 
-      28           0 : PhotonOutput1D::PhotonOutput1D(const std::string &filename) : outfile(
-      29           0 :         filename.c_str(), std::ios::binary), out(&outfile), filename(filename) {
-      30           0 :         KISS_LOG_WARNING << "PhotonOutput1D is deprecated and will be removed in the future. Replace with TextOutput or HDF5Output with features ObserverNucleusVeto + ObserverDetectAll";
-      31           0 :         if (kiss::ends_with(filename, ".gz"))
-      32           0 :                 gzip();
-      33             : 
-      34           0 :         *out << "#ID\tE\tD\tpID\tpE\tiID\tiE\tiD\n";
-      35           0 :         *out << "#\n";
-      36           0 :         *out << "# ID          Id of particle (photon, electron, positron)\n";
-      37           0 :         *out << "# E           Energy [EeV]\n";
-      38           0 :         *out << "# D           Comoving distance to origin [Mpc]\n";
-      39           0 :         *out << "# pID         Id of parent particle\n";
-      40           0 :         *out << "# pE          Energy [EeV] of parent particle\n";
-      41           0 :         *out << "# iID         Id of source particle\n";
-      42           0 :         *out << "# iE          Energy [EeV] of source particle\n";
-      43           0 :         *out << "# iD          Comoving distance [Mpc] to source\n";
-      44           0 :         *out << "#\n";
-      45           0 : }
-      46             : 
-      47           0 : void PhotonOutput1D::process(Candidate *candidate) const {
-      48           0 :         int pid = candidate->current.getId();
-      49           0 :         if ((pid != 22) and (abs(pid) != 11))
-      50           0 :                 return;
-      51             : 
-      52             :         char buffer[1024];
-      53             :         size_t p = 0;
-      54             : 
-      55           0 :         p += std::sprintf(buffer + p, "%4i\t", pid);
-      56           0 :         p += std::sprintf(buffer + p, "%g\t", candidate->current.getEnergy() / EeV);
-      57           0 :         p += std::sprintf(buffer + p, "%8.4f\t", candidate->current.getPosition().getR() / Mpc);
-      58             : 
-      59           0 :         p += std::sprintf(buffer + p, "%10i\t", candidate->created.getId());
-      60           0 :         p += std::sprintf(buffer + p, "%8.4f\t", candidate->created.getEnergy() / EeV);
-      61             : 
-      62           0 :         p += std::sprintf(buffer + p, "%10i\t", candidate->source.getId());
-      63           0 :         p += std::sprintf(buffer + p, "%8.4f\t", candidate->source.getEnergy() / EeV);
-      64           0 :         p += std::sprintf(buffer + p, "%8.4f\n", candidate->source.getPosition().getR() / Mpc);
-      65             : 
-      66           0 : #pragma omp critical
-      67             :         {
-      68           0 :                 out->write(buffer, p);
-      69             :         }
-      70             : 
-      71           0 :         candidate->setActive(false);
-      72             : }
-      73             : 
-      74           0 : void PhotonOutput1D::close() {
-      75             :         #ifdef CRPROPA_HAVE_ZLIB
-      76           0 :                 zstream::ogzstream *zs = dynamic_cast<zstream::ogzstream *>(out);
-      77           0 :                 if (zs) {
-      78           0 :                         zs->close();
-      79           0 :                         delete out;
-      80           0 :                         out = 0;
-      81             :                 }
-      82             :         #endif
-      83           0 :         outfile.flush();
-      84           0 : }
-      85             : 
-      86           0 : string PhotonOutput1D::getDescription() const {
-      87           0 :         std::stringstream s;
-      88             :         s << "PhotonOutput1D: Output file = " << filename;
-      89           0 :         return s.str();
-      90           0 : }
-      91             : 
-      92           0 : PhotonOutput1D::~PhotonOutput1D() {
-      93           0 :         close();
-      94           0 : }
-      95             : 
-      96           0 : void PhotonOutput1D::gzip() {
-      97             :         #ifdef CRPROPA_HAVE_ZLIB
-      98           0 :                 out = new zstream::ogzstream(*out);
-      99             :         #else
-     100             :                 throw std::runtime_error("CRPropa was build without Zlib compression!");
-     101             :         #endif
-     102           0 : }
-     103             : 
-     104             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html b/doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html deleted file mode 100644 index ba52b0e12..000000000 --- a/doc/coverageReport/src/module/PropagationBP.cpp.func-sort-c.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PropagationBP.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PropagationBP.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9210488.5 %
Date:2024-04-08 14:58:22Functions:151693.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13PropagationBP14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationBP12getToleranceEv2
_ZNK7crpropa13PropagationBP14getMinimumStepEv2
_ZNK7crpropa13PropagationBP8getFieldEv2
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEddd5
_ZNK7crpropa13PropagationBP14getMaximumStepEv5
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEd10
_ZN7crpropa13PropagationBP8setFieldENS_7ref_ptrINS_13MagneticFieldEEE16
_ZN7crpropa13PropagationBP12setToleranceEd22
_ZN7crpropa13PropagationBP14setMaximumStepEd22
_ZN7crpropa13PropagationBP14setMinimumStepEd24
_ZNK7crpropa13PropagationBP15errorEstimationENS_7Vector3IdEES2_d28
_ZNK7crpropa13PropagationBP7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEddd28
_ZNK7crpropa13PropagationBP7processEPNS_9CandidateE37
_ZNK7crpropa13PropagationBP2dYENS_7Vector3IdEES2_dddd103
_ZNK7crpropa13PropagationBP18getFieldAtPositionENS_7Vector3IdEEd104
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PropagationBP.cpp.func.html b/doc/coverageReport/src/module/PropagationBP.cpp.func.html deleted file mode 100644 index d14b61859..000000000 --- a/doc/coverageReport/src/module/PropagationBP.cpp.func.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PropagationBP.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PropagationBP.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9210488.5 %
Date:2024-04-08 14:58:22Functions:151693.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13PropagationBP12setToleranceEd22
_ZN7crpropa13PropagationBP14setMaximumStepEd22
_ZN7crpropa13PropagationBP14setMinimumStepEd24
_ZN7crpropa13PropagationBP8setFieldENS_7ref_ptrINS_13MagneticFieldEEE16
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEd10
_ZN7crpropa13PropagationBPC2ENS_7ref_ptrINS_13MagneticFieldEEEddd5
_ZNK7crpropa13PropagationBP12getToleranceEv2
_ZNK7crpropa13PropagationBP14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationBP14getMaximumStepEv5
_ZNK7crpropa13PropagationBP14getMinimumStepEv2
_ZNK7crpropa13PropagationBP15errorEstimationENS_7Vector3IdEES2_d28
_ZNK7crpropa13PropagationBP18getFieldAtPositionENS_7Vector3IdEEd104
_ZNK7crpropa13PropagationBP2dYENS_7Vector3IdEES2_dddd103
_ZNK7crpropa13PropagationBP7processEPNS_9CandidateE37
_ZNK7crpropa13PropagationBP7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEddd28
_ZNK7crpropa13PropagationBP8getFieldEv2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PropagationBP.cpp.gcov.html b/doc/coverageReport/src/module/PropagationBP.cpp.gcov.html deleted file mode 100644 index 8e1869baf..000000000 --- a/doc/coverageReport/src/module/PropagationBP.cpp.gcov.html +++ /dev/null @@ -1,285 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PropagationBP.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PropagationBP.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:9210488.5 %
Date:2024-04-08 14:58:22Functions:151693.8 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/PropagationBP.h"
-       2             : 
-       3             : #include <sstream>
-       4             : #include <stdexcept>
-       5             : #include <vector>
-       6             : 
-       7             : namespace crpropa {
-       8          28 :         void PropagationBP::tryStep(const Y &y, Y &out, Y &error, double h,
-       9             :                         ParticleState &particle, double z, double q, double m) const {
-      10          28 :                 out = dY(y.x, y.u, h, z, q, m);  // 1 step with h
-      11             : 
-      12          28 :                 Y outHelp = dY(y.x, y.u, h/2, z, q, m);  // 2 steps with h/2
-      13          28 :                 Y outCompare = dY(outHelp.x, outHelp.u, h/2, z, q, m);
-      14             : 
-      15          28 :                 error = errorEstimation(out.x , outCompare.x , h);
-      16          28 :         }
-      17             : 
-      18             : 
-      19         103 :         PropagationBP::Y PropagationBP::dY(Vector3d pos, Vector3d dir, double step,
-      20             :                         double z, double q, double m) const {
-      21             :                 // half leap frog step in the position
-      22             :                 pos += dir * step / 2.;
-      23             : 
-      24             :                 // get B field at particle position
-      25         103 :                 Vector3d B = getFieldAtPosition(pos, z);
-      26             : 
-      27             :                 // Boris help vectors
-      28             :                 Vector3d t = B * q / 2 / m * step / c_light;
-      29         103 :                 Vector3d s = t * 2 / (1 + t.dot(t));
-      30             :                 Vector3d v_help;
-      31             : 
-      32             :                 // Boris push
-      33             :                 v_help = dir + dir.cross(t);
-      34             :                 dir = dir + v_help.cross(s);
-      35             : 
-      36             :                 // the other half leap frog step in the position
-      37             :                 pos += dir * step / 2.;
-      38         103 :                 return Y(pos, dir);
-      39             :         }
-      40             : 
-      41             : 
-      42             :         // with a fixed step size
-      43          10 :         PropagationBP::PropagationBP(ref_ptr<MagneticField> field, double fixedStep) :
-      44          10 :                         minStep(0) {
-      45          10 :                 setField(field);
-      46          10 :                 setTolerance(0.42);
-      47          10 :                 setMaximumStep(fixedStep);
-      48          10 :                 setMinimumStep(fixedStep);
-      49          10 :         }
-      50             : 
-      51             : 
-      52             :         // with adaptive step size
-      53           5 :         PropagationBP::PropagationBP(ref_ptr<MagneticField> field, double tolerance, double minStep, double maxStep) :
-      54           5 :                         minStep(0) {
-      55           7 :                 setField(field);
-      56           5 :                 setTolerance(tolerance);
-      57           4 :                 setMaximumStep(maxStep);
-      58           4 :                 setMinimumStep(minStep);
-      59           3 :         }
-      60             : 
-      61             : 
-      62          37 :         void PropagationBP::process(Candidate *candidate) const {
-      63             :                 // save the new previous particle state
-      64          37 :                 ParticleState &current = candidate->current;
-      65             :                 candidate->previous = current;
-      66             : 
-      67          37 :                 Y yIn(current.getPosition(), current.getDirection());
-      68             : 
-      69             :                 // calculate charge of particle
-      70          37 :                 double q = current.getCharge();
-      71          37 :                 double step = maxStep;
-      72             : 
-      73             :                 // rectilinear propagation for neutral particles
-      74          37 :                 if (q == 0) {
-      75           2 :                         step = clip(candidate->getNextStep(), minStep, maxStep);
-      76           1 :                         current.setPosition(yIn.x + yIn.u * step);
-      77           1 :                         candidate->setCurrentStep(step);
-      78           1 :                         candidate->setNextStep(maxStep);
-      79             :                         return;
-      80             :                 }
-      81             : 
-      82             :                 Y yOut, yErr;
-      83          36 :                 double newStep = step;
-      84          36 :                 double z = candidate->getRedshift();
-      85          36 :                 double m = current.getEnergy()/(c_light * c_light);
-      86             : 
-      87             :                 // if minStep is the same as maxStep the adaptive algorithm with its error
-      88             :                 // estimation is not needed and the computation time can be saved:
-      89          36 :                 if (minStep == maxStep){
-      90          19 :                         yOut = dY(yIn.x, yIn.u, step, z, q, m);
-      91             :                 } else {
-      92          17 :                         step = clip(candidate->getNextStep(), minStep, maxStep);
-      93          17 :                         newStep = step;
-      94             :                         double r = 42;  // arbitrary value
-      95             : 
-      96             :                         // try performing step until the target error (tolerance) or the minimum/maximum step size has been reached
-      97             :                         while (true) {
-      98          28 :                                 tryStep(yIn, yOut, yErr, step, current, z, q, m);
-      99          28 :                                 r = yErr.u.getR() / tolerance;  // ratio of absolute direction error and tolerance
-     100          28 :                                 if (r > 1) {  // large direction error relative to tolerance, try to decrease step size
-     101          18 :                                         if (step == minStep)  // already minimum step size
-     102             :                                                 break;
-     103             :                                         else {
-     104          11 :                                                 newStep = step * 0.95 * pow(r, -0.2);
-     105          19 :                                                 newStep = std::max(newStep, 0.1 * step); // limit step size decrease
-     106          11 :                                                 newStep = std::max(newStep, minStep); // limit step size to minStep
-     107             :                                                 step = newStep;
-     108             :                                         }
-     109             :                                 } else {  // small direction error relative to tolerance, try to increase step size
-     110          10 :                                         if (step != maxStep) {  // only update once if maximum step size yet not reached
-     111          10 :                                                 newStep = step * 0.95 * pow(r, -0.2);
-     112          17 :                                                 newStep = std::min(newStep, 5 * step); // limit step size increase
-     113          10 :                                                 newStep = std::min(newStep, maxStep); // limit step size to maxStep
-     114             :                                         }
-     115             :                                         break;
-     116             :                                 }
-     117             :                         }
-     118             :                 }
-     119             : 
-     120          36 :                 current.setPosition(yOut.x);
-     121          36 :                 current.setDirection(yOut.u.getUnitVector());
-     122          36 :                 candidate->setCurrentStep(step);
-     123          36 :                 candidate->setNextStep(newStep);
-     124             :         }
-     125             : 
-     126             : 
-     127          16 :         void PropagationBP::setField(ref_ptr<MagneticField> f) {
-     128          16 :                 field = f;
-     129          16 :         }
-     130             : 
-     131             : 
-     132           2 :         ref_ptr<MagneticField> PropagationBP::getField() const {
-     133           2 :                 return field;
-     134             :         }
-     135             : 
-     136             : 
-     137         104 :         Vector3d PropagationBP::getFieldAtPosition(Vector3d pos, double z) const {
-     138             :                 Vector3d B(0, 0, 0);
-     139             :                 try {
-     140             :                         // check if field is valid and use the field vector at the
-     141             :                         // position pos with the redshift z
-     142         104 :                         if (field.valid())
-     143         104 :                                 B = field->getField(pos, z);
-     144           0 :                 } catch (std::exception &e) {
-     145           0 :                         KISS_LOG_ERROR  << "PropagationBP: Exception in PropagationBP::getFieldAtPosition.\n"
-     146           0 :                                         << e.what();
-     147           0 :                 }       
-     148         104 :                 return B;
-     149             :         }
-     150             : 
-     151             : 
-     152          28 :         double PropagationBP::errorEstimation(const Vector3d x1, const Vector3d x2, double step) const {
-     153             :                 // compare the position after one step with the position after two steps with step/2.
-     154             :                 Vector3d diff = (x1 - x2);
-     155             : 
-     156          28 :                 double S = diff.getR() / (step * (1 - 1/4.) );  // 1/4 = (1/2)²  number of steps for x1 divided by number of steps for x2 to the power of p (order)
-     157             : 
-     158          28 :                 return S;
-     159             :         }
-     160             : 
-     161             : 
-     162          22 :         void PropagationBP::setTolerance(double tol) {
-     163          22 :                 if ((tol > 1) or (tol < 0))
-     164           2 :                         throw std::runtime_error(
-     165           4 :                                         "PropagationBP: target error not in range 0-1");
-     166          20 :                 tolerance = tol;
-     167          20 :         }
-     168             : 
-     169             : 
-     170          24 :         void PropagationBP::setMinimumStep(double min) {
-     171          24 :                 if (min < 0)
-     172           1 :                         throw std::runtime_error("PropagationBP: minStep < 0 ");
-     173          23 :                 if (min > maxStep)
-     174           2 :                         throw std::runtime_error("PropagationBP: minStep > maxStep");
-     175          21 :                 minStep = min;
-     176          21 :         }
-     177             : 
-     178             : 
-     179          22 :         void PropagationBP::setMaximumStep(double max) {
-     180          22 :                 if (max < minStep)
-     181           1 :                         throw std::runtime_error("PropagationBP: maxStep < minStep");
-     182          21 :                 maxStep = max;
-     183          21 :         }
-     184             : 
-     185             : 
-     186           2 :         double PropagationBP::getTolerance() const {
-     187           2 :                 return tolerance;
-     188             :         }
-     189             : 
-     190             : 
-     191           2 :         double PropagationBP::getMinimumStep() const {
-     192           2 :                 return minStep;
-     193             :         }
-     194             : 
-     195             : 
-     196           5 :         double PropagationBP::getMaximumStep() const {
-     197           5 :                 return maxStep;
-     198             :         }
-     199             : 
-     200             : 
-     201           0 :         std::string PropagationBP::getDescription() const {
-     202           0 :                 std::stringstream s;
-     203           0 :                 s << "Propagation in magnetic fields using the adaptive Boris push method.";
-     204           0 :                 s << " Target error: " << tolerance;
-     205           0 :                 s << ", Minimum Step: " << minStep / kpc << " kpc";
-     206           0 :                 s << ", Maximum Step: " << maxStep / kpc << " kpc";
-     207           0 :                 return s.str();
-     208           0 :         }
-     209             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html b/doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html deleted file mode 100644 index 01527a79b..000000000 --- a/doc/coverageReport/src/module/PropagationCK.cpp.func-sort-c.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PropagationCK.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PropagationCK.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859787.6 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa13PropagationCK14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationCK12getToleranceEv2
_ZNK7crpropa13PropagationCK14getMinimumStepEv2
_ZNK7crpropa13PropagationCK8getFieldEv2
_ZNK7crpropa13PropagationCK14getMaximumStepEv3
_ZN7crpropa13PropagationCKC2ENS_7ref_ptrINS_13MagneticFieldEEEddd13
_ZN7crpropa13PropagationCK8setFieldENS_7ref_ptrINS_13MagneticFieldEEE14
_ZN7crpropa13PropagationCK12setToleranceEd18
_ZN7crpropa13PropagationCK14setMaximumStepEd19
_ZN7crpropa13PropagationCK14setMinimumStepEd22
_ZNK7crpropa13PropagationCK7processEPNS_9CandidateE34
_ZNK7crpropa13PropagationCK7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEd42
_ZNK7crpropa13PropagationCK4dYdtERKNS0_1YERNS_13ParticleStateEd252
_ZNK7crpropa13PropagationCK18getFieldAtPositionENS_7Vector3IdEEd253
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PropagationCK.cpp.func.html b/doc/coverageReport/src/module/PropagationCK.cpp.func.html deleted file mode 100644 index 6461ce48c..000000000 --- a/doc/coverageReport/src/module/PropagationCK.cpp.func.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PropagationCK.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PropagationCK.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859787.6 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa13PropagationCK12setToleranceEd18
_ZN7crpropa13PropagationCK14setMaximumStepEd19
_ZN7crpropa13PropagationCK14setMinimumStepEd22
_ZN7crpropa13PropagationCK8setFieldENS_7ref_ptrINS_13MagneticFieldEEE14
_ZN7crpropa13PropagationCKC2ENS_7ref_ptrINS_13MagneticFieldEEEddd13
_ZNK7crpropa13PropagationCK12getToleranceEv2
_ZNK7crpropa13PropagationCK14getDescriptionB5cxx11Ev0
_ZNK7crpropa13PropagationCK14getMaximumStepEv3
_ZNK7crpropa13PropagationCK14getMinimumStepEv2
_ZNK7crpropa13PropagationCK18getFieldAtPositionENS_7Vector3IdEEd253
_ZNK7crpropa13PropagationCK4dYdtERKNS0_1YERNS_13ParticleStateEd252
_ZNK7crpropa13PropagationCK7processEPNS_9CandidateE34
_ZNK7crpropa13PropagationCK7tryStepERKNS0_1YERS1_S4_dRNS_13ParticleStateEd42
_ZNK7crpropa13PropagationCK8getFieldEv2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/PropagationCK.cpp.gcov.html b/doc/coverageReport/src/module/PropagationCK.cpp.gcov.html deleted file mode 100644 index 037e88d09..000000000 --- a/doc/coverageReport/src/module/PropagationCK.cpp.gcov.html +++ /dev/null @@ -1,278 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/PropagationCK.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - PropagationCK.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:859787.6 %
Date:2024-04-08 14:58:22Functions:131492.9 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/PropagationCK.h"
-       2             : 
-       3             : #include <limits>
-       4             : #include <sstream>
-       5             : #include <stdexcept>
-       6             : #include <vector>
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10             : // Cash-Karp coefficients
-      11             : const double cash_karp_a[] = {
-      12             :         0., 0., 0., 0., 0., 0.,
-      13             :         1. / 5., 0., 0., 0., 0., 0.,
-      14             :         3. / 40., 9. / 40., 0., 0., 0., 0.,
-      15             :         3. / 10., -9. / 10., 6. / 5., 0., 0., 0.,
-      16             :         -11. / 54., 5. / 2., -70. / 27., 35. / 27., 0., 0.,
-      17             :         1631. / 55296., 175. / 512., 575. / 13824., 44275. / 110592., 253. / 4096., 0.
-      18             : };
-      19             : 
-      20             : const double cash_karp_b[] = {
-      21             :         37. / 378., 0, 250. / 621., 125. / 594., 0., 512. / 1771.
-      22             : };
-      23             : 
-      24             : const double cash_karp_bs[] = {
-      25             :         2825. / 27648., 0., 18575. / 48384., 13525. / 55296., 277. / 14336., 1. / 4.
-      26             : };
-      27             : 
-      28          42 : void PropagationCK::tryStep(const Y &y, Y &out, Y &error, double h,
-      29             :                 ParticleState &particle, double z) const {
-      30             :         std::vector<Y> k;
-      31          42 :         k.reserve(6);
-      32             : 
-      33             :         out = y;
-      34             :         error = Y(0);
-      35             : 
-      36             :         // calculate the sum of b_i * k_i
-      37         294 :         for (size_t i = 0; i < 6; i++) {
-      38             : 
-      39             :                 Y y_n = y;
-      40         882 :                 for (size_t j = 0; j < i; j++)
-      41         630 :                         y_n += k[j] * a[i * 6 + j] * h;
-      42             : 
-      43             :                 // update k_i
-      44         252 :                 k[i] = dYdt(y_n, particle, z);
-      45             : 
-      46         252 :                 out += k[i] * b[i] * h;
-      47         252 :                 error += k[i] * (b[i] - bs[i]) * h;
-      48             :         }
-      49          42 : }
-      50             : 
-      51         252 : PropagationCK::Y PropagationCK::dYdt(const Y &y, ParticleState &p, double z) const {
-      52             :         // normalize direction vector to prevent numerical losses
-      53         252 :         Vector3d velocity = y.u.getUnitVector() * c_light;
-      54             :         
-      55             :         // get B field at particle position
-      56         252 :         Vector3d B = getFieldAtPosition(y.x, z);
-      57             : 
-      58             :         // Lorentz force: du/dt = q*c/E * (v x B)
-      59         252 :         Vector3d dudt = p.getCharge() * c_light / p.getEnergy() * velocity.cross(B);
-      60         252 :         return Y(velocity, dudt);
-      61             : }
-      62             : 
-      63          13 : PropagationCK::PropagationCK(ref_ptr<MagneticField> field, double tolerance,
-      64          13 :                 double minStep, double maxStep) :
-      65          13 :                 minStep(0) {
-      66          15 :         setField(field);
-      67          13 :         setTolerance(tolerance);
-      68          12 :         setMaximumStep(maxStep);
-      69          12 :         setMinimumStep(minStep);
-      70             : 
-      71             :         // load Cash-Karp coefficients
-      72             :         a.assign(cash_karp_a, cash_karp_a + 36);
-      73             :         b.assign(cash_karp_b, cash_karp_b + 6);
-      74             :         bs.assign(cash_karp_bs, cash_karp_bs + 6);
-      75          11 : }
-      76             : 
-      77          34 : void PropagationCK::process(Candidate *candidate) const {
-      78             :         // save the new previous particle state
-      79          34 :         ParticleState &current = candidate->current;
-      80             :         candidate->previous = current;
-      81             : 
-      82          34 :         Y yIn(current.getPosition(), current.getDirection());
-      83          34 :         double step = maxStep;
-      84             : 
-      85             :         // rectilinear propagation for neutral particles
-      86          34 :         if (current.getCharge() == 0) {
-      87           2 :                 step = clip(candidate->getNextStep(), minStep, maxStep);
-      88           1 :                 current.setPosition(yIn.x + yIn.u * step);
-      89           1 :                 candidate->setCurrentStep(step);
-      90           1 :                 candidate->setNextStep(maxStep);
-      91             :                 return;
-      92             :         }
-      93             : 
-      94             :         Y yOut, yErr;
-      95          33 :         double newStep = step;
-      96          33 :         double z = candidate->getRedshift();
-      97             : 
-      98             : 
-      99             :         // if minStep is the same as maxStep the adaptive algorithm with its error
-     100             :         // estimation is not needed and the computation time can be saved:
-     101          33 :         if (minStep == maxStep){
-     102          10 :                 tryStep(yIn, yOut, yErr, step / c_light, current, z);
-     103             :         } else {
-     104          23 :                 step = clip(candidate->getNextStep(), minStep, maxStep);
-     105          23 :                 newStep = step;
-     106             :                 double r = 42;  // arbitrary value
-     107             : 
-     108             :                 // try performing step until the target error (tolerance) or the minimum/maximum step size has been reached
-     109             :                 while (true) {
-     110          32 :                         tryStep(yIn, yOut, yErr, step / c_light, current, z);
-     111          32 :                         r = yErr.u.getR() / tolerance;  // ratio of absolute direction error and tolerance
-     112          32 :                         if (r > 1) {  // large direction error relative to tolerance, try to decrease step size
-     113          10 :                                 if (step == minStep)  // already minimum step size
-     114             :                                         break;
-     115             :                                 else {
-     116           9 :                                         newStep = step * 0.95 * pow(r, -0.2);
-     117          17 :                                         newStep = std::max(newStep, 0.1 * step); // limit step size decrease
-     118           9 :                                         newStep = std::max(newStep, minStep); // limit step size to minStep
-     119             :                                         step = newStep;
-     120             :                                 }
-     121             :                         } else {  // small direction error relative to tolerance, try to increase step size
-     122          22 :                                 if (step != maxStep) {  // only update once if maximum step size yet not reached
-     123          22 :                                         newStep = step * 0.95 * pow(r, -0.2);
-     124          35 :                                         newStep = std::min(newStep, 5 * step); // limit step size increase
-     125          22 :                                         newStep = std::min(newStep, maxStep); // limit step size to maxStep
-     126             :                                 }
-     127             :                                 break;
-     128             :                         }
-     129             :                 }
-     130             :         }
-     131             : 
-     132          33 :         current.setPosition(yOut.x);
-     133          33 :         current.setDirection(yOut.u.getUnitVector());
-     134          33 :         candidate->setCurrentStep(step);
-     135          33 :         candidate->setNextStep(newStep);
-     136             : }
-     137             : 
-     138          14 : void PropagationCK::setField(ref_ptr<MagneticField> f) {
-     139          14 :         field = f;
-     140          14 : }
-     141             : 
-     142           2 : ref_ptr<MagneticField> PropagationCK::getField() const {
-     143           2 :         return field;
-     144             : }
-     145             : 
-     146         253 : Vector3d PropagationCK::getFieldAtPosition(Vector3d pos, double z) const {
-     147             :         Vector3d B(0, 0, 0);
-     148             :         try {
-     149             :                 // check if field is valid and use the field vector at the
-     150             :                 // position pos with the redshift z
-     151         253 :                 if (field.valid())
-     152         253 :                         B = field->getField(pos, z);
-     153           0 :         } catch (std::exception &e) {
-     154           0 :                 KISS_LOG_ERROR  << "PropagationCK: Exception in PropagationCK::getFieldAtPosition.\n"
-     155           0 :                                 << e.what();
-     156           0 :         }       
-     157         253 :         return B;
-     158             : }
-     159             : 
-     160          18 : void PropagationCK::setTolerance(double tol) {
-     161          18 :         if ((tol > 1) or (tol < 0))
-     162           2 :                 throw std::runtime_error(
-     163           4 :                                 "PropagationCK: target error not in range 0-1");
-     164          16 :         tolerance = tol;
-     165          16 : }
-     166             : 
-     167          22 : void PropagationCK::setMinimumStep(double min) {
-     168          22 :         if (min < 0)
-     169           1 :                 throw std::runtime_error("PropagationCK: minStep < 0 ");
-     170          21 :         if (min > maxStep)
-     171           2 :                 throw std::runtime_error("PropagationCK: minStep > maxStep");
-     172          19 :         minStep = min;
-     173          19 : }
-     174             : 
-     175          19 : void PropagationCK::setMaximumStep(double max) {
-     176          19 :         if (max < minStep)
-     177           1 :                 throw std::runtime_error("PropagationCK: maxStep < minStep");
-     178          18 :         maxStep = max;
-     179          18 : }
-     180             : 
-     181           2 : double PropagationCK::getTolerance() const {
-     182           2 :         return tolerance;
-     183             : }
-     184             : 
-     185           2 : double PropagationCK::getMinimumStep() const {
-     186           2 :         return minStep;
-     187             : }
-     188             : 
-     189           3 : double PropagationCK::getMaximumStep() const {
-     190           3 :         return maxStep;
-     191             : }
-     192             : 
-     193           0 : std::string PropagationCK::getDescription() const {
-     194           0 :         std::stringstream s;
-     195           0 :         s << "Propagation in magnetic fields using the Cash-Karp method.";
-     196           0 :         s << " Target error: " << tolerance;
-     197           0 :         s << ", Minimum Step: " << minStep / kpc << " kpc";
-     198           0 :         s << ", Maximum Step: " << maxStep / kpc << " kpc";
-     199           0 :         return s.str();
-     200           0 : }
-     201             : 
-     202             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html b/doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html deleted file mode 100644 index 8258b1e94..000000000 --- a/doc/coverageReport/src/module/Redshift.cpp.func-sort-c.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Redshift.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Redshift.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:92832.1 %
Date:2024-04-08 14:58:22Functions:1425.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa14FutureRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa14FutureRedshift7processEPNS_9CandidateE0
_ZNK7crpropa8Redshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Redshift7processEPNS_9CandidateE7644
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Redshift.cpp.func.html b/doc/coverageReport/src/module/Redshift.cpp.func.html deleted file mode 100644 index 39944b158..000000000 --- a/doc/coverageReport/src/module/Redshift.cpp.func.html +++ /dev/null @@ -1,88 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Redshift.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Redshift.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:92832.1 %
Date:2024-04-08 14:58:22Functions:1425.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa14FutureRedshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa14FutureRedshift7processEPNS_9CandidateE0
_ZNK7crpropa8Redshift14getDescriptionB5cxx11Ev0
_ZNK7crpropa8Redshift7processEPNS_9CandidateE7644
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Redshift.cpp.gcov.html b/doc/coverageReport/src/module/Redshift.cpp.gcov.html deleted file mode 100644 index f41db2d01..000000000 --- a/doc/coverageReport/src/module/Redshift.cpp.gcov.html +++ /dev/null @@ -1,138 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Redshift.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Redshift.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:92832.1 %
Date:2024-04-08 14:58:22Functions:1425.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/Redshift.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Cosmology.h"
-       4             : 
-       5             : #include <limits>
-       6             : 
-       7             : namespace crpropa {
-       8             : 
-       9        7644 : void Redshift::process(Candidate *c) const {
-      10        7644 :         double z = c->getRedshift();
-      11             : 
-      12             :         // check if z = 0
-      13        7644 :         if (z <= std::numeric_limits<double>::min())
-      14          21 :                 return;
-      15             : 
-      16             :         // use small step approximation:  dz = H(z) / c * ds
-      17        7623 :         double dz = hubbleRate(z) / c_light * c->getCurrentStep();
-      18             : 
-      19             :         // prevent dz > z
-      20        7623 :         dz = std::min(dz, z);
-      21             : 
-      22             :         // update redshift
-      23        7623 :         c->setRedshift(z - dz);
-      24             : 
-      25             :         // adiabatic energy loss: dE / dz = E / (1 + z)
-      26        7623 :         double E = c->current.getEnergy();
-      27        7623 :         c->current.setEnergy(E * (1 - dz / (1 + z)));
-      28             : }
-      29             : 
-      30           0 : std::string Redshift::getDescription() const {
-      31           0 :         std::stringstream s;
-      32           0 :         s << "Redshift: h0 = " << hubbleRate() / 1e5 * Mpc << ", omegaL = "
-      33           0 :                         << omegaL() << ", omegaM = " << omegaM();
-      34           0 :         return s.str();
-      35           0 : }
-      36             : 
-      37           0 : void FutureRedshift::process(Candidate *c) const {
-      38           0 :         double z = c->getRedshift();
-      39             : 
-      40             :         // check if z = -1
-      41           0 :         if (z <= -1)
-      42             :                 return;
-      43             : 
-      44             :         // use small step approximation:  dz = H(z) / c * ds
-      45           0 :         double dz = hubbleRate(z) / c_light * c->getCurrentStep();
-      46             : 
-      47             :         // update redshift
-      48           0 :         c->setRedshift(z - dz);
-      49             : 
-      50             :         // adiabatic energy loss: dE / dz = E / (1 + z)
-      51           0 :         double E = c->current.getEnergy();
-      52           0 :         c->current.setEnergy(E * (1 - dz / (1 + z)));
-      53             : }
-      54             : 
-      55           0 : std::string FutureRedshift::getDescription() const {
-      56           0 :         std::stringstream s;
-      57           0 :         s << "FutureRedshift: h0 = " << hubbleRate() / 1e5 * Mpc << ", omegaL = "
-      58           0 :                         << omegaL() << ", omegaM = " << omegaM();
-      59           0 :         return s.str();
-      60           0 : }
-      61             : 
-      62             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html b/doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html deleted file mode 100644 index 89ada30d6..000000000 --- a/doc/coverageReport/src/module/RestrictToRegion.cpp.func-sort-c.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/RestrictToRegion.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - RestrictToRegion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:61250.0 %
Date:2024-04-08 14:58:22Functions:2366.7 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZNK7crpropa16RestrictToRegion14getDescriptionB5cxx11Ev0
_ZN7crpropa16RestrictToRegionC2EPNS_6ModuleEPNS_7SurfaceE1
_ZNK7crpropa16RestrictToRegion7processEPNS_9CandidateE2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/RestrictToRegion.cpp.func.html b/doc/coverageReport/src/module/RestrictToRegion.cpp.func.html deleted file mode 100644 index 6024c3ad3..000000000 --- a/doc/coverageReport/src/module/RestrictToRegion.cpp.func.html +++ /dev/null @@ -1,84 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/RestrictToRegion.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - RestrictToRegion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:61250.0 %
Date:2024-04-08 14:58:22Functions:2366.7 %
-
- -
- - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16RestrictToRegionC2EPNS_6ModuleEPNS_7SurfaceE1
_ZNK7crpropa16RestrictToRegion14getDescriptionB5cxx11Ev0
_ZNK7crpropa16RestrictToRegion7processEPNS_9CandidateE2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html b/doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html deleted file mode 100644 index 38282b565..000000000 --- a/doc/coverageReport/src/module/RestrictToRegion.cpp.gcov.html +++ /dev/null @@ -1,101 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/RestrictToRegion.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - RestrictToRegion.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:61250.0 %
Date:2024-04-08 14:58:22Functions:2366.7 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/RestrictToRegion.h" 
-       2             : 
-       3             : #include <sstream>
-       4             : 
-       5             : namespace crpropa {
-       6             : 
-       7           1 : RestrictToRegion::RestrictToRegion(Module* _module, Surface* _surface) : module(_module), surface(_surface) { 
-       8           1 : };
-       9             : 
-      10           2 : void RestrictToRegion::process(Candidate *candidate) const {
-      11           2 :         if (surface->distance(candidate->current.getPosition()) <= 0) {
-      12           1 :                 module->process(candidate);
-      13             :         }
-      14           2 : };
-      15             : 
-      16           0 : std::string RestrictToRegion::getDescription() const {
-      17           0 :         std::stringstream s;
-      18             :         s << "RestrictToArea:\n"
-      19           0 :                 << "  Module: " << module->getDescription() << std::endl
-      20           0 :                 << "  Region: " << surface->getDescription() << std::endl;
-      21           0 :         return s.str();
-      22           0 : };
-      23             : 
-      24             : 
-      25             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html b/doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html deleted file mode 100644 index 1d24c0fb2..000000000 --- a/doc/coverageReport/src/module/SimplePropagation.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/SimplePropagation.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - SimplePropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:123336.4 %
Date:2024-04-08 14:58:22Functions:2728.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17SimplePropagation14setMaximumStepEd0
_ZN7crpropa17SimplePropagation14setMinimumStepEd0
_ZNK7crpropa17SimplePropagation14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SimplePropagation14getMaximumStepEv0
_ZNK7crpropa17SimplePropagation14getMinimumStepEv0
_ZN7crpropa17SimplePropagationC2Edd12
_ZNK7crpropa17SimplePropagation7processEPNS_9CandidateE19294
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/SimplePropagation.cpp.func.html b/doc/coverageReport/src/module/SimplePropagation.cpp.func.html deleted file mode 100644 index 2f86027c0..000000000 --- a/doc/coverageReport/src/module/SimplePropagation.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/SimplePropagation.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - SimplePropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:123336.4 %
Date:2024-04-08 14:58:22Functions:2728.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa17SimplePropagation14setMaximumStepEd0
_ZN7crpropa17SimplePropagation14setMinimumStepEd0
_ZN7crpropa17SimplePropagationC2Edd12
_ZNK7crpropa17SimplePropagation14getDescriptionB5cxx11Ev0
_ZNK7crpropa17SimplePropagation14getMaximumStepEv0
_ZNK7crpropa17SimplePropagation14getMinimumStepEv0
_ZNK7crpropa17SimplePropagation7processEPNS_9CandidateE19294
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html b/doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html deleted file mode 100644 index c01c7f1d1..000000000 --- a/doc/coverageReport/src/module/SimplePropagation.cpp.gcov.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/SimplePropagation.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - SimplePropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:123336.4 %
Date:2024-04-08 14:58:22Functions:2728.6 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/SimplePropagation.h"
-       2             : 
-       3             : #include <sstream>
-       4             : #include <stdexcept>
-       5             : 
-       6             : namespace crpropa {
-       7             : 
-       8          12 : SimplePropagation::SimplePropagation(double minStep, double maxStep) :
-       9          12 :                 minStep(minStep), maxStep(maxStep) {
-      10          12 :         if (minStep > maxStep)
-      11           0 :                 throw std::runtime_error("SimplePropagation: minStep > maxStep");
-      12          12 : }
-      13             : 
-      14       19294 : void SimplePropagation::process(Candidate *c) const {
-      15             :         c->previous = c->current;
-      16             : 
-      17       19294 :         double step = clip(c->getNextStep(), minStep, maxStep);
-      18       19294 :         c->setCurrentStep(step);
-      19       19294 :         Vector3d pos = c->current.getPosition();
-      20       19294 :         Vector3d dir = c->current.getDirection();
-      21       19294 :         c->current.setPosition(pos + dir * step);
-      22       19294 :         c->setNextStep(maxStep);
-      23       19294 : }
-      24             : 
-      25           0 : void SimplePropagation::setMinimumStep(double step) {
-      26           0 :         if (step > maxStep)
-      27           0 :                 throw std::runtime_error("SimplePropagation: minStep > maxStep");
-      28           0 :         minStep = step;
-      29           0 : }
-      30             : 
-      31           0 : void SimplePropagation::setMaximumStep(double step) {
-      32           0 :         if (minStep > step)
-      33           0 :                 throw std::runtime_error("SimplePropagation: minStep > maxStep");
-      34           0 :         maxStep = step;
-      35           0 : }
-      36             : 
-      37           0 : double SimplePropagation::getMinimumStep() const {
-      38           0 :         return minStep;
-      39             : }
-      40             : 
-      41           0 : double SimplePropagation::getMaximumStep() const {
-      42           0 :         return maxStep;
-      43             : }
-      44             : 
-      45           0 : std::string SimplePropagation::getDescription() const {
-      46           0 :         std::stringstream s;
-      47           0 :         s << "SimplePropagation: Step size = " << minStep / kpc
-      48           0 :                         << " - " << maxStep / kpc << " kpc";
-      49           0 :         return s.str();
-      50           0 : }
-      51             : 
-      52             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html deleted file mode 100644 index d0dcbba06..000000000 --- a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func-sort-c.html +++ /dev/null @@ -1,156 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/SynchrotronRadiation.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - SynchrotronRadiation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8113161.8 %
Date:2024-04-08 14:58:22Functions:102147.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SynchrotronRadiation11getThinningEv0
_ZN7crpropa20SynchrotronRadiation11setThinningEd0
_ZN7crpropa20SynchrotronRadiation14getHavePhotonsEv0
_ZN7crpropa20SynchrotronRadiation17getMaximumSamplesEv0
_ZN7crpropa20SynchrotronRadiation7getBrmsEv0
_ZN7crpropa20SynchrotronRadiation8getFieldEv0
_ZN7crpropa20SynchrotronRadiation8getLimitEv0
_ZN7crpropa20SynchrotronRadiation8setFieldENS_7ref_ptrINS_13MagneticFieldEEE0
_ZN7crpropa20SynchrotronRadiationC2ENS_7ref_ptrINS_13MagneticFieldEEEbdid0
_ZNK7crpropa20SynchrotronRadiation14getDescriptionB5cxx11Ev0
_ZNK7crpropa20SynchrotronRadiation21getSecondaryThresholdEv0
_ZN7crpropa20SynchrotronRadiation12initSpectrumEv1
_ZN7crpropa20SynchrotronRadiation14setHavePhotonsEb1
_ZN7crpropa20SynchrotronRadiation17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa20SynchrotronRadiation17setMaximumSamplesEi1
_ZN7crpropa20SynchrotronRadiation21setSecondaryThresholdEd1
_ZN7crpropa20SynchrotronRadiation7setBrmsEd1
_ZN7crpropa20SynchrotronRadiation8setLimitEd1
_ZN7crpropa20SynchrotronRadiationC2Edbdid1
_ZNK7crpropa20SynchrotronRadiation7processEPNS_9CandidateE1
_ZNK7crpropa20SynchrotronRadiation17getInteractionTagB5cxx11Ev2
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html deleted file mode 100644 index bc212b37e..000000000 --- a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.func.html +++ /dev/null @@ -1,156 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/SynchrotronRadiation.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - SynchrotronRadiation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8113161.8 %
Date:2024-04-08 14:58:22Functions:102147.6 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20SynchrotronRadiation11getThinningEv0
_ZN7crpropa20SynchrotronRadiation11setThinningEd0
_ZN7crpropa20SynchrotronRadiation12initSpectrumEv1
_ZN7crpropa20SynchrotronRadiation14getHavePhotonsEv0
_ZN7crpropa20SynchrotronRadiation14setHavePhotonsEb1
_ZN7crpropa20SynchrotronRadiation17getMaximumSamplesEv0
_ZN7crpropa20SynchrotronRadiation17setInteractionTagENSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE1
_ZN7crpropa20SynchrotronRadiation17setMaximumSamplesEi1
_ZN7crpropa20SynchrotronRadiation21setSecondaryThresholdEd1
_ZN7crpropa20SynchrotronRadiation7getBrmsEv0
_ZN7crpropa20SynchrotronRadiation7setBrmsEd1
_ZN7crpropa20SynchrotronRadiation8getFieldEv0
_ZN7crpropa20SynchrotronRadiation8getLimitEv0
_ZN7crpropa20SynchrotronRadiation8setFieldENS_7ref_ptrINS_13MagneticFieldEEE0
_ZN7crpropa20SynchrotronRadiation8setLimitEd1
_ZN7crpropa20SynchrotronRadiationC2ENS_7ref_ptrINS_13MagneticFieldEEEbdid0
_ZN7crpropa20SynchrotronRadiationC2Edbdid1
_ZNK7crpropa20SynchrotronRadiation14getDescriptionB5cxx11Ev0
_ZNK7crpropa20SynchrotronRadiation17getInteractionTagB5cxx11Ev2
_ZNK7crpropa20SynchrotronRadiation21getSecondaryThresholdEv0
_ZNK7crpropa20SynchrotronRadiation7processEPNS_9CandidateE1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html b/doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html deleted file mode 100644 index 3ea130039..000000000 --- a/doc/coverageReport/src/module/SynchrotronRadiation.cpp.gcov.html +++ /dev/null @@ -1,306 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/SynchrotronRadiation.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - SynchrotronRadiation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8113161.8 %
Date:2024-04-08 14:58:22Functions:102147.6 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/SynchrotronRadiation.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Random.h"
-       4             : 
-       5             : #include <fstream>
-       6             : #include <limits>
-       7             : #include <stdexcept>
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11           0 : SynchrotronRadiation::SynchrotronRadiation(ref_ptr<MagneticField> field, bool havePhotons, double thinning, int nSamples, double limit) {
-      12           0 :         setField(field);
-      13           0 :         setBrms(0);
-      14           0 :         initSpectrum();
-      15           0 :         setHavePhotons(havePhotons);
-      16           0 :         setLimit(limit);
-      17           0 :         setSecondaryThreshold(1e6 * eV);
-      18           0 :         setMaximumSamples(nSamples);
-      19           0 : }
-      20             : 
-      21           1 : SynchrotronRadiation::SynchrotronRadiation(double Brms, bool havePhotons, double thinning, int nSamples, double limit) {
-      22           1 :         setBrms(Brms);
-      23           1 :         initSpectrum();
-      24           1 :         setHavePhotons(havePhotons);
-      25           1 :         setLimit(limit);
-      26           1 :         setSecondaryThreshold(1e6 * eV);
-      27           1 :         setMaximumSamples(nSamples);
-      28           1 : }
-      29             : 
-      30           0 : void SynchrotronRadiation::setField(ref_ptr<MagneticField> f) {
-      31           0 :         this->field = f;
-      32           0 : }
-      33             : 
-      34           0 : ref_ptr<MagneticField> SynchrotronRadiation::getField() {
-      35           0 :         return field;
-      36             : }
-      37             : 
-      38           1 : void SynchrotronRadiation::setBrms(double Brms) {
-      39           1 :         this->Brms = Brms;
-      40           1 : }
-      41             : 
-      42           0 : double SynchrotronRadiation::getBrms() {
-      43           0 :         return Brms;
-      44             : }
-      45             : 
-      46           1 : void SynchrotronRadiation::setHavePhotons(bool havePhotons) {
-      47           1 :         this->havePhotons = havePhotons;
-      48           1 : }
-      49             : 
-      50           0 : bool SynchrotronRadiation::getHavePhotons() {
-      51           0 :         return havePhotons;
-      52             : }
-      53             : 
-      54           0 : void SynchrotronRadiation::setThinning(double thinning) {
-      55           0 :         this->thinning = thinning;
-      56           0 : }
-      57             : 
-      58           0 : double SynchrotronRadiation::getThinning() {
-      59           0 :         return thinning;
-      60             : }
-      61             : 
-      62           1 : void SynchrotronRadiation::setLimit(double limit) {
-      63           1 :         this->limit = limit;
-      64           1 : }
-      65             : 
-      66           0 : double SynchrotronRadiation::getLimit() {
-      67           0 :         return limit;
-      68             : }
-      69             : 
-      70           1 : void SynchrotronRadiation::setMaximumSamples(int nmax) {
-      71           1 :         maximumSamples = nmax;
-      72           1 : }
-      73             : 
-      74           0 : int SynchrotronRadiation::getMaximumSamples() {
-      75           0 :         return maximumSamples;
-      76             : }
-      77             : 
-      78           1 : void SynchrotronRadiation::setSecondaryThreshold(double threshold) {
-      79           1 :         secondaryThreshold = threshold;
-      80           1 : }
-      81             : 
-      82           0 : double SynchrotronRadiation::getSecondaryThreshold() const {
-      83           0 :         return secondaryThreshold;
-      84             : }
-      85             : 
-      86           1 : void SynchrotronRadiation::initSpectrum() {
-      87           2 :         std::string filename = getDataPath("Synchrotron/spectrum.txt");
-      88           1 :         std::ifstream infile(filename.c_str());
-      89             : 
-      90           1 :         if (!infile.good())
-      91           0 :                 throw std::runtime_error("SynchrotronRadiation: could not open file " + filename);
-      92             : 
-      93             :         // clear previously loaded interaction rates
-      94           1 :         tabx.clear();
-      95           1 :         tabCDF.clear();
-      96             : 
-      97        1407 :         while (infile.good()) {
-      98        1406 :                 if (infile.peek() != '#') {
-      99             :                         double a, b;
-     100             :                         infile >> a >> b;
-     101        1402 :                         if (infile) {
-     102        1401 :                                 tabx.push_back(pow(10, a));
-     103        1401 :                                 tabCDF.push_back(b);
-     104             :                         }
-     105             :                 }
-     106        1406 :                 infile.ignore(std::numeric_limits < std::streamsize > ::max(), '\n');
-     107             :         }
-     108           1 :         infile.close();
-     109           2 : }
-     110             : 
-     111           1 : void SynchrotronRadiation::process(Candidate *candidate) const {
-     112           1 :         double charge = fabs(candidate->current.getCharge());
-     113           1 :         if (charge == 0)
-     114           0 :                 return; // only charged particles
-     115             : 
-     116             :         // calculate gyroradius, evaluated at the current position
-     117           1 :         double z = candidate->getRedshift();
-     118             :         double B;
-     119           1 :         if (field.valid()) {
-     120           0 :                 Vector3d Bvec = field->getField(candidate->current.getPosition(), z);
-     121           0 :                 B = Bvec.cross(candidate->current.getDirection()).getR();
-     122             :         } else {
-     123           1 :                 B = sqrt(2. / 3) * Brms; // average perpendicular field component
-     124             :         }
-     125           1 :         B *= pow(1 + z, 2); // cosmological scaling
-     126           1 :         double Rg = candidate->current.getMomentum().getR() / charge / B;
-     127             : 
-     128             :         // calculate energy loss
-     129           1 :         double lf = candidate->current.getLorentzFactor();
-     130           1 :         double dEdx = 1. / 6 / M_PI / epsilon0 * pow(lf * lf - 1, 2) * pow(charge / Rg, 2); // Jackson p. 770 (14.31)
-     131           1 :         double step = candidate->getCurrentStep() / (1 + z); // step size in local frame
-     132           1 :         double dE = step * dEdx;
-     133             : 
-     134             :         // apply energy loss and limit next step
-     135           1 :         double E = candidate->current.getEnergy();
-     136           1 :         candidate->current.setEnergy(E - dE);
-     137           1 :         candidate->limitNextStep(limit * E / dEdx);
-     138             : 
-     139             :         // optionally add secondary photons
-     140           1 :         if (not(havePhotons))
-     141             :                 return;
-     142             : 
-     143             :         // check if photons with energies > 14 * Ecrit are possible
-     144           1 :         double Ecrit = 3. / 4 * h_planck / M_PI * c_light * pow(lf, 3) / Rg;
-     145           1 :         if (14 * Ecrit < secondaryThreshold)
-     146             :                 return;
-     147             : 
-     148             :         // draw photons up to the total energy loss
-     149             :         // if maximumSamples is reached before that, compensate the total energy afterwards
-     150           1 :         Random &random = Random::instance();
-     151             :         double dE0 = dE;
-     152             :         std::vector<double> energies;
-     153             :         int counter = 0;
-     154     3620603 :         while (dE > 0) {
-     155             :                 // draw random value between 0 and maximum of corresponding cdf
-     156             :                 // choose bin of s where cdf(x) = cdf_rand -> x_rand
-     157     3620602 :                 size_t i = random.randBin(tabCDF); // draw random bin (upper bin boundary returned)
-     158     3620602 :                 double binWidth = (tabx[i] - tabx[i-1]);
-     159     3620602 :                 double x = tabx[i-1] + random.rand() * binWidth; // draw random x uniformly distributed in bin
-     160     3620602 :                 double Ephoton = x * Ecrit;
-     161             : 
-     162             :                 // if the remaining energy is not sufficient check for random accepting
-     163     3620602 :                 if (Ephoton > dE) {
-     164           1 :                         if (random.rand() > (dE / Ephoton))
-     165             :                                 break; // not accepted
-     166             :                 }
-     167             : 
-     168             :                 // only activate the "per-step" sampling if maximumSamples is explicitly set.
-     169     3620602 :                 if (maximumSamples > 0) {
-     170           0 :                         if (counter >= maximumSamples) 
-     171             :                                 break;                  
-     172             :                 }
-     173             : 
-     174             :                 // store energies in array
-     175     3620602 :                 energies.push_back(Ephoton);
-     176             : 
-     177             :                 // energy loss
-     178     3620602 :                 dE -= Ephoton;
-     179             : 
-     180             :                 // counter for sampling break condition;
-     181     3620602 :                 counter++;
-     182             :         }
-     183             : 
-     184             :         // while loop before gave total energy which is just a fraction of the required
-     185             :         double w1 = 1;
-     186           1 :         if (maximumSamples > 0 && dE > 0)
-     187           0 :                 w1 = 1. / (1. - dE / dE0); 
-     188             : 
-     189             :         // loop over sampled photons and attribute weights accordingly
-     190     3620603 :         for (int i = 0; i < energies.size(); i++) {
-     191     3620602 :                 double Ephoton = energies[i];
-     192     3620602 :                 double f = Ephoton / (E - dE0);
-     193     3620602 :                 double w = w1 / pow(f, thinning);
-     194             : 
-     195             :                 // thinning procedure: accepts only a few random secondaries
-     196     3620602 :                 if (random.rand() < pow(f, thinning)) {
-     197     3620602 :                         Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition());
-     198     3620602 :                         if (Ephoton > secondaryThreshold) // create only photons with energies above threshold
-     199     3309554 :                                 candidate->addSecondary(22, Ephoton, pos, w, interactionTag);
-     200             :                 }
-     201             :         }
-     202             : }
-     203             : 
-     204           0 : std::string SynchrotronRadiation::getDescription() const {
-     205           0 :         std::stringstream s;
-     206           0 :         s << "Synchrotron radiation";
-     207           0 :         if (field.valid())
-     208           0 :                 s << " for specified magnetic field";
-     209             :         else
-     210           0 :                 s << " for Brms = " << Brms / nG << " nG";
-     211           0 :         if (havePhotons)
-     212           0 :                 s << ", synchrotron photons E > " << secondaryThreshold / eV << " eV";
-     213             :         else
-     214           0 :                 s << ", no synchrotron photons";
-     215           0 :         if (maximumSamples > 0)
-     216           0 :                 s << "maximum number of photon samples: " << maximumSamples;
-     217           0 :         if (thinning > 0)
-     218           0 :                 s << "thinning parameter: " << thinning; 
-     219           0 :         return s.str();
-     220           0 : }
-     221             : 
-     222           1 : void SynchrotronRadiation::setInteractionTag(std::string tag) {
-     223           1 :         interactionTag = tag;
-     224           1 : }
-     225             : 
-     226           2 : std::string SynchrotronRadiation::getInteractionTag() const {
-     227           2 :         return interactionTag;
-     228             : }
-     229             : 
-     230             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html b/doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html deleted file mode 100644 index 97378d014..000000000 --- a/doc/coverageReport/src/module/TextOutput.cpp.func-sort-c.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/TextOutput.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - TextOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21924988.0 %
Date:2024-04-08 14:58:22Functions:91464.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10TextOutput4gzipEv0
_ZN7crpropa10TextOutputC2ERSo0
_ZN7crpropa10TextOutputC2ERSoNS_6Output10OutputTypeE0
_ZN7crpropa10TextOutputC2Ev0
_ZNK7crpropa10TextOutput14getDescriptionB5cxx11Ev0
_ZN7crpropa10TextOutput4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEPNS_17ParticleCollectorE1
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE1
_ZN7crpropa10TextOutputD0Ev1
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa10TextOutputC2ENS_6Output10OutputTypeE7
_ZN7crpropa10TextOutputD2Ev9
_ZNK7crpropa10TextOutput11printHeaderEv9
_ZN7crpropa10TextOutput5closeEv10
_ZNK7crpropa10TextOutput7processEPNS_9CandidateE54
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/TextOutput.cpp.func.html b/doc/coverageReport/src/module/TextOutput.cpp.func.html deleted file mode 100644 index 1ca5f18f5..000000000 --- a/doc/coverageReport/src/module/TextOutput.cpp.func.html +++ /dev/null @@ -1,128 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/TextOutput.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - TextOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21924988.0 %
Date:2024-04-08 14:58:22Functions:91464.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa10TextOutput4gzipEv0
_ZN7crpropa10TextOutput4loadERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEEPNS_17ParticleCollectorE1
_ZN7crpropa10TextOutput5closeEv10
_ZN7crpropa10TextOutputC2ENS_6Output10OutputTypeE7
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEE2
_ZN7crpropa10TextOutputC2ERKNSt7__cxx1112basic_stringIcSt11char_traitsIcESaIcEEENS_6Output10OutputTypeE1
_ZN7crpropa10TextOutputC2ERSo0
_ZN7crpropa10TextOutputC2ERSoNS_6Output10OutputTypeE0
_ZN7crpropa10TextOutputC2Ev0
_ZN7crpropa10TextOutputD0Ev1
_ZN7crpropa10TextOutputD2Ev9
_ZNK7crpropa10TextOutput11printHeaderEv9
_ZNK7crpropa10TextOutput14getDescriptionB5cxx11Ev0
_ZNK7crpropa10TextOutput7processEPNS_9CandidateE54
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/TextOutput.cpp.gcov.html b/doc/coverageReport/src/module/TextOutput.cpp.gcov.html deleted file mode 100644 index 7ac87a19d..000000000 --- a/doc/coverageReport/src/module/TextOutput.cpp.gcov.html +++ /dev/null @@ -1,457 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/TextOutput.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - TextOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:21924988.0 %
Date:2024-04-08 14:58:22Functions:91464.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/TextOutput.h"
-       2             : #include "crpropa/module/ParticleCollector.h"
-       3             : #include "crpropa/Units.h"
-       4             : #include "crpropa/Version.h"
-       5             : #include "crpropa/Random.h"
-       6             : #include "crpropa/base64.h"
-       7             : 
-       8             : #include "kiss/string.h"
-       9             : 
-      10             : #include <cstdio>
-      11             : #include <stdexcept>
-      12             : #include <iostream>
-      13             : 
-      14             : #ifdef CRPROPA_HAVE_ZLIB
-      15             : #include <izstream.hpp>
-      16             : #include <ozstream.hpp>
-      17             : #endif
-      18             : 
-      19             : namespace crpropa {
-      20             : 
-      21           0 : TextOutput::TextOutput() : Output(), out(&std::cout), storeRandomSeeds(false) {
-      22           0 : }
-      23             : 
-      24           7 : TextOutput::TextOutput(OutputType outputtype) : Output(outputtype), out(&std::cout), storeRandomSeeds(false) {
-      25           7 : }
-      26             : 
-      27           0 : TextOutput::TextOutput(std::ostream &out) : Output(), out(&out), storeRandomSeeds(false) {
-      28           0 : }
-      29             : 
-      30           0 : TextOutput::TextOutput(std::ostream &out,
-      31           0 :                 OutputType outputtype) : Output(outputtype), out(&out), storeRandomSeeds(false) {
-      32           0 : }
-      33             : 
-      34           4 : TextOutput::TextOutput(const std::string &filename) :  Output(), outfile(filename.c_str(),
-      35           2 :                                 std::ios::binary), out(&outfile),  filename(
-      36           4 :                                 filename), storeRandomSeeds(false) {
-      37           2 :         if (!outfile.is_open())
-      38           2 :                 throw std::runtime_error(std::string("Cannot create file: ") + filename);
-      39           3 :         if (kiss::ends_with(filename, ".gz"))
-      40           0 :                 gzip();
-      41           3 : }
-      42             : 
-      43           1 : TextOutput::TextOutput(const std::string &filename,
-      44           2 :                                 OutputType outputtype) : Output(outputtype), outfile(filename.c_str(),
-      45           1 :                                 std::ios::binary), out(&outfile), filename(
-      46           2 :                                 filename), storeRandomSeeds(false) {
-      47           1 :         if (!outfile.is_open())
-      48           0 :                 throw std::runtime_error(std::string("Cannot create file: ") + filename);
-      49           2 :         if (kiss::ends_with(filename, ".gz"))
-      50           0 :                 gzip();
-      51           1 : }
-      52             : 
-      53           9 : void TextOutput::printHeader() const {
-      54           9 :         *out << "#";
-      55           9 :         if (fields.test(TrajectoryLengthColumn))
-      56           6 :                 *out << "\tD";
-      57           9 :         if (fields.test(RedshiftColumn))
-      58           2 :                 *out << "\tz";
-      59           9 :         if (fields.test(SerialNumberColumn))
-      60           3 :                 *out << "\tSN";
-      61           9 :         if (fields.test(CurrentIdColumn))
-      62           8 :                 *out << "\tID";
-      63           9 :         if (fields.test(CurrentEnergyColumn))
-      64           8 :                 *out << "\tE";
-      65           9 :         if (fields.test(CurrentPositionColumn) && oneDimensional)
-      66           2 :                 *out << "\tX";
-      67           9 :         if (fields.test(CurrentPositionColumn) && not oneDimensional)
-      68           3 :                 *out << "\tX\tY\tZ";
-      69           9 :         if (fields.test(CurrentDirectionColumn) && not oneDimensional)
-      70           3 :                 *out << "\tPx\tPy\tPz";
-      71           9 :         if (fields.test(SerialNumberColumn))
-      72           3 :                 *out << "\tSN0";
-      73           9 :         if (fields.test(SourceIdColumn))
-      74           6 :                 *out << "\tID0";
-      75           9 :         if (fields.test(SourceEnergyColumn))
-      76           6 :                 *out << "\tE0";
-      77           9 :         if (fields.test(SourcePositionColumn) && oneDimensional) 
-      78           1 :                 *out << "\tX0";
-      79           9 :         if (fields.test(SourcePositionColumn) && not oneDimensional)
-      80           2 :                 *out << "\tX0\tY0\tZ0";
-      81           9 :         if (fields.test(SourceDirectionColumn) && not oneDimensional)
-      82           2 :                 *out << "\tP0x\tP0y\tP0z";
-      83           9 :         if (fields.test(SerialNumberColumn))
-      84           3 :                 *out << "\tSN1";
-      85           9 :         if (fields.test(CreatedIdColumn))
-      86           2 :                 *out << "\tID1";
-      87           9 :         if (fields.test(CreatedEnergyColumn))
-      88           2 :                 *out << "\tE1";
-      89           9 :         if (fields.test(CreatedPositionColumn) && oneDimensional)
-      90           1 :                 *out << "\tX1";
-      91           9 :         if (fields.test(CreatedPositionColumn) && not oneDimensional)
-      92           1 :                 *out << "\tX1\tY1\tZ1";
-      93           9 :         if (fields.test(CreatedDirectionColumn) && not oneDimensional)
-      94           1 :                 *out << "\tP1x\tP1y\tP1z";
-      95           9 :         if (fields.test(WeightColumn))
-      96           2 :                 *out << "\tW";
-      97           9 :         if (fields.test(CandidateTagColumn))
-      98           3 :                 *out << "\ttag";
-      99           9 :         for(std::vector<Property>::const_iterator iter = properties.begin();
-     100          10 :                         iter != properties.end(); ++iter)
-     101             :         {
-     102           1 :                 *out << "\t" << (*iter).name;
-     103             :         }
-     104             : 
-     105           9 :         *out << "\n#\n";
-     106           9 :         if (fields.test(TrajectoryLengthColumn))
-     107           6 :                 *out << "# D             Trajectory length [" << lengthScale / Mpc
-     108           6 :                                 << " Mpc]\n";
-     109           9 :         if (fields.test(RedshiftColumn))
-     110           2 :                 *out << "# z             Redshift\n";
-     111           9 :         if (fields.test(SerialNumberColumn))
-     112           3 :                 *out << "# SN/SN0/SN1    Serial number. Unique (within this run) id of the particle.\n";
-     113           1 :         if (fields.test(CurrentIdColumn) || fields.test(CreatedIdColumn)
-     114          10 :                         || fields.test(SourceIdColumn))
-     115           8 :                 *out << "# ID/ID0/ID1    Particle type (PDG MC numbering scheme)\n";
-     116           1 :         if (fields.test(CurrentEnergyColumn) || fields.test(CreatedEnergyColumn)
-     117          10 :                         || fields.test(SourceEnergyColumn))
-     118           8 :                 *out << "# E/E0/E1       Energy [" << energyScale / EeV << " EeV]\n";
-     119           4 :         if (fields.test(CurrentPositionColumn) || fields.test(CreatedPositionColumn)
-     120          13 :                         || fields.test(SourcePositionColumn))
-     121           5 :                 *out << "# X/X0/X1...    Position [" << lengthScale / Mpc << " Mpc]\n";
-     122             :         if (fields.test(CurrentDirectionColumn)
-     123           5 :                         || fields.test(CreatedDirectionColumn)
-     124          14 :                         || fields.test(SourceDirectionColumn))
-     125           4 :                 *out << "# Px/P0x/P1x... Heading (unit vector of momentum)\n";
-     126           9 :         if (fields.test(WeightColumn))
-     127           2 :                 *out << "# W             Weights" << " \n";
-     128           9 :         if (fields.test(CandidateTagColumn)) {
-     129           3 :                 *out << "# tag           Candidate tag can be given by the source feature (user defined tag) or by the following interaction process \n";
-     130           3 :                 *out << "#\tES  \tElasticScattering \n" << "#\tEPP \tElectronPairProduction \n" << "#\tEMPP\tEMPairProduction\n"
-     131             :                         << "#\tEMDP\tEMDoublePairProduction\n" << "#\tEMTP\tEMTripletPairProduction \n" << "#\tEMIC\tEMInverseComptonScattering\n"
-     132             :                         << "#\tND  \tNuclearDecay\n" << "#\tPD  \tPhotoDisintegration\n" << "#\tPPP  \tPhotoPionProduction\n" << "#\tSYN \tSynchrotronRadiation\n"
-     133           3 :                         << "#\tPRIM/SEC\t primary / secondary particle\n";
-     134             :         }
-     135           9 :         for(std::vector<Property>::const_iterator iter = properties.begin();
-     136          10 :                         iter != properties.end(); ++iter)
-     137             :         {
-     138           2 :                         *out << "# " << (*iter).name << " " << (*iter).comment << "\n";
-     139             :         }
-     140             : 
-     141           9 :         *out << "# no index = current, 0 = at source, 1 = at point of creation\n#\n";
-     142          18 :         *out << "# CRPropa version: " << g_GIT_DESC << "\n#\n";
-     143             : 
-     144           9 :         if (storeRandomSeeds)
-     145             :         {
-     146           0 :                 *out << "# Random seeds:\n";
-     147           0 :                 std::vector< std::vector<uint32_t> > seeds = Random::getSeedThreads();
-     148             : 
-     149           0 :                 for (size_t i =0; i < seeds.size(); i++)
-     150             :                 {
-     151           0 :                         std::string encoded_data = Base64::encode((unsigned char*) &seeds[i][0], sizeof(seeds[i][0]) * seeds[i].size() / sizeof(unsigned char));
-     152           0 :                         *out << "#   Thread " << i << ": ";
-     153           0 :                         *out << encoded_data;
-     154           0 :                         *out << "\n";
-     155             :                 }
-     156           0 :         }
-     157           9 : }
-     158             : 
-     159          54 : void TextOutput::process(Candidate *c) const {
-     160          54 :         if (fields.none() && properties.empty())
-     161           0 :                 return;
-     162             : 
-     163             :         char buffer[1024];
-     164             :         size_t p = 0;
-     165             : 
-     166          54 :         std::locale old_locale = std::locale::global(std::locale::classic());
-     167             : 
-     168          54 :         if (fields.test(TrajectoryLengthColumn))
-     169          51 :                 p += std::sprintf(buffer + p, "%8.5E\t",
-     170          51 :                                 c->getTrajectoryLength() / lengthScale);
-     171             : 
-     172          54 :         if (fields.test(RedshiftColumn))
-     173          47 :                 p += std::sprintf(buffer + p, "%1.5E\t", c->getRedshift());
-     174             : 
-     175          54 :         if (fields.test(SerialNumberColumn))
-     176          48 :                 p += std::sprintf(buffer + p, "%10lu\t",
-     177             :                                 c->getSerialNumber());
-     178          54 :         if (fields.test(CurrentIdColumn))
-     179          53 :                 p += std::sprintf(buffer + p, "%10i\t", c->current.getId());
-     180          54 :         if (fields.test(CurrentEnergyColumn))
-     181          53 :                 p += std::sprintf(buffer + p, "%8.5E\t",
-     182          53 :                                 c->current.getEnergy() / energyScale);
-     183          54 :         if (fields.test(CurrentPositionColumn)) {
-     184          50 :                 if (oneDimensional) {
-     185          37 :                         p += std::sprintf(buffer + p, "%8.5E\t",
-     186          37 :                                         c->current.getPosition().x / lengthScale);
-     187             :                 } else {
-     188          13 :                         const Vector3d pos = c->current.getPosition() / lengthScale;
-     189          13 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
-     190             :                                         pos.z);
-     191             :                 }
-     192             :         }
-     193          54 :         if (fields.test(CurrentDirectionColumn)) {
-     194          49 :                 if (not oneDimensional) {
-     195          13 :                         const Vector3d pos = c->current.getDirection();
-     196          13 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
-     197             :                                         pos.z);
-     198             :                 }
-     199             :         }
-     200             : 
-     201          54 :         if (fields.test(SerialNumberColumn))
-     202          48 :                 p += std::sprintf(buffer + p, "%10lu\t", c->getSourceSerialNumber());
-     203          54 :         if (fields.test(SourceIdColumn))
-     204          51 :                 p += std::sprintf(buffer + p, "%10i\t", c->source.getId());
-     205          54 :         if (fields.test(SourceEnergyColumn))
-     206          51 :                 p += std::sprintf(buffer + p, "%8.5E\t",
-     207          51 :                                 c->source.getEnergy() / energyScale);
-     208          54 :         if (fields.test(SourcePositionColumn)) {
-     209          48 :                 if (oneDimensional) {
-     210          36 :                         p += std::sprintf(buffer + p, "%8.5E\t",
-     211          36 :                                         c->source.getPosition().x / lengthScale);
-     212             :                 } else {
-     213          12 :                         const Vector3d pos = c->source.getPosition() / lengthScale;
-     214          12 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
-     215             :                                         pos.z);
-     216             :                 }
-     217             :         }
-     218          54 :         if (fields.test(SourceDirectionColumn)) {
-     219          48 :                 if (not oneDimensional) {
-     220          12 :                         const Vector3d pos = c->source.getDirection();
-     221          12 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
-     222             :                                         pos.z);
-     223             :                 }
-     224             : 
-     225             :         }
-     226             : 
-     227          54 :         if (fields.test(SerialNumberColumn))
-     228          48 :                 p += std::sprintf(buffer + p, "%10lu\t",
-     229             :                                 c->getCreatedSerialNumber());
-     230          54 :         if (fields.test(CreatedIdColumn))
-     231          47 :                 p += std::sprintf(buffer + p, "%10i\t", c->created.getId());
-     232          54 :         if (fields.test(CreatedEnergyColumn))
-     233          47 :                 p += std::sprintf(buffer + p, "%8.5E\t",
-     234          47 :                                 c->created.getEnergy() / energyScale);
-     235          54 :         if (fields.test(CreatedPositionColumn)) {
-     236          47 :                 if (oneDimensional) {
-     237          36 :                         p += std::sprintf(buffer + p, "%8.5E\t",
-     238          36 :                                         c->created.getPosition().x / lengthScale);
-     239             :                 } else {
-     240          11 :                         const Vector3d pos = c->created.getPosition() / lengthScale;
-     241          11 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
-     242             :                                         pos.z);
-     243             :                 }
-     244             :         }
-     245          54 :         if (fields.test(CreatedDirectionColumn)) {
-     246          47 :                 if (not oneDimensional) {
-     247          11 :                         const Vector3d pos = c->created.getDirection();
-     248          11 :                         p += std::sprintf(buffer + p, "%8.5E\t%8.5E\t%8.5E\t", pos.x, pos.y,
-     249             :                                         pos.z);
-     250             :                 }
-     251             :         }
-     252          54 :         if (fields.test(WeightColumn)) {
-     253          47 :                 p += std::sprintf(buffer + p, "%8.5E\t", c->getWeight());
-     254             :         }
-     255          54 :         if (fields.test(CandidateTagColumn)) {
-     256          48 :                 p += std::sprintf(buffer + p, "%s\t", c->getTagOrigin().c_str());
-     257             :         }
-     258             : 
-     259          54 :         for(std::vector<Output::Property>::const_iterator iter = properties.begin();
-     260          55 :                         iter != properties.end(); ++iter) {
-     261           1 :                   Variant v;
-     262           1 :                         if (c->hasProperty((*iter).name)) {
-     263           0 :                                 v = c->getProperty((*iter).name);
-     264             :                         } else {
-     265           1 :                                 v = (*iter).defaultValue;
-     266             :                         }
-     267           1 :                         p += std::sprintf(buffer + p, "%s", v.toString("\t").c_str());
-     268           1 :                         p += std::sprintf(buffer + p, "\t");
-     269           1 :         }
-     270          54 :         buffer[p - 1] = '\n';
-     271             : 
-     272          54 :         std::locale::global(old_locale);
-     273             : 
-     274         108 : #pragma omp critical
-     275             :         {
-     276          54 :                 if (count == 0)
-     277           9 :                         printHeader();
-     278          54 :                 Output::process(c);
-     279          54 :                 out->write(buffer, p);
-     280             :         }
-     281             : 
-     282          54 : }
-     283             : 
-     284           1 : void TextOutput::load(const std::string &filename, ParticleCollector *collector){
-     285             : 
-     286             :         std::string line;
-     287             :         std::istream *in;
-     288           1 :         std::ifstream infile(filename.c_str());
-     289             :         
-     290             :         double lengthScale = Mpc; // default Mpc
-     291             :         double energyScale = EeV; // default EeV
-     292             : 
-     293           1 :         if (!infile.good())
-     294           0 :                 throw std::runtime_error("crpropa::TextOutput: could not open file " + filename);
-     295             :         in = &infile;
-     296             :         
-     297           2 :         if (kiss::ends_with(filename, ".gz")){
-     298             : #ifdef CRPROPA_HAVE_ZLIB
-     299           0 :                 in = new zstream::igzstream(*in);
-     300             : #else
-     301             :                 throw std::runtime_error("CRPropa was built without Zlib compression!");
-     302             : #endif
-     303             :         }
-     304             : 
-     305          38 :         while (std::getline(*in, line)) {
-     306          37 :                 std::stringstream stream(line);
-     307          37 :                 if (stream.peek() == '#')
-     308             :                         continue;
-     309             : 
-     310          22 :                 ref_ptr<Candidate> c = new Candidate(); 
-     311             :                 double val_d; int val_i;
-     312             :                 double x, y, z;
-     313             :                 stream >> val_d;
-     314          11 :                 c->setTrajectoryLength(val_d*lengthScale); // D
-     315             :                 stream >> val_d;
-     316          11 :                 c->setRedshift(val_d); // z
-     317          11 :                 stream >> val_i;
-     318          11 :                 c->setSerialNumber(val_i); // SN
-     319          11 :                 stream >> val_i;
-     320          11 :                 c->current.setId(val_i); // ID
-     321             :                 stream >> val_d;
-     322          11 :                 c->current.setEnergy(val_d*energyScale); // E
-     323             :                 stream >> x >> y >> z;
-     324          11 :                 c->current.setPosition(Vector3d(x, y, z)*lengthScale); // X, Y, Z
-     325             :                 stream >> x >> y >> z;
-     326          11 :                 c->current.setDirection(Vector3d(x, y, z)*lengthScale); // Px, Py, Pz
-     327          11 :                 stream >> val_i; // SN0 (TODO: Reconstruct the parent-child relationship)
-     328          11 :                 stream >> val_i;
-     329          11 :                 c->source.setId(val_i); // ID0
-     330             :                 stream >> val_d;
-     331          11 :                 c->source.setEnergy(val_d*energyScale);      // E0
-     332             :                 stream >> x >> y >> z;
-     333          11 :                 c->source.setPosition(Vector3d(x, y, z)*lengthScale); // X0, Y0, Z0
-     334             :                 stream >> x >> y >> z;
-     335          11 :                 c->source.setDirection(Vector3d(x, y, z)*lengthScale); // P0x, P0y, P0z
-     336          11 :                 stream >> val_i; // SN1
-     337          11 :                 stream >> val_i;
-     338          11 :                 c->created.setId(val_i); // ID1
-     339             :                 stream >> val_d;
-     340          11 :                 c->created.setEnergy(val_d*energyScale); // E1
-     341             :                 stream >> x >> y >> z;
-     342          11 :                 c->created.setPosition(Vector3d(x, y, z)*lengthScale); // X1, Y1, Z1
-     343             :                 stream >> x >> y >> z;
-     344          11 :                 c->created.setDirection(Vector3d(x, y, z)*lengthScale); // P1x, P1y, P1z
-     345             :                 stream >> val_d;
-     346          11 :                 c->setWeight(val_d); // W
-     347             : 
-     348          22 :                 collector->process(c);
-     349          37 :         }
-     350           1 :         infile.close();
-     351           2 : }
-     352             : 
-     353           0 : std::string TextOutput::getDescription() const {
-     354           0 :         return "TextOutput";
-     355             : }
-     356             : 
-     357          10 : void TextOutput::close() {
-     358             : #ifdef CRPROPA_HAVE_ZLIB
-     359          10 :         zstream::ogzstream *zs = dynamic_cast<zstream::ogzstream *>(out);
-     360          10 :         if (zs) {
-     361           0 :                 zs->close();
-     362           0 :                 delete out;
-     363           0 :                 out = 0;
-     364             :         }
-     365             : #endif
-     366          10 :         outfile.flush();
-     367          10 : }
-     368             : 
-     369          10 : TextOutput::~TextOutput() {
-     370           9 :         close();
-     371          10 : }
-     372             : 
-     373           0 : void TextOutput::gzip() {
-     374             : #ifdef CRPROPA_HAVE_ZLIB
-     375           0 :         out = new zstream::ogzstream(*out);
-     376             : #else
-     377             :         throw std::runtime_error("CRPropa was built without Zlib compression!");
-     378             : #endif
-     379           0 : }
-     380             : 
-     381             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Tools.cpp.func-sort-c.html b/doc/coverageReport/src/module/Tools.cpp.func-sort-c.html deleted file mode 100644 index ec6611df0..000000000 --- a/doc/coverageReport/src/module/Tools.cpp.func-sort-c.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Tools.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Tools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:77010.0 %
Date:2024-04-08 14:58:22Functions:21612.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14ParticleFilter5addIdEi0
_ZN7crpropa14ParticleFilter6getIdsEv0
_ZN7crpropa14ParticleFilter8removeIdEi0
_ZN7crpropa14ParticleFilterC2Ev0
_ZN7crpropa17EmissionMapFiller14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17EmissionMapFillerC2EPNS_11EmissionMapE0
_ZN7crpropa17PerformanceModule3addEPNS_6ModuleE0
_ZN7crpropa17PerformanceModuleD0Ev0
_ZN7crpropa17PerformanceModuleD2Ev0
_ZNK7crpropa14ParticleFilter14getDescriptionB5cxx11Ev0
_ZNK7crpropa17EmissionMapFiller14getDescriptionB5cxx11Ev0
_ZNK7crpropa17EmissionMapFiller7processEPNS_9CandidateE0
_ZNK7crpropa17PerformanceModule14getDescriptionB5cxx11Ev0
_ZNK7crpropa17PerformanceModule7processEPNS_9CandidateE0
_ZN7crpropa14ParticleFilterC2ERKSt3setIiSt4lessIiESaIiEE1
_ZNK7crpropa14ParticleFilter7processEPNS_9CandidateE7
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Tools.cpp.func.html b/doc/coverageReport/src/module/Tools.cpp.func.html deleted file mode 100644 index 23037d8e8..000000000 --- a/doc/coverageReport/src/module/Tools.cpp.func.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Tools.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Tools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:77010.0 %
Date:2024-04-08 14:58:22Functions:21612.5 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa14ParticleFilter5addIdEi0
_ZN7crpropa14ParticleFilter6getIdsEv0
_ZN7crpropa14ParticleFilter8removeIdEi0
_ZN7crpropa14ParticleFilterC2ERKSt3setIiSt4lessIiESaIiEE1
_ZN7crpropa14ParticleFilterC2Ev0
_ZN7crpropa17EmissionMapFiller14setEmissionMapEPNS_11EmissionMapE0
_ZN7crpropa17EmissionMapFillerC2EPNS_11EmissionMapE0
_ZN7crpropa17PerformanceModule3addEPNS_6ModuleE0
_ZN7crpropa17PerformanceModuleD0Ev0
_ZN7crpropa17PerformanceModuleD2Ev0
_ZNK7crpropa14ParticleFilter14getDescriptionB5cxx11Ev0
_ZNK7crpropa14ParticleFilter7processEPNS_9CandidateE7
_ZNK7crpropa17EmissionMapFiller14getDescriptionB5cxx11Ev0
_ZNK7crpropa17EmissionMapFiller7processEPNS_9CandidateE0
_ZNK7crpropa17PerformanceModule14getDescriptionB5cxx11Ev0
_ZNK7crpropa17PerformanceModule7processEPNS_9CandidateE0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/Tools.cpp.gcov.html b/doc/coverageReport/src/module/Tools.cpp.gcov.html deleted file mode 100644 index 050d3fde4..000000000 --- a/doc/coverageReport/src/module/Tools.cpp.gcov.html +++ /dev/null @@ -1,199 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module/Tools.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/module - Tools.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:77010.0 %
Date:2024-04-08 14:58:22Functions:21612.5 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/module/Tools.h"
-       2             : #include "crpropa/Clock.h"
-       3             : 
-       4             : #include <iostream>
-       5             : #include <sstream>
-       6             : 
-       7             : using namespace std;
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11           0 : PerformanceModule::~PerformanceModule() {
-      12             :         double total = 0;
-      13           0 :         for (size_t i = 0; i < modules.size(); i++) {
-      14             :                 _module_info &m = modules[i];
-      15           0 :                 total += m.time;
-      16             :         }
-      17           0 :         cout << "Performance for " << calls << " calls:" << endl;
-      18           0 :         for (size_t i = 0; i < modules.size(); i++) {
-      19             :                 _module_info &m = modules[i];
-      20           0 :                 cout << " - " << floor((1000 * m.time / total) + 0.5) / 10 << "% -> "
-      21           0 :                                 << m.module->getDescription() << ": " << (m.time / calls)
-      22             :                                 << endl;
-      23             :         }
-      24           0 : }
-      25             : 
-      26           0 : void PerformanceModule::add(Module *module) {
-      27             :         _module_info info;
-      28           0 :         info.module = module;
-      29           0 :         info.time = 0;
-      30           0 :         modules.push_back(info);
-      31           0 : }
-      32             : 
-      33           0 : void PerformanceModule::process(Candidate *candidate) const {
-      34           0 :         vector<double> times(modules.size());
-      35           0 :         for (size_t i = 0; i < modules.size(); i++) {
-      36             :                 _module_info &m = modules[i];
-      37           0 :                 double start = Clock::getInstance().getMillisecond();
-      38           0 :                 m.module->process(candidate);
-      39           0 :                 double end = Clock::getInstance().getMillisecond();
-      40           0 :                 times[i] = end - start;
-      41             :         }
-      42             : 
-      43           0 : #pragma omp critical
-      44             :         {
-      45           0 :                 for (size_t i = 0; i < modules.size(); i++) {
-      46             :                         _module_info &m = modules[i];
-      47           0 :                         m.time += times[i];
-      48             :                 }
-      49           0 :                 calls++;
-      50             :         }
-      51           0 : }
-      52             : 
-      53           0 : string PerformanceModule::getDescription() const {
-      54           0 :         stringstream sstr;
-      55           0 :         sstr << "PerformanceModule (";
-      56           0 :         for (size_t i = 0; i < modules.size(); i++) {
-      57             :                 _module_info &m = modules[i];
-      58           0 :                 if (i > 0)
-      59           0 :                         sstr << ", ";
-      60           0 :                 sstr << m.module->getDescription();
-      61             :         }
-      62           0 :         sstr << ")";
-      63           0 :         return sstr.str();
-      64           0 : }
-      65             : 
-      66             : // ----------------------------------------------------------------------------
-      67           0 : ParticleFilter::ParticleFilter() {
-      68             : 
-      69           0 : }
-      70           1 : ParticleFilter::ParticleFilter(const std::set<int> &ids) : ids(ids) {
-      71             : 
-      72           1 : }
-      73           0 : void ParticleFilter::addId(int id) {
-      74             :         ids.insert(id);
-      75           0 : }
-      76           0 : void ParticleFilter::removeId(int id) {
-      77             :         ids.erase(id);
-      78           0 : }
-      79             : 
-      80           0 : std::set<int> &ParticleFilter::getIds() {
-      81           0 :         return ids;
-      82             : }
-      83             : 
-      84           7 : void ParticleFilter::process(Candidate* candidate) const {
-      85          14 :         if (ids.find(candidate->current.getId()) == ids.end())
-      86           5 :                 reject(candidate);
-      87             :         else
-      88           2 :                 accept(candidate);
-      89           7 : }
-      90             : 
-      91           0 : string ParticleFilter::getDescription() const {
-      92           0 :         stringstream sstr;
-      93           0 :         sstr << "ParticleFilter: ";
-      94           0 :         for (std::set<int>::const_iterator i = ids.begin(); i != ids.end(); i++) {
-      95           0 :                 sstr << *i << ", ";
-      96             :         }
-      97           0 :         sstr << ")";
-      98           0 :         return sstr.str();
-      99           0 : }
-     100             : 
-     101             : // ----------------------------------------------------------------------------
-     102           0 : EmissionMapFiller::EmissionMapFiller(EmissionMap *emissionMap) : emissionMap(emissionMap) {
-     103             : 
-     104           0 : }
-     105             : 
-     106           0 : void EmissionMapFiller::setEmissionMap(EmissionMap *emissionMap) {
-     107           0 :         this->emissionMap = emissionMap;
-     108           0 : }
-     109             : 
-     110           0 : void EmissionMapFiller::process(Candidate* candidate) const {
-     111           0 :         if (emissionMap) {
-     112           0 :                 #pragma omp critical
-     113             :                 {
-     114           0 :                         emissionMap->fillMap(candidate->source);
-     115             :                 }
-     116             :         }
-     117           0 : }
-     118             : 
-     119           0 : string EmissionMapFiller::getDescription() const {
-     120           0 :         return "EmissionMapFiller";
-     121             : }
-     122             : 
-     123             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/index-sort-f.html b/doc/coverageReport/src/module/index-sort-f.html deleted file mode 100644 index cb0181bfe..000000000 --- a/doc/coverageReport/src/module/index-sort-f.html +++ /dev/null @@ -1,383 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:2250354763.4 %
Date:2024-04-08 14:58:22Functions:28648559.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
OutputShell.cpp -
0.0%
-
0.0 %0 / 270.0 %0 / 6
PhotonOutput1D.cpp -
0.0%
-
0.0 %0 / 560.0 %0 / 9
Acceleration.cpp -
0.0%
-
0.0 %0 / 890.0 %0 / 14
Tools.cpp -
10.0%10.0%
-
10.0 %7 / 7012.5 %2 / 16
Redshift.cpp -
32.1%32.1%
-
32.1 %9 / 2825.0 %1 / 4
SimplePropagation.cpp -
36.4%36.4%
-
36.4 %12 / 3328.6 %2 / 7
HDF5Output.cpp -
5.0%5.0%
-
5.0 %12 / 24128.6 %4 / 14
MomentumDiffusion.cpp -
24.4%24.4%
-
24.4 %11 / 4530.0 %3 / 10
Observer.cpp -
44.4%44.4%
-
44.4 %80 / 18036.4 %16 / 44
BreakCondition.cpp -
36.6%36.6%
-
36.6 %63 / 17239.5 %15 / 38
Boundary.cpp -
48.4%48.4%
-
48.4 %106 / 21944.4 %20 / 45
SynchrotronRadiation.cpp -
61.8%61.8%
-
61.8 %81 / 13147.6 %10 / 21
PhotoPionProduction.cpp -
63.6%63.6%
-
63.6 %246 / 38760.0 %24 / 40
TextOutput.cpp -
88.0%88.0%
-
88.0 %219 / 24964.3 %9 / 14
RestrictToRegion.cpp -
50.0%50.0%
-
50.0 %6 / 1266.7 %2 / 3
ParticleCollector.cpp -
75.0%75.0%
-
75.0 %54 / 7270.8 %17 / 24
ElasticScattering.cpp -
90.0%90.0%
-
90.0 %63 / 7071.4 %5 / 7
PhotoDisintegration.cpp -
80.0%80.0%
-
80.0 %140 / 17583.3 %10 / 12
NuclearDecay.cpp -
81.5%81.5%
-
81.5 %137 / 16884.6 %11 / 13
Output.cpp -
89.8%89.8%
-
89.8 %88 / 9887.5 %14 / 16
DiffusionSDE.cpp -
76.2%76.2%
-
76.2 %154 / 20288.0 %22 / 25
ElectronPairProduction.cpp -
92.4%92.4%
-
92.4 %85 / 9290.0 %9 / 10
CandidateSplitting.cpp -
86.9%86.9%
-
86.9 %53 / 6190.9 %10 / 11
PropagationCK.cpp -
87.6%87.6%
-
87.6 %85 / 9792.9 %13 / 14
PropagationBP.cpp -
88.5%88.5%
-
88.5 %92 / 10493.8 %15 / 16
AdiabaticCooling.cpp -
85.2%85.2%
-
85.2 %23 / 27100.0 %5 / 5
EMDoublePairProduction.cpp -
94.4%94.4%
-
94.4 %68 / 72100.0 %10 / 10
EMTripletPairProduction.cpp -
94.0%94.0%
-
94.0 %94 / 100100.0 %11 / 11
EMInverseComptonScattering.cpp -
96.2%96.2%
-
96.2 %128 / 133100.0 %13 / 13
EMPairProduction.cpp -
97.8%97.8%
-
97.8 %134 / 137100.0 %13 / 13
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/index-sort-l.html b/doc/coverageReport/src/module/index-sort-l.html deleted file mode 100644 index aa76e709f..000000000 --- a/doc/coverageReport/src/module/index-sort-l.html +++ /dev/null @@ -1,383 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:2250354763.4 %
Date:2024-04-08 14:58:22Functions:28648559.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
OutputShell.cpp -
0.0%
-
0.0 %0 / 270.0 %0 / 6
PhotonOutput1D.cpp -
0.0%
-
0.0 %0 / 560.0 %0 / 9
Acceleration.cpp -
0.0%
-
0.0 %0 / 890.0 %0 / 14
HDF5Output.cpp -
5.0%5.0%
-
5.0 %12 / 24128.6 %4 / 14
Tools.cpp -
10.0%10.0%
-
10.0 %7 / 7012.5 %2 / 16
MomentumDiffusion.cpp -
24.4%24.4%
-
24.4 %11 / 4530.0 %3 / 10
Redshift.cpp -
32.1%32.1%
-
32.1 %9 / 2825.0 %1 / 4
SimplePropagation.cpp -
36.4%36.4%
-
36.4 %12 / 3328.6 %2 / 7
BreakCondition.cpp -
36.6%36.6%
-
36.6 %63 / 17239.5 %15 / 38
Observer.cpp -
44.4%44.4%
-
44.4 %80 / 18036.4 %16 / 44
Boundary.cpp -
48.4%48.4%
-
48.4 %106 / 21944.4 %20 / 45
RestrictToRegion.cpp -
50.0%50.0%
-
50.0 %6 / 1266.7 %2 / 3
SynchrotronRadiation.cpp -
61.8%61.8%
-
61.8 %81 / 13147.6 %10 / 21
PhotoPionProduction.cpp -
63.6%63.6%
-
63.6 %246 / 38760.0 %24 / 40
ParticleCollector.cpp -
75.0%75.0%
-
75.0 %54 / 7270.8 %17 / 24
DiffusionSDE.cpp -
76.2%76.2%
-
76.2 %154 / 20288.0 %22 / 25
PhotoDisintegration.cpp -
80.0%80.0%
-
80.0 %140 / 17583.3 %10 / 12
NuclearDecay.cpp -
81.5%81.5%
-
81.5 %137 / 16884.6 %11 / 13
AdiabaticCooling.cpp -
85.2%85.2%
-
85.2 %23 / 27100.0 %5 / 5
CandidateSplitting.cpp -
86.9%86.9%
-
86.9 %53 / 6190.9 %10 / 11
PropagationCK.cpp -
87.6%87.6%
-
87.6 %85 / 9792.9 %13 / 14
TextOutput.cpp -
88.0%88.0%
-
88.0 %219 / 24964.3 %9 / 14
PropagationBP.cpp -
88.5%88.5%
-
88.5 %92 / 10493.8 %15 / 16
Output.cpp -
89.8%89.8%
-
89.8 %88 / 9887.5 %14 / 16
ElasticScattering.cpp -
90.0%90.0%
-
90.0 %63 / 7071.4 %5 / 7
ElectronPairProduction.cpp -
92.4%92.4%
-
92.4 %85 / 9290.0 %9 / 10
EMTripletPairProduction.cpp -
94.0%94.0%
-
94.0 %94 / 100100.0 %11 / 11
EMDoublePairProduction.cpp -
94.4%94.4%
-
94.4 %68 / 72100.0 %10 / 10
EMInverseComptonScattering.cpp -
96.2%96.2%
-
96.2 %128 / 133100.0 %13 / 13
EMPairProduction.cpp -
97.8%97.8%
-
97.8 %134 / 137100.0 %13 / 13
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/src/module/index.html b/doc/coverageReport/src/module/index.html deleted file mode 100644 index 7af31a205..000000000 --- a/doc/coverageReport/src/module/index.html +++ /dev/null @@ -1,383 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - src/module - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - src/moduleHitTotalCoverage
Test:coverage.info.cleanedLines:2250354763.4 %
Date:2024-04-08 14:58:22Functions:28648559.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
Acceleration.cpp -
0.0%
-
0.0 %0 / 890.0 %0 / 14
AdiabaticCooling.cpp -
85.2%85.2%
-
85.2 %23 / 27100.0 %5 / 5
Boundary.cpp -
48.4%48.4%
-
48.4 %106 / 21944.4 %20 / 45
BreakCondition.cpp -
36.6%36.6%
-
36.6 %63 / 17239.5 %15 / 38
CandidateSplitting.cpp -
86.9%86.9%
-
86.9 %53 / 6190.9 %10 / 11
DiffusionSDE.cpp -
76.2%76.2%
-
76.2 %154 / 20288.0 %22 / 25
EMDoublePairProduction.cpp -
94.4%94.4%
-
94.4 %68 / 72100.0 %10 / 10
EMInverseComptonScattering.cpp -
96.2%96.2%
-
96.2 %128 / 133100.0 %13 / 13
EMPairProduction.cpp -
97.8%97.8%
-
97.8 %134 / 137100.0 %13 / 13
EMTripletPairProduction.cpp -
94.0%94.0%
-
94.0 %94 / 100100.0 %11 / 11
ElasticScattering.cpp -
90.0%90.0%
-
90.0 %63 / 7071.4 %5 / 7
ElectronPairProduction.cpp -
92.4%92.4%
-
92.4 %85 / 9290.0 %9 / 10
HDF5Output.cpp -
5.0%5.0%
-
5.0 %12 / 24128.6 %4 / 14
MomentumDiffusion.cpp -
24.4%24.4%
-
24.4 %11 / 4530.0 %3 / 10
NuclearDecay.cpp -
81.5%81.5%
-
81.5 %137 / 16884.6 %11 / 13
Observer.cpp -
44.4%44.4%
-
44.4 %80 / 18036.4 %16 / 44
Output.cpp -
89.8%89.8%
-
89.8 %88 / 9887.5 %14 / 16
OutputShell.cpp -
0.0%
-
0.0 %0 / 270.0 %0 / 6
ParticleCollector.cpp -
75.0%75.0%
-
75.0 %54 / 7270.8 %17 / 24
PhotoDisintegration.cpp -
80.0%80.0%
-
80.0 %140 / 17583.3 %10 / 12
PhotoPionProduction.cpp -
63.6%63.6%
-
63.6 %246 / 38760.0 %24 / 40
PhotonOutput1D.cpp -
0.0%
-
0.0 %0 / 560.0 %0 / 9
PropagationBP.cpp -
88.5%88.5%
-
88.5 %92 / 10493.8 %15 / 16
PropagationCK.cpp -
87.6%87.6%
-
87.6 %85 / 9792.9 %13 / 14
Redshift.cpp -
32.1%32.1%
-
32.1 %9 / 2825.0 %1 / 4
RestrictToRegion.cpp -
50.0%50.0%
-
50.0 %6 / 1266.7 %2 / 3
SimplePropagation.cpp -
36.4%36.4%
-
36.4 %12 / 3328.6 %2 / 7
SynchrotronRadiation.cpp -
61.8%61.8%
-
61.8 %81 / 13147.6 %10 / 21
TextOutput.cpp -
88.0%88.0%
-
88.0 %219 / 24964.3 %9 / 14
Tools.cpp -
10.0%10.0%
-
10.0 %7 / 7012.5 %2 / 16
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/index-sort-f.html b/doc/coverageReport/test/index-sort-f.html deleted file mode 100644 index d8992e401..000000000 --- a/doc/coverageReport/test/index-sort-f.html +++ /dev/null @@ -1,243 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - testHitTotalCoverage
Test:coverage.info.cleanedLines:3320339197.9 %
Date:2024-04-08 14:58:22Functions:26427396.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
testFunctionalGroups.cpp -
87.0%87.0%
-
87.0 %20 / 2350.0 %1 / 2
testModuleList.cpp -
94.5%94.5%
-
94.5 %52 / 5585.7 %6 / 7
testVector3.cpp -
96.8%96.8%
-
96.8 %90 / 9392.3 %12 / 13
testOutput.cpp -
96.9%96.9%
-
96.9 %157 / 16294.4 %17 / 18
testPropagation.cpp -
99.1%99.1%
-
99.1 %337 / 34094.7 %18 / 19
testSource.cpp -
98.6%98.6%
-
98.6 %279 / 28395.8 %23 / 24
testBreakCondition.cpp -
99.3%99.3%
-
99.3 %398 / 40196.8 %30 / 31
testInteraction.cpp -
94.4%94.4%
-
94.4 %743 / 78798.1 %52 / 53
testCore.cpp -
99.5%99.5%
-
99.5 %654 / 65798.3 %58 / 59
testCandidateSplitting.cpp -
100.0%
-
100.0 %47 / 47100.0 %2 / 2
testAdiabaticCooling.cpp -
100.0%
-
100.0 %23 / 23100.0 %2 / 2
testAdvectionField.cpp -
100.0%
-
100.0 %83 / 83100.0 %5 / 5
testMagneticLens.cpp -
100.0%
-
100.0 %87 / 87100.0 %7 / 7
testDensity.cpp -
100.0%
-
100.0 %166 / 166100.0 %7 / 7
testTurbulentField.cpp -
100.0%
-
100.0 %46 / 46100.0 %8 / 8
testMagneticField.cpp -
100.0%
-
100.0 %138 / 138100.0 %16 / 16
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/index-sort-l.html b/doc/coverageReport/test/index-sort-l.html deleted file mode 100644 index a458518a3..000000000 --- a/doc/coverageReport/test/index-sort-l.html +++ /dev/null @@ -1,243 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - testHitTotalCoverage
Test:coverage.info.cleanedLines:3320339197.9 %
Date:2024-04-08 14:58:22Functions:26427396.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
testFunctionalGroups.cpp -
87.0%87.0%
-
87.0 %20 / 2350.0 %1 / 2
testInteraction.cpp -
94.4%94.4%
-
94.4 %743 / 78798.1 %52 / 53
testModuleList.cpp -
94.5%94.5%
-
94.5 %52 / 5585.7 %6 / 7
testVector3.cpp -
96.8%96.8%
-
96.8 %90 / 9392.3 %12 / 13
testOutput.cpp -
96.9%96.9%
-
96.9 %157 / 16294.4 %17 / 18
testSource.cpp -
98.6%98.6%
-
98.6 %279 / 28395.8 %23 / 24
testPropagation.cpp -
99.1%99.1%
-
99.1 %337 / 34094.7 %18 / 19
testBreakCondition.cpp -
99.3%99.3%
-
99.3 %398 / 40196.8 %30 / 31
testCore.cpp -
99.5%99.5%
-
99.5 %654 / 65798.3 %58 / 59
testAdiabaticCooling.cpp -
100.0%
-
100.0 %23 / 23100.0 %2 / 2
testTurbulentField.cpp -
100.0%
-
100.0 %46 / 46100.0 %8 / 8
testCandidateSplitting.cpp -
100.0%
-
100.0 %47 / 47100.0 %2 / 2
testAdvectionField.cpp -
100.0%
-
100.0 %83 / 83100.0 %5 / 5
testMagneticLens.cpp -
100.0%
-
100.0 %87 / 87100.0 %7 / 7
testMagneticField.cpp -
100.0%
-
100.0 %138 / 138100.0 %16 / 16
testDensity.cpp -
100.0%
-
100.0 %166 / 166100.0 %7 / 7
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/index.html b/doc/coverageReport/test/index.html deleted file mode 100644 index 8374654ca..000000000 --- a/doc/coverageReport/test/index.html +++ /dev/null @@ -1,243 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - testHitTotalCoverage
Test:coverage.info.cleanedLines:3320339197.9 %
Date:2024-04-08 14:58:22Functions:26427396.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Filename Sort by nameLine Coverage Sort by line coverageFunctions Sort by function coverage
testAdiabaticCooling.cpp -
100.0%
-
100.0 %23 / 23100.0 %2 / 2
testAdvectionField.cpp -
100.0%
-
100.0 %83 / 83100.0 %5 / 5
testBreakCondition.cpp -
99.3%99.3%
-
99.3 %398 / 40196.8 %30 / 31
testCandidateSplitting.cpp -
100.0%
-
100.0 %47 / 47100.0 %2 / 2
testCore.cpp -
99.5%99.5%
-
99.5 %654 / 65798.3 %58 / 59
testDensity.cpp -
100.0%
-
100.0 %166 / 166100.0 %7 / 7
testFunctionalGroups.cpp -
87.0%87.0%
-
87.0 %20 / 2350.0 %1 / 2
testInteraction.cpp -
94.4%94.4%
-
94.4 %743 / 78798.1 %52 / 53
testMagneticField.cpp -
100.0%
-
100.0 %138 / 138100.0 %16 / 16
testMagneticLens.cpp -
100.0%
-
100.0 %87 / 87100.0 %7 / 7
testModuleList.cpp -
94.5%94.5%
-
94.5 %52 / 5585.7 %6 / 7
testOutput.cpp -
96.9%96.9%
-
96.9 %157 / 16294.4 %17 / 18
testPropagation.cpp -
99.1%99.1%
-
99.1 %337 / 34094.7 %18 / 19
testSource.cpp -
98.6%98.6%
-
98.6 %279 / 28395.8 %23 / 24
testTurbulentField.cpp -
100.0%
-
100.0 %46 / 46100.0 %8 / 8
testVector3.cpp -
96.8%96.8%
-
96.8 %90 / 9392.3 %12 / 13
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html b/doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html deleted file mode 100644 index 32530ff4f..000000000 --- a/doc/coverageReport/test/testAdiabaticCooling.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testAdiabaticCooling.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testAdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2323100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa34AdiabaticCooling_UniformField_Test8TestBodyEv1
_ZN7crpropa44AdiabaticCooling_ConstantSphericalField_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testAdiabaticCooling.cpp.func.html b/doc/coverageReport/test/testAdiabaticCooling.cpp.func.html deleted file mode 100644 index 2bf778f01..000000000 --- a/doc/coverageReport/test/testAdiabaticCooling.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testAdiabaticCooling.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testAdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2323100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa34AdiabaticCooling_UniformField_Test8TestBodyEv1
_ZN7crpropa44AdiabaticCooling_ConstantSphericalField_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html b/doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html deleted file mode 100644 index 6953c46a9..000000000 --- a/doc/coverageReport/test/testAdiabaticCooling.cpp.gcov.html +++ /dev/null @@ -1,131 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testAdiabaticCooling.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testAdiabaticCooling.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:2323100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Candidate.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/advectionField/AdvectionField.h"
-       5             : #include "crpropa/module/AdiabaticCooling.h"
-       6             : #include "gtest/gtest.h"
-       7             : 
-       8             : //#include <fstream>
-       9             : 
-      10             : namespace crpropa {
-      11             : 
-      12             : // AdiabaticCooling ---------------------------------------------------------------
-      13             : 
-      14           2 : TEST (AdiabaticCooling, UniformField) {
-      15             :         // Test in a uniform advection Field
-      16             : 
-      17           2 :         AdiabaticCooling AC(new UniformAdvectionField(Vector3d(1,0,0)));
-      18           1 :         Candidate c(nucleusId(1,1), 1e13*eV);
-      19           1 :         c.setCurrentStep(10*kpc);
-      20           1 :         c.setNextStep(10*kpc);
-      21           1 :         double E = c.current.getEnergy();
-      22           1 :         AC.process(&c);
-      23             : 
-      24             :         // Energy is expected to be conserved
-      25           1 :         EXPECT_DOUBLE_EQ(c.current.getEnergy(), E);
-      26           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 10*kpc);
-      27             : 
-      28             :         double limit = 0.2;
-      29           3 :         AdiabaticCooling AC2(new UniformAdvectionField(Vector3d(1,0,0)), limit);
-      30             :         
-      31           1 :         EXPECT_DOUBLE_EQ(AC2.getLimit(), limit);
-      32             : 
-      33             :         //
-      34             : 
-      35           1 : }
-      36             : 
-      37           2 : TEST (AdiabaticCooling, ConstantSphericalField) {
-      38             :         // Constant velocity vector
-      39             :         
-      40           2 :         AdiabaticCooling AC(new ConstantSphericalAdvectionField(Vector3d(0,0,0), 1));
-      41           1 :         Candidate c(nucleusId(1,1), 10);
-      42           1 :         c.current.setPosition(Vector3d(1,0,0));
-      43           1 :         c.setCurrentStep(c_light);
-      44           1 :         c.setNextStep(c_light);
-      45           1 :         double E = c.current.getEnergy();
-      46           1 :         AC.process(&c);
-      47             : 
-      48             :         // Check energy loss and step limitation
-      49           1 :         EXPECT_DOUBLE_EQ(c.current.getEnergy(), E/3.);
-      50           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 0.15*c_light);
-      51             : 
-      52           1 : }
-      53             : 
-      54             : 
-      55             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html b/doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html deleted file mode 100644 index f4debdd54..000000000 --- a/doc/coverageReport/test/testAdvectionField.cpp.func-sort-c.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testAdvectionField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testAdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8383100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testAdvectionFieldList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa41testUniformAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionShock_SimpleTest_Test8TestBodyEv1
_ZN7crpropa51testConstantSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testAdvectionField.cpp.func.html b/doc/coverageReport/test/testAdvectionField.cpp.func.html deleted file mode 100644 index c24ce98a8..000000000 --- a/doc/coverageReport/test/testAdvectionField.cpp.func.html +++ /dev/null @@ -1,92 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testAdvectionField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testAdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8383100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testAdvectionFieldList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa41testUniformAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
_ZN7crpropa43testSphericalAdvectionShock_SimpleTest_Test8TestBodyEv1
_ZN7crpropa51testConstantSphericalAdvectionField_SimpleTest_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testAdvectionField.cpp.gcov.html b/doc/coverageReport/test/testAdvectionField.cpp.gcov.html deleted file mode 100644 index e0ac90041..000000000 --- a/doc/coverageReport/test/testAdvectionField.cpp.gcov.html +++ /dev/null @@ -1,245 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testAdvectionField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testAdvectionField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8383100.0 %
Date:2024-04-08 14:58:22Functions:55100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/advectionField/AdvectionField.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/Common.h"
-       4             : 
-       5             : #include "gtest/gtest.h"
-       6             : #include <stdexcept>
-       7             : #include <cmath>
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11           2 : TEST(testUniformAdvectionField, SimpleTest) {
-      12           1 :         UniformAdvectionField A(Vector3d(-1, 5, 3));
-      13           1 :         Vector3d a = A.getField(Vector3d(1, 0, 0));
-      14           1 :         double D = A.getDivergence(Vector3d(1, 0, 0));
-      15           1 :         EXPECT_DOUBLE_EQ(a.x, -1);
-      16           1 :         EXPECT_DOUBLE_EQ(a.y, 5);
-      17           1 :         EXPECT_DOUBLE_EQ(a.z, 3);
-      18           1 :         EXPECT_DOUBLE_EQ(D, 0.);
-      19           1 : }
-      20             : 
-      21           2 : TEST(testAdvectionFieldList, SimpleTest) {
-      22             :         // Test a list of three advection fields
-      23             :         AdvectionFieldList A;
-      24           2 :         A.addField(new UniformAdvectionField(Vector3d(1, 0, 0)));
-      25           2 :         A.addField(new UniformAdvectionField(Vector3d(0, 2, 0)));
-      26           2 :         A.addField(new UniformAdvectionField(Vector3d(0, 0, 3)));
-      27           1 :         Vector3d a = A.getField(Vector3d(0.));
-      28           1 :         double D = A.getDivergence(Vector3d(1, 2, 3));
-      29           1 :         EXPECT_DOUBLE_EQ(a.x, 1);
-      30           1 :         EXPECT_DOUBLE_EQ(a.y, 2);
-      31           1 :         EXPECT_DOUBLE_EQ(a.z, 3);
-      32           1 :         EXPECT_DOUBLE_EQ(D, 0.);
-      33           1 : }
-      34             : 
-      35           2 : TEST(testConstantSphericalAdvectionField, SimpleTest) {
-      36             :         
-      37             :         Vector3d origin(1, 0, 0);
-      38             :         double V_wind(10);
-      39             :         
-      40           1 :         ConstantSphericalAdvectionField A(origin, V_wind);
-      41             :         
-      42             :         // Check the properties of the advection field
-      43           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().x, origin.x);
-      44           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().y, origin.y);
-      45           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().z, origin.z);
-      46             : 
-      47           1 :         EXPECT_DOUBLE_EQ(A.getVWind(), V_wind);
-      48             : 
-      49             :         // Field should be radial with center (1,0,0)
-      50             :         Vector3d Pos(2, 1, 1);
-      51           1 :         Vector3d V = A.getField(Pos);
-      52             : 
-      53           1 :         EXPECT_DOUBLE_EQ(V.x, 10.*pow(3, -0.5));
-      54           1 :         EXPECT_DOUBLE_EQ(V.y, 10.*pow(3, -0.5));
-      55           1 :         EXPECT_DOUBLE_EQ(V.z, 10.*pow(3, -0.5));
-      56             :         
-      57             :         // Divergence should be 2*V/r
-      58             :         Vector3d Pos2(2, 0, 0);
-      59           1 :         double D = A.getDivergence(Pos2);
-      60           1 :         EXPECT_DOUBLE_EQ(D, 2*10);
-      61           1 : }
-      62             : 
-      63           2 : TEST(testSphericalAdvectionField, SimpleTest) {
-      64             : 
-      65             :         Vector3d origin(1, 0, 0);
-      66             :         double R_max(10);
-      67             :         double V_max(1000);
-      68             :         double tau(3.);
-      69             :         double alpha(2.);
-      70             : 
-      71           1 :         SphericalAdvectionField A(origin, R_max, V_max, tau, alpha);
-      72             : 
-      73             :         // Check the properties of the advection field
-      74           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().x, origin.x);
-      75           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().y, origin.y);
-      76           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().z, origin.z);
-      77             :         
-      78           1 :         EXPECT_DOUBLE_EQ(A.getRadius(), R_max);
-      79           1 :         EXPECT_DOUBLE_EQ(A.getVMax(), V_max);
-      80           1 :         EXPECT_DOUBLE_EQ(A.getTau(), tau);
-      81           1 :         EXPECT_DOUBLE_EQ(A.getAlpha(), alpha);
-      82             : 
-      83             :         // Field/divergence should be zero for R>10
-      84           1 :         EXPECT_DOUBLE_EQ(A.getField(Vector3d(12,0,0)).getR(), 0.);
-      85           1 :         EXPECT_DOUBLE_EQ(A.getDivergence(Vector3d(12,0,0)), 0.);
-      86             : 
-      87             :         // Check field and divergence
-      88             :         Vector3d Pos(2, 0, 0);
-      89           1 :         Vector3d a = A.getField(Pos);
-      90           1 :         Vector3d a0 = a.getUnitVector();
-      91           1 :         double d = A.getDivergence(Pos);
-      92             : 
-      93           1 :         EXPECT_DOUBLE_EQ(a0.x, 1.);
-      94           1 :         EXPECT_DOUBLE_EQ(a0.y, 0.);
-      95           1 :         EXPECT_DOUBLE_EQ(a0.z, 0.);
-      96           1 :         EXPECT_DOUBLE_EQ(a.getR(), V_max*(1.-exp(-1./tau)) );
-      97             : 
-      98           1 :         EXPECT_NEAR(d, 1044.624919, 1e-5);
-      99             : 
-     100             :         // Check asymptotic of the Field
-     101           1 :         EXPECT_NEAR(A.getField(Vector3d(11, 0, 0)).getR(), 1000., 1e-4);
-     102             :         
-     103             :         // Divergence should be 2*V_max/r for r>>1
-     104           1 :         EXPECT_NEAR(A.getDivergence(Vector3d(11, 0, 0)), 2*1000./10., 1e-4);
-     105           1 : }
-     106             : 
-     107             : 
-     108           2 : TEST(testSphericalAdvectionShock, SimpleTest) {
-     109             : 
-     110             :         Vector3d origin(0, 0, 0);
-     111             :         double R_0(10);
-     112             :         double V_0(1000);
-     113             :         double lambda(0.1);
-     114             :         double R_rot(1.);
-     115             :         double V_rot(100);
-     116             :         
-     117             : 
-     118           1 :         SphericalAdvectionShock A(origin, R_0, V_0, lambda);
-     119             : 
-     120             :         // Check the properties of the advection field
-     121           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().x, origin.x);
-     122           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().y, origin.y);
-     123           1 :         EXPECT_DOUBLE_EQ(A.getOrigin().z, origin.z);
-     124             :         
-     125           1 :         EXPECT_DOUBLE_EQ(A.getR0(), R_0);
-     126           1 :         EXPECT_DOUBLE_EQ(A.getV0(), V_0);
-     127           1 :         EXPECT_DOUBLE_EQ(A.getLambda(), lambda);
-     128             : 
-     129             :         // Default values for R_Rot is R_0
-     130             :         // Default value for Azimuthal speed is 0
-     131           1 :         EXPECT_DOUBLE_EQ(A.getRRot(), R_0);
-     132           1 :         EXPECT_DOUBLE_EQ(A.getAzimuthalSpeed(), 0.);    
-     133             : 
-     134             :         // Field should drop to 0.625*V_0 at the shock 
-     135             :         // That's a difference to the analytic shock model where it should
-     136             :         // drop to v_r(R_0)=0.25*V_0.
-     137           1 :         EXPECT_DOUBLE_EQ(A.getField(Vector3d(R_0,0,0)).getR(), 0.625*V_0);
-     138             : 
-     139             :         // Field divergence should be zero for R>>R_0
-     140           1 :         EXPECT_NEAR(A.getDivergence(Vector3d(15,0,0)), 0., 1e-10);
-     141             : 
-     142             :         // Check field and divergence
-     143             :         Vector3d Pos(2, 0, 0);
-     144           1 :         Vector3d a = A.getField(Pos);
-     145           1 :         Vector3d a0 = a.getUnitVector();
-     146           1 :         double d = A.getDivergence(Pos);
-     147             : 
-     148           1 :         EXPECT_DOUBLE_EQ(a0.x, 1.);
-     149           1 :         EXPECT_DOUBLE_EQ(a0.y, 0.);
-     150           1 :         EXPECT_DOUBLE_EQ(a0.z, 0.);
-     151           1 :         EXPECT_DOUBLE_EQ(a.getR(), V_0);
-     152             :         
-     153             :         //Set explicitely the azimuthal rotation speed 
-     154           1 :         A.setRRot(R_rot);
-     155           1 :         A.setAzimuthalSpeed(V_rot);
-     156             :         
-     157           1 :         EXPECT_DOUBLE_EQ(A.getRRot(), R_rot);
-     158           1 :         EXPECT_DOUBLE_EQ(A.getAzimuthalSpeed(), V_rot); 
-     159             :         
-     160             :         Vector3d pos(1., 0., 0.);
-     161           1 :         Vector3d f = A.getField(pos);
-     162           1 :         EXPECT_DOUBLE_EQ(f.x, 1000.);
-     163           1 :         EXPECT_DOUBLE_EQ(f.y, 100.);
-     164           1 :         EXPECT_DOUBLE_EQ(f.z, 0.);      
-     165             : 
-     166             :         
-     167           1 : }
-     168             : 
-     169             : } //namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html b/doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html deleted file mode 100644 index fdc048a9d..000000000 --- a/doc/coverageReport/test/testBreakCondition.cpp.func-sort-c.html +++ /dev/null @@ -1,196 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testBreakCondition.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testBreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:39840199.3 %
Date:2024-04-08 14:58:22Functions:303196.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa20PeriodicBox_low_Test8TestBodyEv1
_ZN7crpropa21PeriodicBox_high_Test8TestBodyEv1
_ZN7crpropa23MinimumEnergy_test_Test8TestBodyEv1
_ZN7crpropa23ReflectiveBox_high_Test8TestBodyEv1
_ZN7crpropa25CubicBoundary_inside_Test8TestBodyEv1
_ZN7crpropa25DetectionLength_test_Test8TestBodyEv1
_ZN7crpropa25MinimumRedshift_test_Test8TestBodyEv1
_ZN7crpropa26CubicBoundary_outside_Test8TestBodyEv1
_ZN7crpropa26ObserverFeature_Point_Test8TestBodyEv1
_ZN7crpropa29MinimumChargeNumber_test_Test8TestBodyEv1
_ZN7crpropa29SphericalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa30ObserverFeature_DetectAll_Test8TestBodyEv1
_ZN7crpropa30SphericalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa31CylindricalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa31EllipsoidalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa32CylindricalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32EllipsoidalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_LargeSphere_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_SmallSphere_Test8TestBodyEv1
_ZN7crpropa32SphericalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepLower_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepUpper_Test8TestBodyEv1
_ZN7crpropa33MaximumTrajectoryLength_test_Test8TestBodyEv1
_ZN7crpropa34CylindricalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34EllipsoidalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34ObserverFeature_TimeEvolution_Test8TestBodyEv1
_ZN7crpropa36MinimumEnergyPerParticleId_test_Test8TestBodyEv1
_ZN7crpropa37MaximumTrajectoryLength_observer_Test8TestBodyEv1
_ZN7crpropa37ObserverFeature_TimeEvolutionLog_Test8TestBodyEv1
_ZN7crpropa38RestrictToRegion_RestrictToRegion_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testBreakCondition.cpp.func.html b/doc/coverageReport/test/testBreakCondition.cpp.func.html deleted file mode 100644 index 13dcf1aae..000000000 --- a/doc/coverageReport/test/testBreakCondition.cpp.func.html +++ /dev/null @@ -1,196 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testBreakCondition.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testBreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:39840199.3 %
Date:2024-04-08 14:58:22Functions:303196.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa20PeriodicBox_low_Test8TestBodyEv1
_ZN7crpropa21PeriodicBox_high_Test8TestBodyEv1
_ZN7crpropa23MinimumEnergy_test_Test8TestBodyEv1
_ZN7crpropa23ReflectiveBox_high_Test8TestBodyEv1
_ZN7crpropa25CubicBoundary_inside_Test8TestBodyEv1
_ZN7crpropa25DetectionLength_test_Test8TestBodyEv1
_ZN7crpropa25MinimumRedshift_test_Test8TestBodyEv1
_ZN7crpropa26CubicBoundary_outside_Test8TestBodyEv1
_ZN7crpropa26ObserverFeature_Point_Test8TestBodyEv1
_ZN7crpropa29MinimumChargeNumber_test_Test8TestBodyEv1
_ZN7crpropa29SphericalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa30ObserverFeature_DetectAll_Test8TestBodyEv1
_ZN7crpropa30SphericalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa31CylindricalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa31EllipsoidalBoundary_inside_Test8TestBodyEv1
_ZN7crpropa32CylindricalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32EllipsoidalBoundary_outside_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_LargeSphere_Test8TestBodyEv1
_ZN7crpropa32ObserverFeature_SmallSphere_Test8TestBodyEv1
_ZN7crpropa32SphericalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepLower_Test8TestBodyEv1
_ZN7crpropa33CubicBoundary_limitStepUpper_Test8TestBodyEv1
_ZN7crpropa33MaximumTrajectoryLength_test_Test8TestBodyEv1
_ZN7crpropa34CylindricalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34EllipsoidalBoundary_limitStep_Test8TestBodyEv1
_ZN7crpropa34ObserverFeature_TimeEvolution_Test8TestBodyEv1
_ZN7crpropa36MinimumEnergyPerParticleId_test_Test8TestBodyEv1
_ZN7crpropa37MaximumTrajectoryLength_observer_Test8TestBodyEv1
_ZN7crpropa37ObserverFeature_TimeEvolutionLog_Test8TestBodyEv1
_ZN7crpropa38RestrictToRegion_RestrictToRegion_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testBreakCondition.cpp.gcov.html b/doc/coverageReport/test/testBreakCondition.cpp.gcov.html deleted file mode 100644 index daded67ee..000000000 --- a/doc/coverageReport/test/testBreakCondition.cpp.gcov.html +++ /dev/null @@ -1,621 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testBreakCondition.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testBreakCondition.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:39840199.3 %
Date:2024-04-08 14:58:22Functions:303196.8 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /** Unit tests for break condition, observer, boundary and tool modules */
-       2             : 
-       3             : #include "crpropa/module/BreakCondition.h"
-       4             : #include "crpropa/module/Observer.h"
-       5             : #include "crpropa/module/Boundary.h"
-       6             : #include "crpropa/module/Tools.h"
-       7             : #include "crpropa/module/RestrictToRegion.h"
-       8             : #include "crpropa/ParticleID.h"
-       9             : #include "crpropa/Geometry.h"
-      10             : 
-      11             : #include "gtest/gtest.h"
-      12             : 
-      13             : namespace crpropa {
-      14             : 
-      15             : //** ========================= Break conditions ============================= */
-      16           1 : TEST(MinimumEnergy, test) {
-      17           1 :         MinimumEnergy minEnergy(5);
-      18           1 :         Candidate c;
-      19             : 
-      20           1 :         c.current.setEnergy(5.1);
-      21           1 :         minEnergy.process(&c);
-      22           1 :         EXPECT_TRUE(c.isActive());
-      23             : 
-      24           1 :         c.current.setEnergy(4.9);
-      25           1 :         minEnergy.process(&c);
-      26           1 :         EXPECT_FALSE(c.isActive());
-      27           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-      28           2 : }
-      29             : 
-      30           1 : TEST(MinimumChargeNumber, test) {
-      31           1 :         MinimumChargeNumber minChargeNumber(20);
-      32           1 :         Candidate c;
-      33             : 
-      34           1 :         c.current.setId(nucleusId(56, 26));
-      35           1 :         minChargeNumber.process(&c);
-      36           1 :         EXPECT_TRUE(c.isActive());
-      37             :         
-      38           1 :         c.current.setId(-nucleusId(56, 26));
-      39           1 :         minChargeNumber.process(&c);
-      40           1 :         EXPECT_TRUE(c.isActive());
-      41             : 
-      42           1 :         c.current.setId(nucleusId(4, 2));
-      43           1 :         minChargeNumber.process(&c);
-      44           1 :         EXPECT_FALSE(c.isActive());
-      45           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-      46             :         
-      47           1 :         c.setActive(true);
-      48           1 :         c.removeProperty("Rejected");
-      49             : 
-      50           1 :         c.current.setId(-nucleusId(4, 2));
-      51           1 :         minChargeNumber.process(&c);
-      52           1 :         EXPECT_FALSE(c.isActive());
-      53           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-      54           2 : }
-      55             : 
-      56           1 : TEST(MinimumEnergyPerParticleId, test) {
-      57           1 :         MinimumEnergyPerParticleId minEnergy(1);
-      58           1 :         minEnergy.add(22, 10);
-      59           1 :         minEnergy.add(12, 2);
-      60           1 :         minEnergy.add(11, 20);
-      61             : 
-      62           1 :         Candidate c;
-      63             : 
-      64           1 :         c.current.setEnergy(20);
-      65           1 :         c.current.setId(22);
-      66           1 :         minEnergy.process(&c);
-      67           1 :         EXPECT_TRUE(c.isActive());
-      68             : 
-      69           1 :         c.current.setEnergy(5);
-      70           1 :         c.current.setId(22);
-      71           1 :         minEnergy.process(&c);
-      72           1 :         EXPECT_FALSE(c.isActive());
-      73           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-      74             : 
-      75           1 :         c.setActive(true);
-      76           1 :         c.removeProperty("Rejected");
-      77             : 
-      78           1 :         c.current.setEnergy(10);
-      79           1 :         c.current.setId(11);
-      80           1 :         minEnergy.process(&c);
-      81           1 :         EXPECT_FALSE(c.isActive());
-      82           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-      83             : 
-      84           1 :         c.setActive(true);
-      85           1 :         c.removeProperty("Rejected");
-      86             : 
-      87           1 :         c.current.setEnergy(5);
-      88           1 :         c.current.setId(12);
-      89           1 :         minEnergy.process(&c);
-      90           1 :         EXPECT_TRUE(c.isActive());      
-      91             : 
-      92           1 :         c.current.setEnergy(0.1);
-      93           1 :         c.current.setId(12);
-      94           1 :         minEnergy.process(&c);
-      95           1 :         EXPECT_FALSE(c.isActive());
-      96           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-      97           1 : }
-      98             : 
-      99           1 : TEST(MaximumTrajectoryLength, test) {
-     100           1 :         MaximumTrajectoryLength maxLength(10);
-     101           1 :         Candidate c;
-     102             : 
-     103           1 :         c.setTrajectoryLength(9.9);
-     104           1 :         maxLength.process(&c);
-     105           1 :         EXPECT_TRUE(c.isActive());
-     106             : 
-     107           1 :         c.setTrajectoryLength(10.1);
-     108           1 :         maxLength.process(&c);
-     109           1 :         EXPECT_FALSE(c.isActive());
-     110           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-     111           1 : }
-     112             : 
-     113           1 : TEST(MaximumTrajectoryLength, observer) {
-     114           1 :         MaximumTrajectoryLength maxLength(12);
-     115           1 :         maxLength.addObserverPosition(Vector3d(10, 0, 0));
-     116           1 :         Candidate c;
-     117           1 :         c.current.setPosition(Vector3d(5, 0, 0));
-     118             : 
-     119           1 :         c.setTrajectoryLength(5);
-     120           1 :         maxLength.process(&c);
-     121           1 :         EXPECT_TRUE(c.isActive());
-     122             : 
-     123           1 :         c.setTrajectoryLength(8);
-     124           1 :         maxLength.process(&c);
-     125           1 :         EXPECT_FALSE(c.isActive());
-     126           1 : }
-     127             : 
-     128           1 : TEST(MinimumRedshift, test) {
-     129           1 :         MinimumRedshift minZ; // default minimum redshift of 0
-     130           1 :         Candidate c;
-     131             : 
-     132           1 :         c.setRedshift(0.1);
-     133           1 :         minZ.process(&c);
-     134           1 :         EXPECT_TRUE(c.isActive());
-     135             : 
-     136           1 :         c.setRedshift(0);
-     137           1 :         minZ.process(&c);
-     138           1 :         EXPECT_FALSE(c.isActive());
-     139           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-     140           2 : }
-     141             : 
-     142           1 : TEST(DetectionLength, test) {
-     143           1 :         DetectionLength detL(10);
-     144           1 :         detL.setMakeRejectedInactive(false);
-     145           1 :         Candidate c;
-     146           1 :         c.current.setPosition(Vector3d(5,0,0));
-     147             : 
-     148           1 :         c.setTrajectoryLength(2);
-     149           1 :         detL.process(&c);
-     150           1 :         EXPECT_TRUE(c.isActive());
-     151             :         
-     152           1 :         c.setCurrentStep(10);
-     153           1 :         c.setTrajectoryLength(12);
-     154           1 :         detL.process(&c);
-     155           1 :         EXPECT_TRUE(c.isActive());
-     156           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-     157           2 : }
-     158             : 
-     159             : //** ============================= Observers ================================ */
-     160           1 : TEST(ObserverFeature, SmallSphere) {
-     161             :         // detect if the current position is inside and the previous outside of the sphere
-     162           1 :         Observer obs;
-     163           1 :         obs.add(new ObserverSurface(new Sphere (Vector3d(0, 0, 0), 1)));
-     164           1 :         Candidate c;
-     165           1 :         c.setNextStep(10);
-     166             : 
-     167             :         // no detection: particle was inside already
-     168           1 :         c.current.setPosition(Vector3d(0.9, 0, 0));
-     169           1 :         c.previous.setPosition(Vector3d(0.95, 0, 0));
-     170           1 :         obs.process(&c);
-     171           1 :         EXPECT_TRUE(c.isActive());
-     172             : 
-     173             :         // limit step
-     174           1 :         EXPECT_NEAR(c.getNextStep(), 0.1, 0.001);
-     175             : 
-     176             :         // detection: particle just entered
-     177           1 :         c.current.setPosition(Vector3d(0.9, 0, 0));
-     178           1 :         c.previous.setPosition(Vector3d(1.1, 0, 0));
-     179           1 :         obs.process(&c);
-     180           1 :         EXPECT_FALSE(c.isActive());
-     181           1 : }
-     182             : 
-     183           1 : TEST(ObserverFeature, LargeSphere) {
-     184             :         // detect if the current position is outside and the previous inside of the sphere
-     185           1 :         Observer obs;
-     186           1 :         obs.add(new ObserverSurface(new Sphere (Vector3d(0, 0, 0), 10)));
-     187           1 :         Candidate c;
-     188           1 :         c.setNextStep(10);
-     189             : 
-     190             :         // no detection: particle was outside already
-     191           1 :         c.current.setPosition(Vector3d(11, 0, 0));
-     192           1 :         c.previous.setPosition(Vector3d(10.5, 0, 0));
-     193           1 :         obs.process(&c);
-     194           1 :         EXPECT_TRUE(c.isActive());
-     195             : 
-     196             :         // limit step
-     197           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 1);
-     198             : 
-     199             :         // detection: particle just left
-     200           1 :         c.current.setPosition(Vector3d(11, 0, 0));
-     201           1 :         c.previous.setPosition(Vector3d(9.5, 0, 0));
-     202           1 :         obs.process(&c);
-     203           1 :         EXPECT_FALSE(c.isActive());
-     204           1 : }
-     205             : 
-     206           1 : TEST(ObserverFeature, Point) {
-     207           1 :         Observer obs;
-     208           1 :         obs.add(new Observer1D());
-     209           1 :         Candidate c;
-     210           1 :         c.setNextStep(10);
-     211             : 
-     212             :         // no detection, limit step
-     213           1 :         c.current.setPosition(Vector3d(5, 0, 0));
-     214           1 :         obs.process(&c);
-     215           1 :         EXPECT_TRUE(c.isActive());
-     216             : 
-     217             :         // limit step
-     218           1 :         EXPECT_DOUBLE_EQ(5, c.getNextStep());
-     219             : 
-     220             :         // detection
-     221           1 :         c.current.setPosition(Vector3d(0, 0, 0));
-     222           1 :         obs.process(&c);
-     223           1 :         EXPECT_FALSE(c.isActive());
-     224           1 : }
-     225             : 
-     226           1 : TEST(ObserverFeature, DetectAll) {
-     227             :         // DetectAll should detect all candidates
-     228           1 :         Observer obs;
-     229           1 :         obs.add(new ObserverDetectAll());
-     230           1 :         Candidate c;
-     231           1 :         obs.process(&c);
-     232           1 :         EXPECT_FALSE(c.isActive());
-     233           1 : }
-     234             : 
-     235           1 : TEST(ObserverFeature, TimeEvolution) {
-     236           1 :   Observer obs;
-     237           1 :   obs.setDeactivateOnDetection(false);
-     238           2 :   obs.setFlag("Detected", "Detected");
-     239           1 :   obs.add(new ObserverTimeEvolution(5, 5, 2));
-     240           1 :   Candidate c;
-     241           1 :   c.setNextStep(10);
-     242           1 :   c.setTrajectoryLength(3);
-     243             :   
-     244             :   // no detection, limit next step
-     245           1 :   obs.process(&c);
-     246           1 :   EXPECT_TRUE(c.isActive());
-     247             : 
-     248             :   // limit step
-     249           1 :   EXPECT_DOUBLE_EQ(2, c.getNextStep());
-     250             :   
-     251             :   // detection one
-     252           1 :   c.setCurrentStep(0.1);
-     253           1 :   c.setTrajectoryLength(5);
-     254           1 :   obs.process(&c);
-     255           1 :   EXPECT_TRUE(c.isActive());
-     256           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
-     257             : 
-     258             :   // delete property
-     259           1 :   c.removeProperty("Detected");
-     260           1 :   EXPECT_FALSE(c.hasProperty("Detected"));
-     261             : 
-     262             :   // detection two
-     263           1 :   c.setCurrentStep(0.1);
-     264           1 :   c.setTrajectoryLength(10.05);
-     265           1 :   obs.process(&c);
-     266           1 :   EXPECT_TRUE(c.isActive());
-     267           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
-     268           1 : }
-     269             : 
-     270           1 : TEST(ObserverFeature, TimeEvolutionLog) {
-     271           1 :   Observer obs;
-     272           1 :   obs.setDeactivateOnDetection(false);
-     273           2 :   obs.setFlag("Detected", "Detected");
-     274             :   // usage of a log scaling for the observer
-     275             :   bool log = true;
-     276           1 :   obs.add(new ObserverTimeEvolution(5, 5, 2, log));
-     277           1 :   Candidate c;
-     278           1 :   c.setNextStep(10);
-     279           1 :   c.setTrajectoryLength(3);
-     280             :   
-     281             :   // no detection, limit next step
-     282           1 :   obs.process(&c);
-     283           1 :   EXPECT_TRUE(c.isActive());
-     284             : 
-     285             :   // limit step
-     286           1 :   EXPECT_DOUBLE_EQ(2, c.getNextStep());
-     287             :   
-     288             :   // detection one
-     289           1 :   c.setCurrentStep(0.1);
-     290           1 :   c.setTrajectoryLength(5);
-     291           1 :   obs.process(&c);
-     292           1 :   EXPECT_TRUE(c.isActive());
-     293           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
-     294             : 
-     295             :   // delete property
-     296           1 :   c.removeProperty("Detected");
-     297           1 :   EXPECT_FALSE(c.hasProperty("Detected"));
-     298             : 
-     299             :   // detection two
-     300           1 :   c.setCurrentStep(0.1);
-     301           1 :   c.setTrajectoryLength(10.05);
-     302           1 :   obs.process(&c);
-     303           1 :   EXPECT_TRUE(c.isActive());
-     304           2 :   EXPECT_TRUE(c.hasProperty("Detected"));
-     305           1 : }
-     306             : 
-     307             : //** ========================= Boundaries =================================== */
-     308           2 : TEST(PeriodicBox, high) {
-     309             :         // Tests if the periodical boundaries place the particle back inside the box and translate the initial position accordingly.
-     310             :         Vector3d origin(2, 2, 2);
-     311             :         Vector3d size(2, 2, 2);
-     312           1 :         PeriodicBox box(origin, size);
-     313             : 
-     314           1 :         Candidate c;
-     315           1 :         c.current.setPosition(Vector3d(4.5, 4.3, 4.4));
-     316           1 :         c.created.setPosition(Vector3d(3, 3, 3));
-     317             : 
-     318           1 :         box.process(&c);
-     319             : 
-     320           1 :         EXPECT_DOUBLE_EQ(2.5, c.current.getPosition().x);
-     321           1 :         EXPECT_DOUBLE_EQ(1, c.created.getPosition().x);
-     322           1 :         EXPECT_DOUBLE_EQ(2.3, c.current.getPosition().y);
-     323           1 :         EXPECT_DOUBLE_EQ(1, c.created.getPosition().y);
-     324           1 :         EXPECT_DOUBLE_EQ(2.4, c.current.getPosition().z);
-     325           1 :         EXPECT_DOUBLE_EQ(1, c.created.getPosition().z);
-     326           2 : }
-     327             : 
-     328           2 : TEST(PeriodicBox, low) {
-     329             :         // Tests if the periodical boundaries place the particle back inside the box and translate the initial position accordingly.
-     330             :         Vector3d origin(0, 0, 0);
-     331             :         Vector3d size(2, 2, 2);
-     332           1 :         PeriodicBox box(origin, size);
-     333             : 
-     334           1 :         Candidate c;
-     335           1 :         c.current.setPosition(Vector3d(-2.5, -0.3, -0.4));
-     336           1 :         c.created.setPosition(Vector3d(1, 1, 1));
-     337             : 
-     338           1 :         box.process(&c);
-     339             : 
-     340           1 :         EXPECT_DOUBLE_EQ(1.5, c.current.getPosition().x);
-     341           1 :         EXPECT_DOUBLE_EQ(5, c.created.getPosition().x);
-     342           1 :         EXPECT_DOUBLE_EQ(1.7, c.current.getPosition().y);
-     343           1 :         EXPECT_DOUBLE_EQ(3, c.created.getPosition().y);
-     344           1 :         EXPECT_DOUBLE_EQ(1.6, c.current.getPosition().z);
-     345           1 :         EXPECT_DOUBLE_EQ(3, c.created.getPosition().z);
-     346           2 : }
-     347             : 
-     348           2 : TEST(ReflectiveBox, high) {
-     349             :         // Tests if the reflective boundaries place the particle back inside the box and translate the initial position accordingly.
-     350             :         // Also the initial and final directions are to be reflected
-     351             :         Vector3d origin(10, 10, 10);
-     352             :         Vector3d size(10, 20, 20);
-     353           1 :         ReflectiveBox box(origin, size);
-     354             : 
-     355           1 :         Candidate c;
-     356           1 :         c.source.setPosition(Vector3d(16, 17, 18));
-     357           1 :         c.source.setDirection(Vector3d(1, 1.6, 1.8));
-     358           1 :         c.created.setPosition(Vector3d(15, 15, 15));
-     359           1 :         c.created.setDirection(Vector3d(0, 0.6, 0.8));
-     360           1 :         c.previous.setPosition(Vector3d(15, 15, 29.5));
-     361           1 :         c.previous.setDirection(Vector3d(0, 0.6, 0.8));
-     362           1 :         c.current.setPosition(Vector3d(15, 15, 30.5));
-     363           1 :         c.current.setDirection(Vector3d(0, 0.6, 0.8));
-     364             : 
-     365           1 :         box.process(&c);
-     366             : 
-     367           1 :         EXPECT_DOUBLE_EQ(16, c.source.getPosition().x);
-     368           1 :         EXPECT_DOUBLE_EQ(17, c.source.getPosition().y);
-     369           1 :         EXPECT_DOUBLE_EQ(42, c.source.getPosition().z);
-     370             : 
-     371           1 :         EXPECT_DOUBLE_EQ(15, c.created.getPosition().x);
-     372           1 :         EXPECT_DOUBLE_EQ(15, c.created.getPosition().y);
-     373           1 :         EXPECT_DOUBLE_EQ(45, c.created.getPosition().z);
-     374             : 
-     375           1 :         EXPECT_DOUBLE_EQ(15, c.previous.getPosition().x);
-     376           1 :         EXPECT_DOUBLE_EQ(15, c.previous.getPosition().y);
-     377           1 :         EXPECT_DOUBLE_EQ(30.5, c.previous.getPosition().z);
-     378             : 
-     379           1 :         EXPECT_DOUBLE_EQ(15, c.current.getPosition().x);
-     380           1 :         EXPECT_DOUBLE_EQ(15, c.current.getPosition().y);
-     381           1 :         EXPECT_DOUBLE_EQ(29.5, c.current.getPosition().z);
-     382             : 
-     383           1 :         EXPECT_DOUBLE_EQ(0, c.created.getDirection().x);
-     384           1 :         EXPECT_DOUBLE_EQ(0.6, c.created.getDirection().y);
-     385           1 :         EXPECT_DOUBLE_EQ(-0.8, c.created.getDirection().z);
-     386             : 
-     387           1 :         EXPECT_DOUBLE_EQ(0, c.previous.getDirection().x);
-     388           1 :         EXPECT_DOUBLE_EQ(0.6, c.previous.getDirection().y);
-     389           1 :         EXPECT_DOUBLE_EQ(-0.8, c.previous.getDirection().z);
-     390             : 
-     391           1 :         EXPECT_DOUBLE_EQ(0, c.current.getDirection().x);
-     392           1 :         EXPECT_DOUBLE_EQ(0.6, c.current.getDirection().y);
-     393           1 :         EXPECT_DOUBLE_EQ(-0.8, c.current.getDirection().z);
-     394           2 : }
-     395             : 
-     396           2 : TEST(CubicBoundary, inside) {
-     397           1 :         CubicBoundary cube(Vector3d(0, 0, 0), 10);
-     398           1 :         Candidate c;
-     399           1 :         c.current.setPosition(Vector3d(9, 5, 5));
-     400           1 :         cube.process(&c);
-     401           1 :         EXPECT_TRUE(c.isActive());
-     402           2 : }
-     403             : 
-     404           2 : TEST(CubicBoundary, outside) {
-     405           1 :         CubicBoundary cube(Vector3d(0, 0, 0), 10);
-     406           1 :         Candidate c;
-     407           1 :         c.current.setPosition(Vector3d(10.1, 5, 5));
-     408           1 :         cube.process(&c);
-     409           1 :         EXPECT_FALSE(c.isActive());
-     410           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-     411           2 : }
-     412             : 
-     413           2 : TEST(CubicBoundary, limitStepLower) {
-     414           1 :         CubicBoundary cube(Vector3d(10, 10, 10), 10);
-     415           1 :         cube.setLimitStep(true);
-     416           1 :         cube.setMargin(1);
-     417           1 :         Candidate c;
-     418           1 :         c.current.setPosition(Vector3d(15, 15, 10.5));
-     419           1 :         c.setNextStep(100);
-     420           1 :         cube.process(&c);
-     421           1 :         EXPECT_DOUBLE_EQ(1.5, c.getNextStep());
-     422           2 : }
-     423             : 
-     424           2 : TEST(CubicBoundary, limitStepUpper) {
-     425           1 :         CubicBoundary cube(Vector3d(-10, -10, -10), 10);
-     426           1 :         cube.setLimitStep(true);
-     427           1 :         cube.setMargin(1);
-     428           1 :         Candidate c;
-     429           1 :         c.current.setPosition(Vector3d(-5, -5, -0.5));
-     430           1 :         c.setNextStep(100);
-     431           1 :         cube.process(&c);
-     432           1 :         EXPECT_DOUBLE_EQ(1.5, c.getNextStep());
-     433           2 : }
-     434             : 
-     435           2 : TEST(SphericalBoundary, inside) {
-     436           1 :         SphericalBoundary sphere(Vector3d(0, 0, 0), 10);
-     437           1 :         Candidate c;
-     438           1 :         c.current.setPosition(Vector3d(9, 0, 0));
-     439           1 :         sphere.process(&c);
-     440           1 :         EXPECT_TRUE(c.isActive());
-     441           1 :         EXPECT_FALSE(c.hasProperty("Rejected"));
-     442           2 : }
-     443             : 
-     444           2 : TEST(SphericalBoundary, outside) {
-     445           1 :         SphericalBoundary sphere(Vector3d(0, 0, 0), 10);
-     446           2 :         sphere.setRejectFlag("I passed the galactic border", "Nothing happened");
-     447           1 :         Candidate c;
-     448           1 :         c.current.setPosition(Vector3d(0, -10.1, 0));
-     449           1 :         sphere.process(&c);
-     450           1 :         EXPECT_FALSE(c.isActive());
-     451           2 :         EXPECT_TRUE(c.hasProperty("I passed the galactic border"));
-     452           2 : }
-     453             : 
-     454           2 : TEST(SphericalBoundary, limitStep) {
-     455           1 :         SphericalBoundary sphere(Vector3d(0, 0, 0), 10);
-     456           1 :         sphere.setLimitStep(true);
-     457           1 :         sphere.setMargin(1);
-     458           1 :         Candidate c;
-     459           1 :         c.setNextStep(100);
-     460           1 :         c.current.setPosition(Vector3d(0, 0, 9.5));
-     461           1 :         sphere.process(&c);
-     462           1 :         EXPECT_DOUBLE_EQ(1.5, c.getNextStep());
-     463           2 : }
-     464             : 
-     465           2 : TEST(EllipsoidalBoundary, inside) {
-     466           1 :         EllipsoidalBoundary ellipsoid(Vector3d(-5, 0, 0), Vector3d(5, 0, 0), 15);
-     467           1 :         Candidate c;
-     468           1 :         c.current.setPosition(Vector3d(3, 2, 0));
-     469           1 :         ellipsoid.process(&c);
-     470           1 :         EXPECT_TRUE(c.isActive());
-     471           1 :         EXPECT_FALSE(c.hasProperty("Rejected"));
-     472           2 : }
-     473             : 
-     474           2 : TEST(EllipsoidalBoundary, outside) {
-     475           1 :         EllipsoidalBoundary ellipsoid(Vector3d(-5, 0, 0), Vector3d(5, 0, 0), 15);
-     476           1 :         Candidate c;
-     477           1 :         c.current.setPosition(Vector3d(0, 25, 0));
-     478           1 :         ellipsoid.process(&c);
-     479           1 :         EXPECT_FALSE(c.isActive());
-     480           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-     481           2 : }
-     482             : 
-     483           2 : TEST(EllipsoidalBoundary, limitStep) {
-     484           1 :         EllipsoidalBoundary ellipsoid(Vector3d(-5, 0, 0), Vector3d(5, 0, 0), 15);
-     485           1 :         ellipsoid.setLimitStep(true);
-     486           1 :         ellipsoid.setMargin(0.5);
-     487           1 :         Candidate c;
-     488           1 :         c.setNextStep(2);
-     489           1 :         c.current.setPosition(Vector3d(7, 0, 0));
-     490           1 :         ellipsoid.process(&c);
-     491           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 1.5);
-     492           2 : }
-     493             : 
-     494           2 : TEST(CylindricalBoundary, inside) {
-     495           1 :         CylindricalBoundary cylinder(Vector3d(0, 0, 0), 2, 15);
-     496           1 :         Candidate c;
-     497           1 :         c.current.setPosition(Vector3d(6, -3, 0.5));
-     498           1 :         cylinder.process(&c);
-     499           1 :         EXPECT_TRUE(c.isActive());
-     500           1 :         EXPECT_FALSE(c.hasProperty("Rejected"));
-     501           2 : }
-     502             : 
-     503           2 : TEST(CylindricalBoundary, outside) {
-     504           1 :         CylindricalBoundary cylinder(Vector3d(0, 0, 0), 2, 15);
-     505           1 :         Candidate c;
-     506           1 :         c.current.setPosition(Vector3d(6, -3, 1.5));
-     507           1 :         cylinder.process(&c);
-     508           1 :         EXPECT_FALSE(c.isActive());
-     509           2 :         EXPECT_TRUE(c.hasProperty("Rejected"));
-     510           2 : }
-     511             : 
-     512           2 : TEST(CylindricalBoundary, limitStep) {
-     513           1 :         CylindricalBoundary cylinder(Vector3d(0, 0, 0), 2, 15);
-     514           1 :         cylinder.setLimitStep(true);
-     515           1 :         cylinder.setMargin(0.5);
-     516           1 :         Candidate c;
-     517           1 :         c.setNextStep(2);
-     518           1 :         c.current.setPosition(Vector3d(7, 0, 0));
-     519           1 :         cylinder.process(&c);
-     520           1 :         EXPECT_DOUBLE_EQ(c.getNextStep(), 1.5);
-     521           2 : }
-     522             : 
-     523           1 : TEST(RestrictToRegion, RestrictToRegion) {
-     524             : 
-     525           1 :         ref_ptr<Observer> obs = new Observer();
-     526           1 :         obs->add(new ObserverDetectAll());
-     527           1 :         RestrictToRegion R(obs, new Sphere(Vector3d(0, 0, 0), 10));
-     528             : 
-     529           1 :         Candidate c;
-     530           1 :         c.previous.setPosition(Vector3d(13,0,0));
-     531           1 :         c.current.setPosition(Vector3d(12,0,0));
-     532           1 :         R.process(&c);
-     533           1 :         EXPECT_TRUE(c.isActive());
-     534           1 :         c.current.setPosition(Vector3d(9,0,0));
-     535           1 :         R.process(&c);
-     536           1 :         EXPECT_FALSE(c.isActive());
-     537           2 : }
-     538             : 
-     539             : 
-     540           0 : int main(int argc, char **argv) {
-     541           0 :         ::testing::InitGoogleTest(&argc, argv);
-     542           0 :         return RUN_ALL_TESTS();
-     543             : }
-     544             : 
-     545             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html b/doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html deleted file mode 100644 index fd272427c..000000000 --- a/doc/coverageReport/test/testCandidateSplitting.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testCandidateSplitting.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testCandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4747100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testCandidateSplitting_SimpleTest_Test8TestBodyEv1
_ZN7crpropa39testCandidateSplitting_CheckSplits_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testCandidateSplitting.cpp.func.html b/doc/coverageReport/test/testCandidateSplitting.cpp.func.html deleted file mode 100644 index 5940d2ea4..000000000 --- a/doc/coverageReport/test/testCandidateSplitting.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testCandidateSplitting.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testCandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4747100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa38testCandidateSplitting_SimpleTest_Test8TestBodyEv1
_ZN7crpropa39testCandidateSplitting_CheckSplits_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html b/doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html deleted file mode 100644 index 7f7795772..000000000 --- a/doc/coverageReport/test/testCandidateSplitting.cpp.gcov.html +++ /dev/null @@ -1,166 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testCandidateSplitting.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testCandidateSplitting.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4747100.0 %
Date:2024-04-08 14:58:22Functions:22100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Units.h"
-       2             : #include "crpropa/Common.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/module/CandidateSplitting.h"
-       5             : 
-       6             : #include "gtest/gtest.h"
-       7             : #include <stdexcept>
-       8             : #include <cmath>
-       9             : 
-      10             : namespace crpropa {
-      11             : 
-      12           1 : TEST(testCandidateSplitting, SimpleTest) {
-      13           1 :         int nSplit = 2;
-      14             :         int nBins = 4;
-      15             :         double minWeight = pow(1. / nSplit, 2);
-      16             :         double Emin = 1; // dimensionless for testing
-      17             :         double Emax = 10;       
-      18             : 
-      19           1 :         CandidateSplitting split_lin(nSplit, Emin, Emax, nBins, minWeight);
-      20             :         double dE = (Emax - Emin) / nBins;
-      21           1 :         EXPECT_DOUBLE_EQ(split_lin.getEnergyBins()[0], Emin);
-      22           1 :         EXPECT_DOUBLE_EQ(split_lin.getEnergyBins()[1], Emin + dE);
-      23             : 
-      24           1 :         EXPECT_EQ(split_lin.getNsplit(), nSplit);
-      25           1 :         EXPECT_DOUBLE_EQ(split_lin.getMinimalWeight(), minWeight);
-      26             : 
-      27           2 :         CandidateSplitting split_log(nSplit, Emin, Emax, nBins, minWeight, true);
-      28             :         double dE_log = pow(Emax / Emin, 1. / (nBins - 1.0));
-      29           1 :         EXPECT_DOUBLE_EQ(split_log.getEnergyBins()[0], Emin);
-      30           1 :         EXPECT_DOUBLE_EQ(split_log.getEnergyBins()[1], Emin * dE_log);
-      31             : 
-      32             :         double spectralIndex = -2.;
-      33           2 :         CandidateSplitting split_dsa(spectralIndex, Emin, nBins);
-      34             :         double dE_dsa = pow(1. / 2, 1. / (spectralIndex + 1));
-      35           1 :         EXPECT_DOUBLE_EQ(split_dsa.getEnergyBins()[0], Emin * dE_dsa);
-      36           1 :         EXPECT_DOUBLE_EQ(split_dsa.getEnergyBins()[nBins - 1], Emin * pow(dE_dsa, nBins));
-      37           1 : }
-      38             : 
-      39             : 
-      40           1 : TEST(testCandidateSplitting, CheckSplits) {
-      41             :         int nSplit = 2;
-      42             :         int nBins = 3;
-      43             :         double Emin = 1; // dimensionless for testing
-      44             :         double Emax = 10;
-      45             :         double minWeight = pow(1. / nSplit, 4);
-      46             : 
-      47           1 :         CandidateSplitting splitting(nSplit, Emin, Emax, nBins, minWeight);
-      48           1 :         Candidate c(nucleusId(1,1),0.5);
-      49             :         double weight = 1.0;
-      50           1 :         double serial = c.getSerialNumber();
-      51             :         
-      52           1 :         splitting.process(&c); // no split
-      53           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
-      54           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial);
-      55             : 
-      56           1 :         c.current.setEnergy(2); 
-      57           1 :         splitting.process(&c); // 1. split
-      58             :         weight = weight/nSplit;
-      59           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
-      60           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 1);
-      61           1 :         c.previous.setEnergy(2);
-      62             : 
-      63           1 :         c.current.setEnergy(6); 
-      64           1 :         splitting.process(&c); // 2. split
-      65             :         weight = weight/nSplit;
-      66           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
-      67           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 2);
-      68           1 :         c.previous.setEnergy(6);
-      69             : 
-      70           1 :         c.current.setEnergy(0.5); 
-      71           1 :         splitting.process(&c); // no split, cooling
-      72           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
-      73           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 2);
-      74           1 :         c.previous.setEnergy(0.5);
-      75             : 
-      76           1 :         c.current.setEnergy(6); 
-      77           1 :         splitting.process(&c); // 3. & 4. split, crosses two boundaries
-      78             :         weight = weight/nSplit/nSplit;
-      79           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
-      80           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 4);
-      81           1 :         c.previous.setEnergy(6);
-      82             : 
-      83           1 :         c.current.setEnergy(8); 
-      84           1 :         splitting.process(&c); // no split, minimal weight reached
-      85           1 :         EXPECT_DOUBLE_EQ(c.getWeight(), weight);
-      86           1 :         EXPECT_DOUBLE_EQ(c.getNextSerialNumber(), serial + 4);
-      87           1 :         c.previous.setEnergy(8);
-      88           1 : }
-      89             : 
-      90             : } //namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testCore.cpp.func-sort-c.html b/doc/coverageReport/test/testCore.cpp.func-sort-c.html deleted file mode 100644 index d65894f63..000000000 --- a/doc/coverageReport/test/testCore.cpp.func-sort-c.html +++ /dev/null @@ -1,308 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testCore.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testCore.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:65465799.5 %
Date:2024-04-08 14:58:22Functions:585998.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa16Random_seed_Test8TestBodyEv1
_ZN7crpropa17Grid3f_Speed_Test8TestBodyEv1
_ZN7crpropa17common_digit_Test8TestBodyEv1
_ZN7crpropa18HepPID_charge_Test8TestBodyEv1
_ZN7crpropa19Geometry_Plane_Test8TestBodyEv1
_ZN7crpropa20Geometry_Sphere_Test8TestBodyEv1
_ZN7crpropa20Grid3f_DumpLoad_Test8TestBodyEv1
_ZN7crpropa20common_gaussInt_Test8TestBodyEv1
_ZN7crpropa21Candidate_weight_Test8TestBodyEv1
_ZN7crpropa21ParticleState_id_Test8TestBodyEv1
_ZN7crpropa22EmissionMap_merge_Test8TestBodyEv1
_ZN7crpropa22Grid1f_SimpleTest_Test8TestBodyEv1
_ZN7crpropa22Grid1f_clipVolume_Test8TestBodyEv1
_ZN7crpropa22Random_base64Seed_Test8TestBodyEv1
_ZN7crpropa22VectordGrid_Scale_Test8TestBodyEv1
_ZN7crpropa23Candidate_isActive_Test8TestBodyEv1
_ZN7crpropa23Candidate_property_Test8TestBodyEv1
_ZN7crpropa23Grid3f_DumpLoadTxt_Test8TestBodyEv1
_ZN7crpropa23Grid3f_Periodicity_Test8TestBodyEv1
_ZN7crpropa23Grid_PeriodicClamp_Test8TestBodyEv1
_ZN7crpropa23ParticleState_Mass_Test8TestBodyEv1
_ZN7crpropa23common_interpolate_Test8TestBodyEv1
_ZN7crpropa23common_pow_integer_Test8TestBodyEv1
_ZN7crpropa24Grid1f_ClosestValue_Test8TestBodyEv1
_ZN7crpropa24Grid3f_Reflectivity_Test8TestBodyEv1
_ZN7crpropa24base64_de_en_coding_Test8TestBodyEv1
_ZN7crpropa25Geometry_ParaxialBox_Test8TestBodyEv1
_ZN7crpropa25Grid3f_Interpolation_Test8TestBodyEv1
_ZN7crpropa25Grid_ReflectiveClamp_Test8TestBodyEv1
_ZN7crpropa25ParticleID_isNucleus_Test8TestBodyEv1
_ZN7crpropa25ParticleID_nucleusId_Test8TestBodyEv1
_ZN7crpropa25ParticleState_Charge_Test8TestBodyEv1
_ZN7crpropa25ParticleState_energy_Test8TestBodyEv1
_ZN7crpropa25Variant_copyToBuffer_Test8TestBodyEv1
_ZN7crpropa26Candidate_currentStep_Test8TestBodyEv1
_ZN7crpropa26EmissionMap_functions_Test8TestBodyEv1
_ZN7crpropa26Grid_PeriodicBoundary_Test8TestBodyEv1
_ZN7crpropa26ParticleID_massNumber_Test8TestBodyEv1
_ZN7crpropa26Random_bigSeedStorage_Test8TestBodyEv1
_ZN7crpropa27Candidate_addSecondary_Test8TestBodyEv1
_ZN7crpropa27Candidate_candidateTag_Test8TestBodyEv1
_ZN7crpropa27Candidate_serialNumber_Test8TestBodyEv1
_ZN7crpropa27ParticleState_Rigidity_Test8TestBodyEv1
_ZN7crpropa27ParticleState_momentum_Test8TestBodyEv1
_ZN7crpropa27ParticleState_position_Test8TestBodyEv1
_ZN7crpropa27ParticleState_velocity_Test8TestBodyEv1
_ZN7crpropa28Candidate_limitNextStep_Test8TestBodyEv1
_ZN7crpropa28Grid_ReflectiveBoundary_Test8TestBodyEv1
_ZN7crpropa28ParticleID_chargeNumber_Test8TestBodyEv1
_ZN7crpropa28ParticleState_direction_Test8TestBodyEv1
_ZN7crpropa29Grid1f_TestVectorSpacing_Test8TestBodyEv1
_ZN7crpropa29Variant_stringConversion_Test8TestBodyEv1
_ZN7crpropa30ParticleState_idException_Test8TestBodyEv1
_ZN7crpropa32ParticleState_lorentzFactor_Test8TestBodyEv1
_ZN7crpropa34common_interpolateEquidistant_Test8TestBodyEv1
_ZN7crpropa37Grid1f_GridPropertiesConstructor_Test8TestBodyEv1
_ZN7crpropa39CylindricalProjectionMap_functions_Test8TestBodyEv1
_ZN7crpropa50HepPID_consistencyWithReferenceImplementation_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testCore.cpp.func.html b/doc/coverageReport/test/testCore.cpp.func.html deleted file mode 100644 index 1336167ed..000000000 --- a/doc/coverageReport/test/testCore.cpp.func.html +++ /dev/null @@ -1,308 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testCore.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testCore.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:65465799.5 %
Date:2024-04-08 14:58:22Functions:585998.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16Random_seed_Test8TestBodyEv1
_ZN7crpropa17Grid3f_Speed_Test8TestBodyEv1
_ZN7crpropa17common_digit_Test8TestBodyEv1
_ZN7crpropa18HepPID_charge_Test8TestBodyEv1
_ZN7crpropa19Geometry_Plane_Test8TestBodyEv1
_ZN7crpropa20Geometry_Sphere_Test8TestBodyEv1
_ZN7crpropa20Grid3f_DumpLoad_Test8TestBodyEv1
_ZN7crpropa20common_gaussInt_Test8TestBodyEv1
_ZN7crpropa21Candidate_weight_Test8TestBodyEv1
_ZN7crpropa21ParticleState_id_Test8TestBodyEv1
_ZN7crpropa22EmissionMap_merge_Test8TestBodyEv1
_ZN7crpropa22Grid1f_SimpleTest_Test8TestBodyEv1
_ZN7crpropa22Grid1f_clipVolume_Test8TestBodyEv1
_ZN7crpropa22Random_base64Seed_Test8TestBodyEv1
_ZN7crpropa22VectordGrid_Scale_Test8TestBodyEv1
_ZN7crpropa23Candidate_isActive_Test8TestBodyEv1
_ZN7crpropa23Candidate_property_Test8TestBodyEv1
_ZN7crpropa23Grid3f_DumpLoadTxt_Test8TestBodyEv1
_ZN7crpropa23Grid3f_Periodicity_Test8TestBodyEv1
_ZN7crpropa23Grid_PeriodicClamp_Test8TestBodyEv1
_ZN7crpropa23ParticleState_Mass_Test8TestBodyEv1
_ZN7crpropa23common_interpolate_Test8TestBodyEv1
_ZN7crpropa23common_pow_integer_Test8TestBodyEv1
_ZN7crpropa24Grid1f_ClosestValue_Test8TestBodyEv1
_ZN7crpropa24Grid3f_Reflectivity_Test8TestBodyEv1
_ZN7crpropa24base64_de_en_coding_Test8TestBodyEv1
_ZN7crpropa25Geometry_ParaxialBox_Test8TestBodyEv1
_ZN7crpropa25Grid3f_Interpolation_Test8TestBodyEv1
_ZN7crpropa25Grid_ReflectiveClamp_Test8TestBodyEv1
_ZN7crpropa25ParticleID_isNucleus_Test8TestBodyEv1
_ZN7crpropa25ParticleID_nucleusId_Test8TestBodyEv1
_ZN7crpropa25ParticleState_Charge_Test8TestBodyEv1
_ZN7crpropa25ParticleState_energy_Test8TestBodyEv1
_ZN7crpropa25Variant_copyToBuffer_Test8TestBodyEv1
_ZN7crpropa26Candidate_currentStep_Test8TestBodyEv1
_ZN7crpropa26EmissionMap_functions_Test8TestBodyEv1
_ZN7crpropa26Grid_PeriodicBoundary_Test8TestBodyEv1
_ZN7crpropa26ParticleID_massNumber_Test8TestBodyEv1
_ZN7crpropa26Random_bigSeedStorage_Test8TestBodyEv1
_ZN7crpropa27Candidate_addSecondary_Test8TestBodyEv1
_ZN7crpropa27Candidate_candidateTag_Test8TestBodyEv1
_ZN7crpropa27Candidate_serialNumber_Test8TestBodyEv1
_ZN7crpropa27ParticleState_Rigidity_Test8TestBodyEv1
_ZN7crpropa27ParticleState_momentum_Test8TestBodyEv1
_ZN7crpropa27ParticleState_position_Test8TestBodyEv1
_ZN7crpropa27ParticleState_velocity_Test8TestBodyEv1
_ZN7crpropa28Candidate_limitNextStep_Test8TestBodyEv1
_ZN7crpropa28Grid_ReflectiveBoundary_Test8TestBodyEv1
_ZN7crpropa28ParticleID_chargeNumber_Test8TestBodyEv1
_ZN7crpropa28ParticleState_direction_Test8TestBodyEv1
_ZN7crpropa29Grid1f_TestVectorSpacing_Test8TestBodyEv1
_ZN7crpropa29Variant_stringConversion_Test8TestBodyEv1
_ZN7crpropa30ParticleState_idException_Test8TestBodyEv1
_ZN7crpropa32ParticleState_lorentzFactor_Test8TestBodyEv1
_ZN7crpropa34common_interpolateEquidistant_Test8TestBodyEv1
_ZN7crpropa37Grid1f_GridPropertiesConstructor_Test8TestBodyEv1
_ZN7crpropa39CylindricalProjectionMap_functions_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
_ZN7crpropa50HepPID_consistencyWithReferenceImplementation_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testCore.cpp.gcov.html b/doc/coverageReport/test/testCore.cpp.gcov.html deleted file mode 100644 index 3e1716747..000000000 --- a/doc/coverageReport/test/testCore.cpp.gcov.html +++ /dev/null @@ -1,1144 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testCore.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testCore.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:65465799.5 %
Date:2024-04-08 14:58:22Functions:585998.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /** Unit tests for core features of CRPropa
-       2             :         Candidate
-       3             :         ParticleState
-       4             :         Random
-       5             :         Common functions
-       6             :  */
-       7             : 
-       8             : #include <complex>
-       9             : 
-      10             : #include "crpropa/Candidate.h"
-      11             : #include "crpropa/base64.h"
-      12             : #include "crpropa/Common.h"
-      13             : #include "crpropa/Units.h"
-      14             : #include "crpropa/ParticleID.h"
-      15             : #include "crpropa/ParticleMass.h"
-      16             : #include "crpropa/Random.h"
-      17             : #include "crpropa/Grid.h"
-      18             : #include "crpropa/GridTools.h"
-      19             : #include "crpropa/Geometry.h"
-      20             : #include "crpropa/EmissionMap.h"
-      21             : #include "crpropa/Vector3.h"
-      22             : 
-      23             : #include <HepPID/ParticleIDMethods.hh>
-      24             : #include "gtest/gtest.h"
-      25             : 
-      26             : namespace crpropa {
-      27             : 
-      28           2 : TEST(ParticleState, position) {
-      29           1 :         ParticleState particle;
-      30             :         Vector3d v(1, 3, 5);
-      31           1 :         particle.setPosition(v * Mpc);
-      32           2 :         EXPECT_TRUE(particle.getPosition() == v * Mpc);
-      33           1 : }
-      34             : 
-      35           2 : TEST(ParticleState, energy) {
-      36           1 :         ParticleState particle;
-      37           1 :         particle.setEnergy(10 * EeV);
-      38           1 :         EXPECT_EQ(particle.getEnergy(), 10 * EeV);
-      39           1 : }
-      40             : 
-      41           2 : TEST(ParticleState, direction) {
-      42           1 :         ParticleState particle;
-      43             :         Vector3d v(1, 2, 3);
-      44           1 :         particle.setDirection(v);
-      45           2 :         EXPECT_TRUE(particle.getDirection() == v.getUnitVector());
-      46           1 : }
-      47             : 
-      48           2 : TEST(ParticleState, velocity) {
-      49           1 :         ParticleState particle;
-      50             :         Vector3d v(1, 1, 0);
-      51           1 :         particle.setDirection(v);
-      52           2 :         EXPECT_TRUE(particle.getVelocity() == v.getUnitVector() * c_light);
-      53           1 : }
-      54             : 
-      55           2 : TEST(ParticleState, momentum) {
-      56           1 :         ParticleState particle;
-      57             :         Vector3d v(0, 1, 0);
-      58           1 :         particle.setDirection(v);
-      59           1 :         particle.setEnergy(100 * EeV);
-      60           2 :         EXPECT_TRUE(particle.getMomentum() == v * (particle.getEnergy() / c_light));
-      61           1 : }
-      62             : 
-      63           2 : TEST(ParticleState, id) {
-      64           1 :         ParticleState particle;
-      65           1 :         particle.setId(nucleusId(12, 6));
-      66           1 :         EXPECT_EQ(particle.getId(), 1000060120);
-      67           1 : }
-      68             : 
-      69             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
-      70           1 : TEST(ParticleState, idException) {
-      71           1 :         EXPECT_THROW(nucleusId(5, 6), std::runtime_error);
-      72           1 : }
-      73             : #endif
-      74             : 
-      75           2 : TEST(ParticleState, Charge) {
-      76           1 :         ParticleState particle;
-      77             : 
-      78           1 :         particle.setId(nucleusId(56, 26)); // iron
-      79           1 :         EXPECT_DOUBLE_EQ(26 * eplus, particle.getCharge());
-      80             : 
-      81           1 :         particle.setId(-nucleusId(56, 26)); // anti-iron
-      82           1 :         EXPECT_DOUBLE_EQ(-26 * eplus, particle.getCharge());
-      83             : 
-      84           1 :         particle.setId(11); // electron
-      85           1 :         EXPECT_DOUBLE_EQ(-1 * eplus, particle.getCharge());
-      86             : 
-      87           1 :         particle.setId(-11); // positron
-      88           1 :         EXPECT_DOUBLE_EQ(1 * eplus, particle.getCharge());
-      89             : 
-      90           1 :         particle.setId(12); // electron neutrino
-      91           1 :         EXPECT_DOUBLE_EQ(0, particle.getCharge());
-      92             : 
-      93           1 :         particle.setId(-12); // electron anti-neutrino
-      94           1 :         EXPECT_DOUBLE_EQ(0, particle.getCharge());
-      95           1 : }
-      96             : 
-      97           2 : TEST(ParticleState, Rigidity) {
-      98           1 :         ParticleState particle;
-      99             : 
-     100           1 :         particle.setId(nucleusId(1, 1)); // proton
-     101           1 :         particle.setEnergy(1 * EeV);
-     102           1 :         EXPECT_EQ(particle.getRigidity(), 1e18);
-     103           1 : }
-     104             : 
-     105           2 : TEST(ParticleState, Mass) {
-     106           1 :         ParticleState particle;
-     107             : 
-     108           1 :         particle.setId(nucleusId(1, 1)); // proton
-     109           1 :         EXPECT_DOUBLE_EQ(mass_proton, particle.getMass());
-     110             : 
-     111           1 :         particle.setId(nucleusId(1, 0)); // neutron
-     112           1 :         EXPECT_DOUBLE_EQ(mass_neutron, particle.getMass());
-     113             : 
-     114           1 :         int id = nucleusId(56, 26);
-     115           1 :         particle.setId(id); // iron
-     116           1 :         EXPECT_DOUBLE_EQ(nuclearMass(id), particle.getMass());
-     117             : 
-     118           1 :         particle.setId(-id); // anti-iron
-     119           1 :         EXPECT_DOUBLE_EQ(nuclearMass(-id), particle.getMass());
-     120             : 
-     121             :         // approximation for unkown nucleus A * amu - Z * mass_electron
-     122             :         int A = 238; int Z = 92; // Uranium92
-     123           1 :         EXPECT_DOUBLE_EQ(nuclearMass(A, Z), A*amu - Z*mass_electron);
-     124           1 : }
-     125             : 
-     126           2 : TEST(ParticleState, lorentzFactor) {
-     127           1 :         ParticleState particle;
-     128           1 :         particle.setId(nucleusId(1, 1));
-     129           1 :         particle.setEnergy(1e12 * eV);
-     130           1 :         EXPECT_DOUBLE_EQ(particle.getLorentzFactor(),
-     131             :                         1e12 * eV / mass_proton / c_squared);
-     132           1 : }
-     133             : 
-     134           1 : TEST(ParticleID, nucleusId) {
-     135           1 :         EXPECT_EQ(nucleusId(3,2), 1000020030);
-     136           1 : }
-     137             : 
-     138           1 : TEST(ParticleID, chargeNumber) {
-     139           1 :         EXPECT_EQ(chargeNumber(1000020030), 2);
-     140           1 : }
-     141             : 
-     142           1 : TEST(ParticleID, massNumber) {
-     143           1 :         EXPECT_EQ(massNumber(2112), 1);
-     144           1 :         EXPECT_EQ(massNumber(1000020030), 3);
-     145           1 : }
-     146             : 
-     147           1 : TEST(ParticleID, isNucleus) {
-     148           1 :         EXPECT_TRUE(isNucleus(1000020030));
-     149           1 :         EXPECT_FALSE(isNucleus(11));
-     150           1 : }
-     151             : 
-     152           1 : TEST(HepPID, consistencyWithReferenceImplementation) {
-     153             :         // Tests the performance improved version against the default one
-     154           1 :         unsigned long testPID = rand() % 1000000000 + 1000000000;
-     155           8 :         for(size_t i=1; i < 8; i++) {
-     156           7 :                 HepPID::location loc = (HepPID::location) i;
-     157           7 :                 unsigned short newResult = HepPID::digit(loc, testPID);
-     158             :                 //original implementation
-     159           7 :                 int numerator = (int) std::pow(10.0,(loc-1));
-     160           7 :                 EXPECT_EQ(newResult, (HepPID::abspid(testPID)/numerator)%10);
-     161             :         }
-     162           1 : }
-     163             : 
-     164           1 : TEST(HepPID, charge) {
-     165           1 :         EXPECT_DOUBLE_EQ(HepPID::charge(11), -1.);
-     166           1 : }
-     167             : 
-     168           1 : TEST(Candidate, currentStep) {
-     169           1 :         Candidate candidate;
-     170           1 :         candidate.setCurrentStep(1 * Mpc);
-     171           1 :         EXPECT_DOUBLE_EQ(candidate.getCurrentStep(), 1 * Mpc);
-     172           1 : }
-     173             : 
-     174           1 : TEST(Candidate, limitNextStep) {
-     175           1 :         Candidate candidate;
-     176           1 :         candidate.setNextStep(5 * Mpc);
-     177           1 :         EXPECT_DOUBLE_EQ(candidate.getNextStep(), 5 * Mpc);
-     178           1 :         candidate.limitNextStep(2 * Mpc);
-     179           1 :         EXPECT_DOUBLE_EQ(candidate.getNextStep(), 2 * Mpc);
-     180           1 :         candidate.limitNextStep(3 * Mpc);
-     181           1 :         EXPECT_DOUBLE_EQ(candidate.getNextStep(), 2 * Mpc);
-     182           1 : }
-     183             : 
-     184           1 : TEST(Candidate, isActive) {
-     185           1 :         Candidate candidate;
-     186           1 :         EXPECT_TRUE(candidate.isActive());
-     187           1 :         candidate.setActive(false);
-     188           1 :         EXPECT_FALSE(candidate.isActive());
-     189           1 : }
-     190             : 
-     191           1 : TEST(Candidate, property) {
-     192           1 :         Candidate candidate;
-     193           2 :         candidate.setProperty("foo", "bar");
-     194           2 :         EXPECT_TRUE(candidate.hasProperty("foo"));
-     195           2 :         std::string value = candidate.getProperty("foo");
-     196           1 :         EXPECT_EQ("bar", value);
-     197           1 : }
-     198             : 
-     199           1 : TEST(Candidate, weight) {
-     200           1 :     Candidate candidate;
-     201           1 :     EXPECT_EQ (1., candidate.getWeight());
-     202             :     
-     203           1 :     candidate.setWeight(5.);
-     204           1 :     EXPECT_EQ (5., candidate.getWeight());
-     205             :     
-     206           1 :     candidate.updateWeight(3.);
-     207           1 :     EXPECT_EQ (15., candidate.getWeight());
-     208           1 : }
-     209             : 
-     210           1 : TEST(Candidate, addSecondary) {
-     211           1 :         Candidate c;
-     212           1 :         c.setRedshift(5);
-     213           1 :         c.setTrajectoryLength(23);
-     214           1 :         c.setWeight(3.);
-     215           1 :         c.previous.setId(nucleusId(56,26));
-     216           1 :         c.previous.setEnergy(1000);
-     217           1 :         c.previous.setPosition(Vector3d(1,2,3));
-     218           1 :         c.previous.setDirection(Vector3d(0,0,1));
-     219             : 
-     220           1 :         c.addSecondary(nucleusId(1,1), 200);
-     221           2 :         c.addSecondary(nucleusId(1,1), 200, 5.);
-     222           1 :         Candidate s1 = *c.secondaries[0];
-     223           1 :         Candidate s2 = *c.secondaries[1];
-     224             : 
-     225           1 :         EXPECT_EQ(nucleusId(1,1), s1.current.getId());
-     226           1 :         EXPECT_EQ(200, s1.current.getEnergy());
-     227           1 :         EXPECT_EQ(5, s1.getRedshift());
-     228           1 :         EXPECT_EQ(23, s1.getTrajectoryLength());
-     229           1 :         EXPECT_EQ(1000, s1.created.getEnergy());
-     230           1 :         EXPECT_EQ(3., s1.getWeight());
-     231           2 :         EXPECT_TRUE(Vector3d(1,2,3) == s1.created.getPosition());
-     232           2 :         EXPECT_TRUE(Vector3d(0,0,1) == s1.created.getDirection());
-     233           2 :         EXPECT_TRUE(s1.getTagOrigin() == "SEC");
-     234             : 
-     235           1 :         EXPECT_EQ(15., s2.getWeight());
-     236           1 : }
-     237             : 
-     238           1 : TEST(Candidate, candidateTag) {
-     239           1 :         Candidate c;
-     240             : 
-     241             :         // test default tag
-     242           2 :         EXPECT_TRUE(c.getTagOrigin() == "PRIM");
-     243             : 
-     244             :         // test setting tag
-     245           1 :         c.setTagOrigin("myTag");
-     246           2 :         EXPECT_TRUE(c.getTagOrigin() == "myTag");
-     247           1 : }
-     248             : 
-     249           1 : TEST(Candidate, serialNumber) {
-     250           1 :         Candidate::setNextSerialNumber(42);
-     251           1 :         Candidate c;
-     252           1 :         EXPECT_EQ(43, c.getSourceSerialNumber());
-     253           1 : }
-     254             : 
-     255           1 : TEST(common, digit) {
-     256           1 :         EXPECT_EQ(1, digit(1234, 1000));
-     257           1 :         EXPECT_EQ(2, digit(1234, 100));
-     258           1 :         EXPECT_EQ(3, digit(1234, 10));
-     259           1 :         EXPECT_EQ(4, digit(1234, 1));
-     260           1 : }
-     261             : 
-     262           1 : TEST(common, interpolate) {
-     263             :         // create vectors x = (0, 0.02, ... 2) and y = 2x + 3 = (3, ... 7)
-     264           1 :         std::vector<double> xD(101), yD(101);
-     265         102 :         for (int i = 0; i <= 100; i++) {
-     266         101 :                 xD[i] = i * 0.02;
-     267         101 :                 yD[i] = 2 * xD[i] + 3;
-     268             :         }
-     269             : 
-     270             :         // interpolating tabulated values of a linear function should produce exact results
-     271           1 :         Random &R = Random::instance();
-     272             :         double x, ytrue, yinterp;
-     273       10001 :         for (int i = 0; i < 10000; i++) {
-     274       10000 :                 x = R.rand() * 2; // random value between 0 and 2
-     275       10000 :                 ytrue = 2 * x + 3;
-     276       10000 :                 yinterp = interpolate(x, xD, yD);
-     277       10000 :                 EXPECT_DOUBLE_EQ(ytrue, yinterp);
-     278             :         }
-     279             : 
-     280             :         // test interpolation in first bin
-     281             :         x = 0.01;
-     282             :         ytrue = 2 * x + 3;
-     283           1 :         yinterp = interpolate(x, xD, yD);
-     284           1 :         EXPECT_DOUBLE_EQ(ytrue, yinterp);
-     285             : 
-     286             :         // test interpolation in last bin
-     287             :         x = 1.99;
-     288             :         ytrue = 2 * x + 3;
-     289           1 :         yinterp = interpolate(x, xD, yD);
-     290           1 :         EXPECT_DOUBLE_EQ(ytrue, yinterp);
-     291             : 
-     292             :         // value out of range, return lower bound
-     293           1 :         EXPECT_EQ(3, interpolate(-0.001, xD, yD));
-     294             : 
-     295             :         // value out of range, return upper bound
-     296           1 :         EXPECT_EQ(7, interpolate(2.001, xD, yD));
-     297           1 : }
-     298             : 
-     299           1 : TEST(common, interpolateEquidistant) {
-     300           1 :         std::vector<double> yD(100);
-     301         101 :         for (int i = 0; i < 100; i++) {
-     302         100 :                 yD[i] = pow(1 + i * 2. / 99., 2);
-     303             :         }
-     304             : 
-     305             :         // interpolated value should be close to computed
-     306           1 :         double y = interpolateEquidistant(1.5001, 1, 3, yD);
-     307           1 :         EXPECT_NEAR(pow(1.5001, 2), y, 1e-4);
-     308             : 
-     309             :         // value out of range, return lower bound
-     310           1 :         EXPECT_EQ(1, interpolateEquidistant(0.9, 1, 3, yD));
-     311             : 
-     312             :         // value out of range, return lower bound
-     313           1 :         EXPECT_EQ(9, interpolateEquidistant(3.1, 1, 3, yD));
-     314           1 : }
-     315             : 
-     316           1 : TEST(common, pow_integer) {
-     317           1 :         EXPECT_EQ(pow_integer<0>(1.23), 1);
-     318           1 :         EXPECT_FLOAT_EQ(pow_integer<1>(1.234), 1.234);
-     319           1 :         EXPECT_FLOAT_EQ(pow_integer<2>(1.234), pow(1.234, 2));
-     320           1 :         EXPECT_FLOAT_EQ(pow_integer<3>(1.234), pow(1.234, 3));
-     321           1 : }
-     322             : 
-     323           2 : TEST(common, gaussInt) {
-     324           9 :         EXPECT_NEAR(gaussInt(([](double x){ return x*x; }), 0, 10), 1000/3., 1e-4);
-     325           9 :         EXPECT_NEAR(gaussInt(([](double x){ return sin(x)*sin(x); }), 0, M_PI), M_PI/2., 1e-4);
-     326           1 : }
-     327             : 
-     328           1 : TEST(Random, seed) {
-     329           1 :         Random &a = Random::instance();
-     330           1 :         Random &b = Random::instance();
-     331             : 
-     332           1 :         a.seed(42);
-     333           1 :         double r1 = a.rand();
-     334             : 
-     335           1 :         a.seed(42);
-     336           1 :         double r2 = a.rand();
-     337             : 
-     338           1 :         a.seed(42);
-     339           1 :         double r3 = b.rand();
-     340             : 
-     341             :         // seeding should give same random numbers
-     342           1 :         EXPECT_EQ(r1, r2);
-     343             : 
-     344             :         // seeding should work for all instances
-     345           1 :         EXPECT_EQ(r1, r3);
-     346           1 : }
-     347             : 
-     348           1 : TEST(Random, bigSeedStorage) {
-     349           1 :         Random a;
-     350             :         std::vector<uint32_t> bigSeed;
-     351             : 
-     352             :         const size_t nComp = 42;
-     353             :         double values[nComp];
-     354          43 :         for (size_t i = 0; i < nComp; i++)
-     355             :         {
-     356          42 :                 values[i] = a.rand();
-     357             :         }
-     358           1 :         bigSeed = a.getSeed();
-     359           1 :         Random b;
-     360             :         //b.load(bigSeed);
-     361           1 :         b.seed(&bigSeed[0], bigSeed.size());
-     362          43 :         for (size_t i = 0; i < nComp; i++)
-     363             :         {
-     364          42 :                 EXPECT_EQ(values[i], b.rand());
-     365             :         }
-     366             : 
-     367           1 :         a.seed(42);
-     368           1 :         bigSeed = a.getSeed();
-     369           1 :         EXPECT_EQ(bigSeed.size(), 1);
-     370           1 :         EXPECT_EQ(bigSeed[0], 42);
-     371           1 :         b.seed(bigSeed[0]);
-     372          43 :         for (size_t i = 0; i < nComp; i++)
-     373             :         {
-     374          42 :                 EXPECT_EQ(a.rand(), b.rand());
-     375             :         }
-     376             : 
-     377           1 : }
-     378             : 
-     379           1 : TEST(base64, de_en_coding) {
-     380           1 :         Random a;
-     381         100 :         for (int N=1; N < 100; N++) {
-     382             :                 std::vector<uint32_t> data;
-     383          99 :                 data.reserve(N);
-     384        5049 :                 for (int i =0; i<N; i++)
-     385        4950 :                         data.push_back(a.randInt());
-     386             : 
-     387          99 :                 std::string encoded_data = Base64::encode((unsigned char*)&data[0], sizeof(data[0]) * data.size() / sizeof(unsigned char));
-     388             : 
-     389          99 :                 std::string decoded_data = Base64::decode(encoded_data);
-     390          99 :                 size_t S = decoded_data.size() * sizeof(decoded_data[0]) / sizeof(uint32_t);
-     391        5049 :                 for (int i=0; i < S; i++) {
-     392        4950 :                         EXPECT_EQ(((uint32_t*)decoded_data.c_str())[i], data[i]);
-     393             :                 }
-     394             :         }
-     395             : 
-     396           1 : }
-     397             : 
-     398           1 : TEST(Random, base64Seed) {
-     399             : 
-     400           1 :         std::string seed =  "I1+8ANzXYwAqAAAAAwAAAA==";
-     401             :         std::vector<uint32_t> bigSeed;
-     402           1 :         bigSeed.push_back(12345123);
-     403           1 :         bigSeed.push_back(6543324);
-     404           1 :         bigSeed.push_back(42);
-     405           1 :         bigSeed.push_back(3);
-     406           1 :         Random a, b;
-     407           1 :         a.seed(seed);
-     408           1 :         b.seed(&bigSeed[0], bigSeed.size());
-     409             : 
-     410             :         const size_t nComp = 42;
-     411             :         double values[nComp];
-     412          43 :         for (size_t i = 0; i < nComp; i++)
-     413             :         {
-     414          42 :                 EXPECT_EQ(a.rand(), b.rand());
-     415             :         }
-     416           1 : }
-     417             : 
-     418           2 : TEST(Grid, PeriodicClamp) {
-     419             :         // Test correct determination of lower and upper neighbor
-     420             :         int lo, hi;
-     421             : 
-     422             :         periodicClamp(23.12, 8, lo, hi);
-     423           1 :         EXPECT_EQ(7, lo);
-     424           1 :         EXPECT_EQ(0, hi);
-     425             : 
-     426             :         periodicClamp(-23.12, 8, lo, hi);
-     427           1 :         EXPECT_EQ(0, lo);
-     428           1 :         EXPECT_EQ(1, hi);
-     429           1 : }
-     430             : 
-     431           1 : TEST(Grid, PeriodicBoundary) {
-     432             :         // Test correct determination of periodic continuated index
-     433             :         // periodic indices for n=8 should repeat like ...0123456701234567...
-     434             :         int index;
-     435             : 
-     436           1 :         index = periodicBoundary(0, 8);
-     437           1 :         EXPECT_EQ(0, index);
-     438           1 :         index = periodicBoundary(7, 8);
-     439           1 :         EXPECT_EQ(7, index);
-     440           1 :         index = periodicBoundary(8, 8);
-     441           1 :         EXPECT_EQ(0, index);
-     442           1 :         index = periodicBoundary(9, 8);
-     443           1 :         EXPECT_EQ(1, index);
-     444           1 : }
-     445             : 
-     446           1 : TEST(Grid, ReflectiveClamp) {
-     447             :         // Test correct determination of lower and upper neighbor
-     448             :         // reflective indices for n=8 should repeat like ...67765432100123456776...
-     449             :         int lo, hi; 
-     450             :         double res;
-     451             : 
-     452           1 :         reflectiveClamp(23.12, 8, lo, hi, res);
-     453           1 :         EXPECT_EQ(7, lo);
-     454           1 :         EXPECT_EQ(7, hi);
-     455           1 :         EXPECT_FLOAT_EQ(7.12, res);
-     456             : 
-     457           1 :         reflectiveClamp(-23.12, 8, lo, hi, res);
-     458           1 :         EXPECT_EQ(6, lo);
-     459           1 :         EXPECT_EQ(7, hi);
-     460           1 :         EXPECT_FLOAT_EQ(6.12, res);
-     461           1 : }
-     462             : 
-     463           2 : TEST(Grid, ReflectiveBoundary) {
-     464             :         // Test correct determination of reflected index
-     465             :         // reflective indices for n=8 should repeat like ...67765432100123456776...
-     466             :         int index; 
-     467             : 
-     468           1 :         index = reflectiveBoundary(8, 8);
-     469           1 :         EXPECT_EQ(7, index);
-     470           1 :         index = reflectiveBoundary(9, 8);
-     471           1 :         EXPECT_EQ(6, index);
-     472           1 :         index = reflectiveBoundary(0, 8);
-     473           1 :         EXPECT_EQ(0, index);
-     474           1 :         index = reflectiveBoundary(-1, 8);
-     475           1 :         EXPECT_EQ(0, index);
-     476           1 :         index = reflectiveBoundary(-8, 8);
-     477           1 :         EXPECT_EQ(7, index);
-     478           1 :         index = reflectiveBoundary(-9, 8);
-     479           1 :         EXPECT_EQ(7, index);
-     480           1 : }
-     481             : 
-     482           1 : TEST(Grid1f, SimpleTest) {
-     483             :         // Test construction and parameters
-     484           1 :         size_t Nx = 5;
-     485           1 :         size_t Ny = 8;
-     486           1 :         size_t Nz = 10;
-     487             :         double spacing = 2.0;
-     488             :         Vector3d origin(1., 2., 3.);
-     489             : 
-     490           1 :         Grid1f grid(origin, Nx, Ny, Nz, spacing);
-     491             : 
-     492           1 :         EXPECT_TRUE(origin == grid.getOrigin());
-     493           1 :         EXPECT_EQ(Nx, grid.getNx());
-     494           1 :         EXPECT_EQ(Ny, grid.getNy());
-     495           1 :         EXPECT_EQ(Nz, grid.getNz());
-     496           1 :         EXPECT_EQ(Vector3d(spacing), grid.getSpacing());
-     497           1 :         EXPECT_EQ(5 * 8 * 10, grid.getGrid().size());
-     498             : 
-     499             :         // Test index handling: get position of grid point (2, 3, 4)
-     500           1 :         size_t some_index = 2 * Ny * Nz + 3 * Nz + 4;
-     501             :         Vector3d some_grid_point = origin + Vector3d(2, 3, 4) * spacing + Vector3d(spacing / 2.);
-     502           2 :         EXPECT_EQ(some_grid_point, grid.positionFromIndex(some_index));
-     503             :         
-     504             :         //Test if value on gridpoint is correctly retrieved
-     505           1 :         grid.get(2, 3, 4) = 7;
-     506           1 :         EXPECT_FLOAT_EQ(7., grid.getGrid()[some_index]);
-     507             :         //trilinear interpolated
-     508           1 :         EXPECT_FLOAT_EQ(7., grid.interpolate(some_grid_point));
-     509             :         //tricubic interpolated
-     510             :         grid.setInterpolationType(TRICUBIC);
-     511           1 :         EXPECT_FLOAT_EQ(7., grid.interpolate(some_grid_point));
-     512             :         //nearest neighbour interpolated
-     513             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
-     514           1 :         EXPECT_FLOAT_EQ(7., grid.interpolate(some_grid_point));
-     515             : 
-     516             :         //Test if grid is set to zero outside of volume for clipVolume=true
-     517             :         grid.setClipVolume(true);
-     518           1 :         EXPECT_FLOAT_EQ(0, grid.interpolate(Vector3d(100, 0, 12)));
-     519           1 : }
-     520             : 
-     521           2 : TEST(Grid1f, GridPropertiesConstructor) {
-     522             :         // Test constructor for vector spacing
-     523             :         size_t Nx = 5;
-     524             :         size_t Ny = 8;
-     525             :         size_t Nz = 10;
-     526             :         Vector3d origin = Vector3d(1., 2., 3.);
-     527             :         Vector3d spacing = Vector3d(1., 5., 3.);
-     528             :         GridProperties properties(origin, Nx, Ny, Nz, spacing);
-     529           1 :         Grid1f grid(properties);
-     530             : 
-     531           1 :         EXPECT_EQ(spacing, grid.getSpacing());
-     532             : 
-     533             :         // Test index handling: get position of grid point (1, 7, 6)
-     534             :         size_t some_index = 1 * Ny * Nz + 7 * Nz + 6;
-     535             :         Vector3d some_grid_point = origin + Vector3d(1, 7, 6) * spacing + spacing / 2.;
-     536             : 
-     537             :         //Test if value on gridpoint is correctly retrieved
-     538           1 :         grid.get(1, 7, 6) = 12;
-     539           1 :         EXPECT_FLOAT_EQ(12., grid.getGrid()[some_index]);
-     540             :         //trilinear interpolated
-     541           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
-     542             :         //tricubic interpolated
-     543             :         grid.setInterpolationType(TRICUBIC);
-     544           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
-     545             :         //nearest neighbour interpolated
-     546             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
-     547           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
-     548           1 : }
-     549             : 
-     550           2 : TEST(Grid1f, TestVectorSpacing) {
-     551             :         // Test constructor for vector spacing
-     552             :         size_t Nx = 5;
-     553             :         size_t Ny = 8;
-     554             :         size_t Nz = 10;
-     555             :         Vector3d origin = Vector3d(1., 2., 3.);
-     556             :         Vector3d spacing = Vector3d(1., 5., 3.);
-     557             : 
-     558           1 :         Grid1f grid(origin, Nx, Ny, Nz, spacing);
-     559             : 
-     560           1 :         EXPECT_EQ(spacing, grid.getSpacing());
-     561             : 
-     562             :         // Test index handling: get position of grid point (1, 7, 6)
-     563             :         size_t some_index = 1 * Ny * Nz + 7 * Nz + 6;
-     564             :         Vector3d some_grid_point = origin + Vector3d(1, 7, 6) * spacing + spacing / 2.;
-     565             : 
-     566             :         //Test if value on gridpoint is correctly retrieved
-     567           1 :         grid.get(1, 7, 6) = 12;
-     568           1 :         EXPECT_FLOAT_EQ(12., grid.getGrid()[some_index]);
-     569             :         //trilinear interpolated
-     570           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
-     571             :         //tricubic interpolated
-     572             :         grid.setInterpolationType(TRICUBIC);
-     573           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
-     574             :         //nearest neighbour interpolated
-     575             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
-     576           1 :         EXPECT_FLOAT_EQ(12., grid.interpolate(some_grid_point));
-     577           1 : }
-     578             : 
-     579           2 : TEST(Grid1f, ClosestValue) {
-     580             :         // Check some closest values / nearest neighbour interpolation
-     581           1 :         Grid1f grid(Vector3d(0.), 2, 2, 2, 1.);
-     582           1 :         grid.get(0, 0, 0) = 1;
-     583           1 :         grid.get(0, 0, 1) = 2;
-     584           1 :         grid.get(0, 1, 0) = 3;
-     585           1 :         grid.get(0, 1, 1) = 4;
-     586           1 :         grid.get(1, 0, 0) = 5;
-     587           1 :         grid.get(1, 0, 1) = 6;
-     588           1 :         grid.get(1, 1, 0) = 7;
-     589           1 :         grid.get(1, 1, 1) = 8;
-     590             : 
-     591             :         // grid points are at 0.5 and 1.5
-     592           1 :         EXPECT_FLOAT_EQ(1, grid.closestValue(Vector3d(0.1,  0.2, 0.6)));
-     593           1 :         EXPECT_FLOAT_EQ(2, grid.closestValue(Vector3d(0.2, 0.1, 1.3)));
-     594           1 :         EXPECT_FLOAT_EQ(3, grid.closestValue(Vector3d(0.3, 1.2, 0.2)));
-     595           1 :         EXPECT_FLOAT_EQ(7, grid.closestValue(Vector3d(1.7, 1.8, 0.4)));
-     596             : 
-     597             :         //Test if grid is set to zero outside of volume for clipVolume=true
-     598           1 :         EXPECT_NE(0, grid.interpolate(Vector3d(0, 0, 12)));
-     599             :         grid.setClipVolume(true);
-     600           1 :         double b = grid.interpolate(Vector3d(0, 0, 12));
-     601           1 :         EXPECT_FLOAT_EQ(0, b);
-     602           1 : }
-     603             : 
-     604           2 : TEST(Grid1f, clipVolume) {
-     605             :         // Check volume clipping for gridproperties constructor
-     606             :         size_t N = 2;
-     607             :         Vector3d origin = Vector3d(0.);
-     608             :         double spacing = 2;
-     609             :         GridProperties properties(origin, N, spacing);
-     610           1 :         Grid1f grid(properties);
-     611           1 :         grid.get(0, 0, 0) = 1;
-     612           1 :         grid.get(0, 0, 1) = 2;
-     613           1 :         grid.get(0, 1, 0) = 3;
-     614           1 :         grid.get(0, 1, 1) = 4;
-     615           1 :         grid.get(1, 0, 0) = 5;
-     616           1 :         grid.get(1, 0, 1) = 6;
-     617           1 :         grid.get(1, 1, 0) = 7;
-     618           1 :         grid.get(1, 1, 1) = 8;
-     619             : 
-     620             :         //Test if grid is set to zero outside of volume for clipVolume=true
-     621           1 :         EXPECT_NE(0, grid.interpolate(Vector3d(0, 0, 12)));
-     622             :         grid.setClipVolume(true);
-     623           1 :         double b = grid.interpolate(Vector3d(0, 0, 10));
-     624           1 :         EXPECT_FLOAT_EQ(0, b);
-     625           1 : }
-     626             : 
-     627           2 : TEST(Grid3f, Interpolation) {
-     628             :         // Explicitly test trilinear and tricubic interpolation
-     629             :         double spacing = 2.793;
-     630             :         int n = 3;
-     631           1 :         Grid3f grid(Vector3d(0.), n, n, n, spacing);
-     632             :         grid.get(0, 0, 1) = Vector3f(1.7, 0., 0.); // set one value
-     633             : 
-     634             :         Vector3d b;
-     635             :         
-     636             :         //trilinear
-     637             : 
-     638             :         // grid points are at [0.5, 1.5, ...] * spacing
-     639           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.5) * spacing);
-     640           1 :         EXPECT_FLOAT_EQ(1.7, b.x);
-     641             : 
-     642           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.4) * spacing);
-     643           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9, b.x);
-     644             : 
-     645           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.6) * spacing);
-     646           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9, b.x);
-     647             : 
-     648           1 :         b = grid.interpolate(Vector3d(0.5, 0.35, 1.6) * spacing);
-     649           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9 * 0.85, b.x);
-     650             : 
-     651           1 :         b = grid.interpolate(Vector3d(0.5, 2.65, 1.6) * spacing); // using periodic repetition
-     652           1 :         EXPECT_FLOAT_EQ(1.7 * 0.9 * 0.15, b.x);
-     653             :         
-     654             :         //tricubic
-     655             :         #ifdef HAVE_SIMD
-     656             :         grid.setInterpolationType(TRICUBIC);
-     657             :         
-     658           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.5) * spacing);
-     659           1 :         EXPECT_FLOAT_EQ(1.7, b.x);
-     660             : 
-     661           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.4) * spacing);
-     662           1 :         EXPECT_FLOAT_EQ(1.66005015373, b.x);
-     663             : 
-     664           1 :         b = grid.interpolate(Vector3d(0.5, 0.5, 1.6) * spacing);
-     665           1 :         EXPECT_FLOAT_EQ(1.66005003452, b.x);
-     666             : 
-     667           1 :         b = grid.interpolate(Vector3d(0.5, 0.35, 1.6) * spacing);
-     668           1 :         EXPECT_FLOAT_EQ(1.57507634163, b.x);
-     669             : 
-     670           1 :         b = grid.interpolate(Vector3d(0.5, 2.65, 1.6) * spacing);
-     671           1 :         EXPECT_FLOAT_EQ(0.190802007914, b.x);
-     672             :         #endif // HAVE_SIMD
-     673           1 : }
-     674             : 
-     675           2 : TEST(VectordGrid, Scale) {
-     676             :         // Test scaling a field
-     677           1 :         ref_ptr<Grid3f> grid = new Grid3f(Vector3d(0.), 3, 1);
-     678           4 :         for (int ix = 0; ix < 3; ix++)
-     679          12 :                 for (int iy = 0; iy < 3; iy++)
-     680          36 :                         for (int iz = 0; iz < 3; iz++)
-     681          27 :                                 grid->get(ix, iy, iz) = Vector3f(1, 0, 0);
-     682             : 
-     683           1 :         scaleGrid(grid, 5);
-     684           4 :         for (int ix = 0; ix < 3; ix++)
-     685          12 :                 for (int iy = 0; iy < 3; iy++)
-     686          36 :                         for (int iz = 0; iz < 3; iz++)
-     687          27 :                                 EXPECT_FLOAT_EQ(5, grid->interpolate(Vector3d(0.7, 0, 0.1)).x);
-     688           1 : }
-     689             : 
-     690           2 : TEST(Grid3f, Periodicity) {
-     691             :         // Test for periodic boundaries: grid(x+a*n) = grid(x)
-     692             :         size_t n = 3;
-     693             :         double spacing = 3;
-     694             :         double size = n * spacing;
-     695           1 :         Grid3f grid(Vector3d(0.), n, spacing);
-     696           4 :         for (int ix = 0; ix < 3; ix++)
-     697          12 :                 for (int iy = 0; iy < 3; iy++)
-     698          36 :                         for (int iz = 0; iz < 3; iz++)
-     699          27 :                                 grid.get(ix, iy, iz) = Vector3f(iz + ix, iy * iz, ix - iz * iy);
-     700             : 
-     701             :         Vector3d pos(1.2, 2.3, 0.7);
-     702             :         
-     703             :         //trilinear interpolated
-     704           1 :         Vector3f b = grid.interpolate(pos);
-     705           1 :         Vector3f b2 = grid.interpolate(pos + Vector3d(1, 0, 0) * size);
-     706           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     707           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     708           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     709             : 
-     710           1 :         b2 = grid.interpolate(pos + Vector3d(0, 5, 0) * size);
-     711           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     712           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     713           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     714             : 
-     715           1 :         b2 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
-     716           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     717           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     718           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     719             :         
-     720             :         //tricubic interpolated
-     721             :         #ifdef HAVE_SIMD
-     722             :         grid.setInterpolationType(TRICUBIC);
-     723           1 :         b = grid.interpolate(pos);
-     724           1 :         b2 = grid.interpolate(pos + Vector3d(1, 0, 0) * size);
-     725           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     726           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     727           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     728             : 
-     729           1 :         b2 = grid.interpolate(pos + Vector3d(0, 5, 0) * size);
-     730           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     731           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     732           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     733             : 
-     734           1 :         b2 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
-     735           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     736           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     737           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     738             :         #endif // HAVE_SIMD
-     739             :         
-     740             :         //nearest neighbour interpolated
-     741             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
-     742           1 :         b = grid.interpolate(pos);
-     743           1 :         b2 = grid.interpolate(pos + Vector3d(1, 0, 0) * size);
-     744           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     745           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     746           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     747             : 
-     748           1 :         b2 = grid.interpolate(pos + Vector3d(0, 5, 0) * size);
-     749           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     750           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     751           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     752             : 
-     753           1 :         b2 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
-     754           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     755           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     756           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     757             : 
-     758             :         //Test if grid is set to zero outside of volume for clipVolume=true
-     759             :         grid.setClipVolume(true);
-     760           1 :         Vector3f b3 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
-     761           1 :         EXPECT_FLOAT_EQ(0., b3.x);
-     762           1 :         EXPECT_FLOAT_EQ(0., b3.y);
-     763           1 :         EXPECT_FLOAT_EQ(0., b3.z);
-     764           1 : }
-     765             : 
-     766           2 : TEST(Grid3f, Reflectivity) {
-     767             :         // Test for reflective boundaries: grid(pos) = grid(x+a) = grid(-x-a)
-     768             :         size_t n = 3;
-     769             :         double spacing = 3;
-     770             :         double size = n * spacing;
-     771           1 :         Grid3f grid(Vector3d(0.), n, spacing);
-     772             :         grid.setReflective(true); //set reflective boundary
-     773           4 :         for (int ix = 0; ix < 3; ix++)
-     774          12 :                 for (int iy = 0; iy < 3; iy++)
-     775          36 :                         for (int iz = 0; iz < 3; iz++)
-     776          27 :                                 grid.get(ix, iy, iz) = Vector3f(iz + ix, iy * iz, ix - iz * iy);
-     777             : 
-     778             :         Vector3d pos(1.2, 2.3, 0.7);
-     779             :         
-     780             :         //trilinear interpolated
-     781           1 :         Vector3f b = grid.interpolate(pos + Vector3d(1,0,0) * spacing);
-     782           1 :         Vector3f b2 = grid.interpolate(pos *(-1) - Vector3d(1,0,0) * spacing);
-     783           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     784           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     785           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     786             :         
-     787           1 :         b = grid.interpolate(pos + Vector3d(0,5,0) * spacing);
-     788           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,5,0) * spacing);
-     789           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     790           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     791           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     792             :         
-     793           1 :         b = grid.interpolate(pos + Vector3d(0,0,-2) * spacing);
-     794           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,0,-2) * spacing);
-     795           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     796           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     797           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     798             :         
-     799             :         //tricubic interpolated
-     800             :         #ifdef HAVE_SIMD
-     801             :         grid.setInterpolationType(TRICUBIC);
-     802           1 :         b = grid.interpolate(pos + Vector3d(1,0,0) * spacing);
-     803           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(1,0,0) * spacing);
-     804           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     805           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     806           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     807             :         
-     808           1 :         b = grid.interpolate(pos + Vector3d(0,5,0) * spacing);
-     809           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,5,0) * spacing);
-     810           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     811           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     812           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     813             :         
-     814           1 :         b = grid.interpolate(pos + Vector3d(0,0,-2) * spacing);
-     815           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,0,-2) * spacing);
-     816           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     817           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     818           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     819             :         #endif //HAVE_SIMD
-     820             :         
-     821             :         //nearest neighbour interpolated
-     822             :         grid.setInterpolationType(NEAREST_NEIGHBOUR);
-     823           1 :         b = grid.interpolate(pos + Vector3d(1,0,0) * spacing);
-     824           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(1,0,0) * spacing);
-     825           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     826           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     827           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     828             :         
-     829           1 :         b = grid.interpolate(pos + Vector3d(0,5,0) * spacing);
-     830           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,5,0) * spacing);
-     831           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     832           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     833           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     834             :         
-     835           1 :         b = grid.interpolate(pos + Vector3d(0,0,-2) * spacing);
-     836           1 :         b2 = grid.interpolate(pos *(-1) - Vector3d(0,0,-2) * spacing);
-     837           1 :         EXPECT_FLOAT_EQ(b.x, b2.x);
-     838           1 :         EXPECT_FLOAT_EQ(b.y, b2.y);
-     839           1 :         EXPECT_FLOAT_EQ(b.z, b2.z);
-     840             : 
-     841             :         //Test if grid is set to zero outside of volume for clipVolume=true
-     842             :         grid.setClipVolume(true);
-     843           1 :         Vector3f b3 = grid.interpolate(pos + Vector3d(0, 0, -2) * size);
-     844           1 :         EXPECT_FLOAT_EQ(0., b3.x);
-     845           1 :         EXPECT_FLOAT_EQ(0., b3.y);
-     846           1 :         EXPECT_FLOAT_EQ(0., b3.z);
-     847           1 : }
-     848             : 
-     849           2 : TEST(Grid3f, DumpLoad) {
-     850             :         // Dump and load a field grid
-     851           1 :         ref_ptr<Grid3f> grid1 = new Grid3f(Vector3d(0.), 3, 1);
-     852           1 :         ref_ptr<Grid3f> grid2 = new Grid3f(Vector3d(0.), 3, 1);
-     853             : 
-     854           4 :         for (int ix = 0; ix < 3; ix++)
-     855          12 :                 for (int iy = 0; iy < 3; iy++)
-     856          36 :                         for (int iz = 0; iz < 3; iz++)
-     857          27 :                                 grid1->get(ix, iy, iz) = Vector3f(1, 2, 3);
-     858             : 
-     859           2 :         dumpGrid(grid1, "testDump.raw");
-     860           2 :         loadGrid(grid2, "testDump.raw");
-     861             : 
-     862           4 :         for (int ix = 0; ix < 3; ix++) {
-     863          12 :                 for (int iy = 0; iy < 3; iy++) {
-     864          36 :                         for (int iz = 0; iz < 3; iz++) {
-     865          27 :                                 Vector3f b1 = grid1->get(ix, iy, iz);
-     866             :                                 Vector3f b2 = grid2->get(ix, iy, iz);
-     867          27 :                                 EXPECT_FLOAT_EQ(b1.x, b2.x);
-     868          27 :                                 EXPECT_FLOAT_EQ(b1.y, b2.y);
-     869          27 :                                 EXPECT_FLOAT_EQ(b1.z, b2.z);
-     870             :                         }
-     871             :                 }
-     872             :         }
-     873           1 : }
-     874             : 
-     875           2 : TEST(Grid3f, DumpLoadTxt) {
-     876             :         // Dump and load a field grid
-     877           1 :         ref_ptr<Grid3f> grid1 = new Grid3f(Vector3d(0.), 3, 1);
-     878           1 :         ref_ptr<Grid3f> grid2 = new Grid3f(Vector3d(0.), 3, 1);
-     879             : 
-     880           4 :         for (int ix = 0; ix < 3; ix++)
-     881          12 :                 for (int iy = 0; iy < 3; iy++)
-     882          36 :                         for (int iz = 0; iz < 3; iz++)
-     883          27 :                                 grid1->get(ix, iy, iz) = Vector3f(ix, iy, iz);
-     884             : 
-     885           2 :         dumpGridToTxt(grid1, "testDump.txt", 1e4);
-     886           2 :         loadGridFromTxt(grid2, "testDump.txt", 1e-4);
-     887             : 
-     888           4 :         for (int ix = 0; ix < 3; ix++) {
-     889          12 :                 for (int iy = 0; iy < 3; iy++) {
-     890          36 :                         for (int iz = 0; iz < 3; iz++) {
-     891          27 :                                 Vector3f b1 = grid1->get(ix, iy, iz);
-     892             :                                 Vector3f b2 = grid2->get(ix, iy, iz);
-     893          27 :                                 EXPECT_FLOAT_EQ(b1.x, b2.x);
-     894          27 :                                 EXPECT_FLOAT_EQ(b1.y, b2.y);
-     895          27 :                                 EXPECT_FLOAT_EQ(b1.z, b2.z);
-     896             :                         }
-     897             :                 }
-     898             :         }
-     899           1 : }
-     900             : 
-     901           2 : TEST(Grid3f, Speed) {
-     902             :         // Dump and load a field grid
-     903           1 :         Grid3f grid(Vector3d(0.), 3, 3);
-     904           4 :         for (int ix = 0; ix < 3; ix++)
-     905          12 :                 for (int iy = 0; iy < 3; iy++)
-     906          36 :                         for (int iz = 0; iz < 3; iz++)
-     907          27 :                                 grid.get(ix, iy, iz) = Vector3f(1, 2, 3);
-     908             : 
-     909             :         Vector3d b;
-     910      100001 :         for (int i = 0; i < 100000; i++)
-     911      100000 :                 b = grid.interpolate(Vector3d(i));
-     912           1 : }
-     913             : 
-     914           2 : TEST(CylindricalProjectionMap, functions) {
-     915             :         Vector3d v;
-     916           1 :         v.setRThetaPhi(1.0, 1.2, 2.4);
-     917           1 :         EXPECT_NEAR(v.getPhi(), 2.4, .00001);
-     918           1 :         EXPECT_NEAR(v.getTheta(), 1.2, .000001);
-     919             : 
-     920             : 
-     921             : 
-     922           2 :         CylindricalProjectionMap cpm(24, 12);
-     923           1 :         size_t bin = 50;
-     924           1 :         Vector3d d = cpm.directionFromBin(bin);
-     925           1 :         size_t bin2 = cpm.binFromDirection(d);
-     926           1 :         EXPECT_EQ(bin, bin2);
-     927           1 : }
-     928             : 
-     929           1 : TEST(EmissionMap, functions) {
-     930             : 
-     931           1 :         EmissionMap em(360, 180, 100, 1 * EeV, 100 * EeV);
-     932           1 :         double e = em.energyFromBin(50);
-     933           1 :         size_t b = em.binFromEnergy(50 * EeV);
-     934             : 
-     935             :         Vector3d d(1.0, 0.0, 0.0);
-     936             : 
-     937           1 :         em.fillMap(1, 50 * EeV, d);
-     938             : 
-     939             :         Vector3d d2;
-     940             : 
-     941           1 :         bool r = em.drawDirection(1, 50 * EeV, d2);
-     942           1 :         EXPECT_TRUE(r);
-     943           1 :         EXPECT_TRUE(d.getAngleTo(d2) < (2. * M_PI / 180.));
-     944             : 
-     945           1 :         r = em.drawDirection(1, 30 * EeV, d2);
-     946           1 :         EXPECT_FALSE(r);
-     947             : 
-     948           1 :         r = em.drawDirection(2, 50 * EeV, d2);
-     949           1 :         EXPECT_FALSE(r);
-     950             : 
-     951           1 : }
-     952             : 
-     953           1 : TEST(EmissionMap, merge) {
-     954           1 :         EmissionMap em1, em2;
-     955           1 :         em1.fillMap(1, 50 * EeV, Vector3d(1.0, 0.0, 0.0));
-     956           1 :         em2.fillMap(1, 50 * EeV, Vector3d(0.0, 1.0, 0.0));
-     957           1 :         em2.fillMap(2, 50 * EeV, Vector3d(0.0, 1.0, 0.0));
-     958             : 
-     959           1 :         em1.merge(&em2);
-     960             : 
-     961           1 :         EXPECT_EQ(em1.getMaps().size(), 2);
-     962             : 
-     963           1 :         ref_ptr<CylindricalProjectionMap> cpm = em1.getMap(1, 50 * EeV);
-     964           1 :         size_t bin = cpm->binFromDirection(Vector3d(0.0, 1.0, 0.0));
-     965           1 :         EXPECT_TRUE(cpm->getPdf()[bin] > 0);
-     966           1 : }
-     967             : 
-     968           1 : TEST(Variant, copyToBuffer) {
-     969           1 :         double a = 23.42;
-     970             :         Variant v(a);
-     971             :         double b;
-     972           1 :         v.copyToBuffer(&b);
-     973           1 :         EXPECT_EQ(a, b);
-     974           1 : }
-     975             : 
-     976           1 : TEST(Variant, stringConversion) {
-     977           1 :         Variant v, w;
-     978             :         {
-     979           1 :                 int32_t a = 12;
-     980           1 :                 v = Variant::fromInt32(a);
-     981           1 :                 EXPECT_EQ(a, v.asInt32());
-     982             : 
-     983           1 :                 w = Variant::fromString(v.toString(), v.getType());
-     984           1 :                 EXPECT_EQ(a, w.asInt32());
-     985             :         }
-     986             : 
-     987             :         {
-     988           1 :                 int64_t a = 12;
-     989           1 :                 v = Variant::fromInt64(a);
-     990           1 :                 EXPECT_EQ(a, v.asInt64());
-     991             : 
-     992           1 :                 w = Variant::fromString(v.toString(), v.getType());
-     993           1 :                 EXPECT_EQ(a, w.asInt64());
-     994             :         }
-     995             : 
-     996             :         {
-     997             :                 Vector3d a(1, 2, 3);
-     998             :                 Variant v = Variant::fromVector3d(a);
-     999             :                 Vector3d u = v.asVector3d();
-    1000           1 :                 EXPECT_EQ(a.getX(), u.getX());
-    1001           1 :                 EXPECT_EQ(a.getY(), u.getY());
-    1002           1 :                 EXPECT_EQ(a.getZ(), u.getZ());
-    1003           1 :         }
-    1004             : 
-    1005             :         {
-    1006           1 :                 std::complex<double> a1(1, 1);
-    1007           1 :                 std::complex<double> a2(2, 0);
-    1008             :                 Vector3<std::complex<double>> a(a1, a1, a2);
-    1009             :                 Variant v = Variant::fromVector3c(a);
-    1010             :                 Vector3<std::complex<double>> u = v.asVector3c();
-    1011           1 :                 EXPECT_EQ(a1, u.getX());
-    1012           1 :                 EXPECT_EQ(a1, u.getY());
-    1013           1 :                 EXPECT_EQ(a2, u.getZ());
-    1014           1 :         }
-    1015             : 
-    1016             :         {
-    1017             :                 std::complex<double> a(1, 2);
-    1018             :                 Variant v = Variant::fromComplexDouble(a);
-    1019           1 :                 std::complex<double> u = v.asComplexDouble();
-    1020           1 :                 EXPECT_EQ(u.real(), 1);
-    1021           1 :                 EXPECT_EQ(u.imag(), 2);
-    1022           1 :         }
-    1023             : 
-    1024             :         {
-    1025             :                 std::vector<Variant> a;
-    1026           1 :                 a.push_back(Variant::fromDouble(1));
-    1027           1 :                 a.push_back(Variant::fromDouble(2));
-    1028           1 :                 a.push_back(Variant::fromDouble(3));
-    1029           1 :                 a.push_back(Variant::fromDouble(4));
-    1030             :                 Variant v = Variant::fromVector(a);
-    1031           1 :                 std::vector<Variant> u = v.asVector();
-    1032           1 :                 EXPECT_EQ(a[0], Variant::fromDouble(u[0]));
-    1033           1 :                 EXPECT_EQ(a[1], Variant::fromDouble(u[1]));
-    1034           1 :                 EXPECT_EQ(a[2], Variant::fromDouble(u[2]));
-    1035           1 :                 EXPECT_EQ(a[3], Variant::fromDouble(u[3]));
-    1036           1 :         }
-    1037             : 
-    1038             : 
-    1039           1 : }
-    1040             : 
-    1041           2 : TEST(Geometry, Plane) {
-    1042           1 :         Plane p(Vector3d(0,0,1), Vector3d(0,0,1));
-    1043           1 :         EXPECT_DOUBLE_EQ(-1., p.distance(Vector3d(0, 0, 0)));
-    1044           1 :         EXPECT_DOUBLE_EQ(9., p.distance(Vector3d(1, 1, 10)));
-    1045           1 : }
-    1046             : 
-    1047           2 : TEST(Geometry, Sphere) {
-    1048           1 :         Sphere s(Vector3d(0,0,0), 1.);
-    1049           1 :         EXPECT_DOUBLE_EQ(-1., s.distance(Vector3d(0, 0, 0)));
-    1050           1 :         EXPECT_DOUBLE_EQ(9., s.distance(Vector3d(10, 0, 0)));
-    1051           1 : }
-    1052             : 
-    1053           2 : TEST(Geometry, ParaxialBox) {
-    1054           1 :         ParaxialBox b(Vector3d(0,0,0), Vector3d(3,4,5));
-    1055           1 :         EXPECT_NEAR(-.1, b.distance(Vector3d(0.1, 0.1, 0.1)), 1E-10);
-    1056           1 :         EXPECT_NEAR(-.1, b.distance(Vector3d(0.1, 3.8, 0.1)), 1E-10);
-    1057           1 :         EXPECT_NEAR(-.2, b.distance(Vector3d(0.9, 3.8, 0.9)), 1E-10);
-    1058           1 :         EXPECT_NEAR(7., b.distance(Vector3d(10., 0., 0.)), 1E-10);
-    1059           1 :         EXPECT_NEAR(7., b.distance(Vector3d(10., 2., 0.)), 1E-10);
-    1060           1 :         EXPECT_NEAR(8., b.distance(Vector3d(-8., 0., 0.)), 1E-10);
-    1061           1 : }
-    1062             : 
-    1063           0 : int main(int argc, char **argv) {
-    1064           0 :         ::testing::InitGoogleTest(&argc, argv);
-    1065           0 :         return RUN_ALL_TESTS();
-    1066             : }
-    1067             : 
-    1068             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testDensity.cpp.func-sort-c.html b/doc/coverageReport/test/testDensity.cpp.func-sort-c.html deleted file mode 100644 index b1eb7ef54..000000000 --- a/doc/coverageReport/test/testDensity.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testDensity.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:166166100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa31testDensityList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa31testGridDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa35testConstantDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa36testGridDensity_testRetrunValue_Test8TestBodyEv1
_ZN7crpropa41testCordes_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa43testFerriere_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa44testNakanishi_checkValueAtCertainPoints_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testDensity.cpp.func.html b/doc/coverageReport/test/testDensity.cpp.func.html deleted file mode 100644 index 337e954df..000000000 --- a/doc/coverageReport/test/testDensity.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testDensity.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:166166100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa31testDensityList_SimpleTest_Test8TestBodyEv1
_ZN7crpropa31testGridDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa35testConstantDensity_SimpleTest_Test8TestBodyEv1
_ZN7crpropa36testGridDensity_testRetrunValue_Test8TestBodyEv1
_ZN7crpropa41testCordes_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa43testFerriere_checkValueAtCertainPoints_Test8TestBodyEv1
_ZN7crpropa44testNakanishi_checkValueAtCertainPoints_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testDensity.cpp.gcov.html b/doc/coverageReport/test/testDensity.cpp.gcov.html deleted file mode 100644 index 587a77d5d..000000000 --- a/doc/coverageReport/test/testDensity.cpp.gcov.html +++ /dev/null @@ -1,372 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testDensity.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testDensity.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:166166100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/massDistribution/Massdistribution.h"
-       2             : #include "crpropa/massDistribution/Cordes.h"
-       3             : #include "crpropa/massDistribution/Ferriere.h"
-       4             : #include "crpropa/massDistribution/Nakanishi.h"
-       5             : #include "crpropa/massDistribution/ConstantDensity.h"
-       6             : #include "crpropa/Units.h"
-       7             : #include "crpropa/Grid.h"
-       8             : 
-       9             : #include "gtest/gtest.h"
-      10             : 
-      11             : #include <stdexcept>
-      12             : #include <cmath>
-      13             : #include <string>
-      14             : 
-      15             : namespace crpropa {
-      16             : 
-      17           1 : TEST(testConstantDensity, SimpleTest) {
-      18             :         //test ConstantDensity in all types and in total density (output)
-      19           1 :         ConstantDensity n(2/ccm,3/ccm, 2/ccm);
-      20             :         Vector3d p(1*pc,2*pc,1*kpc);    // random position for testing density
-      21           1 :         EXPECT_DOUBLE_EQ(n.getHIDensity(p), 2e6);       // density output in m^-3
-      22           1 :         EXPECT_DOUBLE_EQ(n.getHIIDensity(p), 3e6);
-      23           1 :         EXPECT_DOUBLE_EQ( n.getH2Density(p), 2e6);
-      24           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p), 7e6);         // total density 2+3+2 = 7 (/ccm)
-      25           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),9e6);   // nucleon density 2+3+2*2 = 9 (/ccm) factor 2 for molecular hydrogen
-      26             : 
-      27             :         //test set/get function for used type
-      28           1 :         bool useHI = n.getIsForHI();
-      29           1 :         bool useHII= n.getIsForHII();
-      30           1 :         bool useH2 = n.getIsForH2();
-      31             :         //check if all types are activited
-      32           1 :         EXPECT_TRUE(useHI);
-      33           1 :         EXPECT_TRUE(useHII);
-      34           1 :         EXPECT_TRUE(useH2);
-      35             : 
-      36             :         //set density number to 500
-      37           1 :         n.setHI(500.);
-      38           1 :         n.setHII(500.);
-      39           1 :         n.setH2(500.);
-      40             : 
-      41             :         //check if output is changed to 500 in types and is 0 (all deactivated) for Hges
-      42           1 :         EXPECT_DOUBLE_EQ(n.getHIDensity(p), 500.);
-      43           1 :         EXPECT_DOUBLE_EQ(n.getHIIDensity(p), 500.);
-      44           1 :         EXPECT_DOUBLE_EQ(n.getH2Density(p), 500.);
-      45             : 
-      46             :         //deactivate all
-      47           1 :         n.setHI(false);
-      48           1 :         n.setHII(false);
-      49           1 :         n.setH2(false);
-      50             : 
-      51             :         //check if all isfor are set to false
-      52           1 :         useHI = n.getIsForHI();
-      53           1 :         useHII= n.getIsForHII();
-      54           1 :         useH2 = n.getIsForH2();
-      55           1 :         EXPECT_FALSE(useHI);
-      56           1 :         EXPECT_FALSE(useHII);
-      57           1 :         EXPECT_FALSE(useH2);
-      58             : 
-      59             :         //get<type>Density is independent of type activation, getDensity is not independent
-      60             :         //check if getDensity returns 0. (should give a error message in log file)
-      61           1 :         ::testing::internal::CaptureStderr();
-      62           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p), 0);
-      63           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),0);
-      64           1 :         std::string captured = testing::internal::GetCapturedStderr();
-      65           1 :         EXPECT_NE(captured.find("WARNING"), std::string::npos);
-      66           1 : }
-      67             : 
-      68             : 
-      69           2 : TEST(testDensityList, SimpleTest) {
-      70             : 
-      71             :         DensityList MS;
-      72           1 :         MS.addDensity(new ConstantDensity(1,1,2));      //sum 4
-      73           2 :         MS.addDensity(new ConstantDensity(2,3,1));      //sum 6
-      74             : 
-      75             :         Vector3d p(50*pc,10*pc,-30*pc); //random position for testing density
-      76           1 :         EXPECT_DOUBLE_EQ(MS.getHIDensity(p),3);
-      77           1 :         EXPECT_DOUBLE_EQ(MS.getHIIDensity(p),4);
-      78           1 :         EXPECT_DOUBLE_EQ(MS.getH2Density(p),3);
-      79           1 :         EXPECT_DOUBLE_EQ(MS.getDensity(p),10);  //sum of sums
-      80           1 :         EXPECT_DOUBLE_EQ(MS.getNucleonDensity(p),13);   // 3+4+2*3 factor 2 for molecular hydrogen
-      81             : 
-      82           1 : }
-      83             : 
-      84           2 : TEST(testCordes, checkValueAtCertainPoints) {
-      85             : 
-      86             :         Cordes n;
-      87             : 
-      88             :         //check type Information
-      89           1 :         EXPECT_FALSE(n.getIsForHI());
-      90           1 :         EXPECT_TRUE(n.getIsForHII());
-      91           1 :         EXPECT_FALSE(n.getIsForH2());
-      92             : 
-      93             :         Vector3d p(3.1*kpc,2.9*kpc,-30*pc);     //position for testing density
-      94             : 
-      95           1 :         EXPECT_NEAR(n.getHIIDensity(p), 184500.,1);     // output in m^-3 ; uncertainty of 1e-6 cm^-3
-      96           1 :         EXPECT_NEAR(n.getDensity(p), 184500.,1);
-      97           1 :         EXPECT_NEAR(n.getNucleonDensity(p), 184500,1);  // only HII component -> no differenz between density and nucleon density
-      98           1 :         p.z=30*pc;                      // invariant density for +/- z
-      99           1 :         EXPECT_NEAR(n.getDensity(p),184500,1);
-     100             : 
-     101           1 : }
-     102             : 
-     103           2 : TEST(testNakanishi, checkValueAtCertainPoints) {
-     104             : 
-     105             :         Nakanishi n;
-     106             : 
-     107             :         //check type Information
-     108           1 :         EXPECT_TRUE(n.getIsForHI());
-     109           1 :         EXPECT_FALSE(n.getIsForHII());
-     110           1 :         EXPECT_TRUE(n.getIsForH2());
-     111             : 
-     112             :         //first position for testing density
-     113             :         Vector3d p(4*kpc,-2.5*kpc,-0.85*kpc);
-     114             : 
-     115             :         //testing HI component
-     116           1 :         EXPECT_NEAR(n.getHIPlanedensity(p),162597,1);   //uncertaincy of 1e-6 cm^-3
-     117           1 :         EXPECT_NEAR(n.getHIScaleheight(p),0.3109*kpc,0.1*pc);
-     118           1 :         EXPECT_NEAR(n.getHIDensity(p),914,1);   //uncertainc 1e-6 cm^-3
-     119             : 
-     120             :         //testing H2 compontent
-     121           1 :         EXPECT_NEAR(n.getH2Planedensity(p),741999,1); //uncertaincy of 1e-6 cm^-3
-     122           1 :         EXPECT_NEAR(n.getH2Scaleheight(p),88.2*pc,0.1*pc);
-     123           1 :         EXPECT_NEAR(n.getH2Density(p),0,1);
-     124             : 
-     125             :         //testing total Density
-     126           1 :         EXPECT_NEAR(n.getDensity(p),914,2); //double uncertaincy for both type á 1cm^-3
-     127           1 :         EXPECT_NEAR(n.getNucleonDensity(p),914,2);      // 914 + 0*2    factor 2 for molecular hydrogen
-     128             : 
-     129             :         //second position for testing density
-     130             :         p = Vector3d(50*pc,100*pc,10*pc);
-     131             : 
-     132             :         //testing HI component
-     133           1 :         EXPECT_NEAR(n.getHIPlanedensity(p),543249,1);
-     134           1 :         EXPECT_NEAR(n.getHIScaleheight(p),125.6*pc,0.1*pc);
-     135           1 :         EXPECT_NEAR(n.getHIDensity(p),540867,1);
-     136             : 
-     137             :         //testing H2 component
-     138           1 :         EXPECT_NEAR(n.getH2Planedensity(p),10556748,1);
-     139           1 :         EXPECT_NEAR(n.getH2Scaleheight(p),57.2*pc,0.1*pc);
-     140           1 :         EXPECT_NEAR(n.getH2Density(p),10335137,1);
-     141             : 
-     142             :         //testing total Density
-     143           1 :         EXPECT_NEAR(n.getDensity(p),10876004,2);
-     144           1 :         EXPECT_NEAR(n.getNucleonDensity(p),21211141,2); // factor 2 in molecular hydrogen
-     145             : 
-     146             :         //test set type function
-     147           1 :         n.setIsForHI(false);
-     148           1 :         EXPECT_FALSE(n.getIsForHI());
-     149           1 :         EXPECT_TRUE(n.getIsForH2());
-     150             : 
-     151           1 :         n.setIsForH2(false);
-     152           1 :         EXPECT_FALSE(n.getIsForHI());
-     153           1 :         EXPECT_FALSE(n.getIsForH2());
-     154             : 
-     155             :         //check if density output is zero if all density-types are deaktivated (should give warning in log-file)
-     156           1 :         ::testing::internal::CaptureStderr();
-     157           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p),0);
-     158           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),0);
-     159           1 :         std::string captured = testing::internal::GetCapturedStderr();
-     160           1 :         EXPECT_NE(captured.find("WARNING"), std::string::npos);
-     161             : 
-     162           1 : }
-     163             : 
-     164           1 : TEST(testFerriere, checkValueAtCertainPoints) {
-     165           1 :         ::testing::internal::CaptureStderr();
-     166             :         Ferriere n;
-     167             : 
-     168             :         //check type information
-     169             : 
-     170           1 :         EXPECT_TRUE(n.getIsForHI());
-     171           1 :         EXPECT_TRUE(n.getIsForHII());
-     172           1 :         EXPECT_TRUE(n.getIsForH2());
-     173             : 
-     174             :         //testing density in inner Ring (R <= 3*kpc)
-     175             :         Vector3d p(60*pc,-60*pc,-20*pc);        //testing position in region of CMZ
-     176             : 
-     177             :         //test CMZ Trafo
-     178             :         Vector3d Trafo;
-     179           1 :         Trafo = n.CMZTransformation(p);
-     180           1 :         EXPECT_NEAR(Trafo.x,5.9767*pc,1e-4*pc);
-     181           1 :         EXPECT_NEAR(Trafo.y,12.8171*pc,1e-4*pc);
-     182           1 :         EXPECT_DOUBLE_EQ(Trafo.z,p.z);  //no transformation in z component
-     183             : 
-     184             :         //test DISK Trafo
-     185           1 :         Trafo = n.DiskTransformation(p);
-     186           1 :         EXPECT_NEAR(Trafo.x,11.0660*pc,1e-4*pc);
-     187           1 :         EXPECT_NEAR(Trafo.y,82.5860*pc,1e-4*pc);
-     188           1 :         EXPECT_NEAR(Trafo.z,-25.6338*pc,1e-4*pc);
-     189             : 
-     190             :         //testing density
-     191           1 :         EXPECT_NEAR(n.getHIDensity(p),6237723,1);       //uncertaincy 1e-6 cm^-3
-     192           1 :         EXPECT_NEAR(n.getH2Density(p),35484825,1);
-     193           1 :         EXPECT_NEAR(n.getHIIDensity(p),6243793,1);
-     194           1 :         EXPECT_NEAR(n.getDensity(p),47966341,1);
-     195           1 :         EXPECT_NEAR(n.getNucleonDensity(p),83451166,2);         //factor 2 in molecular hydrogen; double uncertaincy
-     196             : 
-     197             :         Vector3d p2(-500*pc,-900*pc,35*pc);     //testing position in region of the DISK
-     198           1 :         EXPECT_NEAR(n.getHIIDensity(p2),48190,1);
-     199           1 :         EXPECT_NEAR(n.getHIDensity(p2),5,1);
-     200           1 :         EXPECT_NEAR(n.getH2Density(p2),0,1);
-     201           1 :         EXPECT_NEAR(n.getDensity(p2),48195,1);
-     202           1 :         EXPECT_NEAR(n.getNucleonDensity(p2),48195,1);   // no H2 component -> no difference between density and nucleon-density
-     203             : 
-     204             :         //testing the outer region R>3kpc
-     205             :         Vector3d p3(5*kpc,4*kpc,-29*pc);        //testing position with 3kpc < R < R_sun
-     206           1 :         EXPECT_NEAR(n.getHIDensity(p3),540607,1);
-     207           1 :         EXPECT_NEAR(n.getHIIDensity(p3),66495 ,1);
-     208           1 :         EXPECT_NEAR(n.getH2Density(p3),2492685,1);
-     209           1 :         EXPECT_NEAR(n.getDensity(p3),3099787,1);
-     210           1 :         EXPECT_NEAR(n.getNucleonDensity(p3), 5592472,1);
-     211             : 
-     212             :         Vector3d p4(10*kpc,2*kpc,50*pc);        //testing position with R > R_sun
-     213           1 :         EXPECT_NEAR(n.getHIDensity(p4),431294,1);
-     214           1 :         EXPECT_NEAR(n.getHIIDensity(p4),22109,1);
-     215           1 :         EXPECT_NEAR(n.getH2Density(p4),54099,1);
-     216           1 :         EXPECT_NEAR(n.getDensity(p4),507502,1);
-     217           1 :         EXPECT_NEAR(n.getNucleonDensity(p4),561601,1);
-     218             : 
-     219             :         //test get/set type function
-     220           1 :         n.setIsForHI(false);
-     221           1 :         EXPECT_FALSE(n.getIsForHI());
-     222           1 :         EXPECT_TRUE(n.getIsForHII());
-     223           1 :         EXPECT_TRUE(n.getIsForH2());
-     224             : 
-     225           1 :         n.setIsForHII(false);
-     226           1 :         EXPECT_FALSE(n.getIsForHI());
-     227           1 :         EXPECT_FALSE(n.getIsForHII());
-     228           1 :         EXPECT_TRUE(n.getIsForH2());
-     229             : 
-     230           1 :         n.setIsForH2(false);
-     231           1 :         EXPECT_FALSE(n.getIsForHI());
-     232           1 :         EXPECT_FALSE(n.getIsForHII());
-     233           1 :         EXPECT_FALSE(n.getIsForH2());
-     234             : 
-     235             :         //check if density is set to zero if all types are deactivated (should give warning in log-file)
-     236           1 :         EXPECT_DOUBLE_EQ(n.getDensity(p),0);
-     237           1 :         EXPECT_DOUBLE_EQ(n.getNucleonDensity(p),0);
-     238           1 :         std::string captured = testing::internal::GetCapturedStderr();
-     239           1 :         EXPECT_NE(captured.find("WARNING"), std::string::npos);
-     240           1 : }
-     241             : 
-     242           2 : TEST(testGridDensity, SimpleTest) {
-     243           1 :         ref_ptr<Grid1f> grid = new Grid1f(Vector3d(0.), 1, 1, 1, 1.);     
-     244           1 :         DensityGrid dens = DensityGrid(grid, true, false, false);
-     245             : 
-     246             :         // check active types
-     247           1 :         EXPECT_TRUE(dens.getIsForHI()); 
-     248           1 :         EXPECT_FALSE(dens.getIsForHII());
-     249           1 :         EXPECT_FALSE(dens.getIsForH2());
-     250             : 
-     251             :         // check set function
-     252           1 :         dens.setIsForH2(true);
-     253           1 :         EXPECT_TRUE(dens.getIsForH2());
-     254             : 
-     255           1 :         dens.setIsForHII(true);
-     256           1 :         EXPECT_TRUE(dens.getIsForHII());
-     257             : 
-     258           1 :         dens.setIsForHI(false);
-     259           1 :         EXPECT_FALSE(dens.getIsForHI());
-     260           1 : }
-     261             : 
-     262           2 : TEST(testGridDensity, testRetrunValue) {
-     263             :         size_t Nx = 5;
-     264             :         size_t Ny = 8;
-     265             :         size_t Nz = 10;
-     266             :         double spacing = 2.0;
-     267             :         Vector3d origin(1., 2., 3.);
-     268             : 
-     269           1 :         ref_ptr<Grid1f> grid = new Grid1f(origin, Nx, Ny, Nz, spacing);
-     270             : 
-     271             :         // set some values for the grid
-     272           1 :         grid->get(3, 2, 4) = 5;
-     273           1 :         grid->get(3, 2, 5) = 12;
-     274           1 :         grid->get(2, 3, 4) = 6;
-     275             : 
-     276           2 :         DensityGrid dens = DensityGrid(grid, true, false, false);
-     277             : 
-     278             :         // a point in the region where values are defined for the grid.
-     279             :         Vector3d position = origin + Vector3d(2.2, 2.8, 4.1) * spacing; 
-     280           1 :         double valueFromGrid =  grid->interpolate(position);
-     281           1 :         double nHI = dens.getHIDensity(position);
-     282           1 :         double nHII = dens.getHIIDensity(position);
-     283           1 :         double nH2 = dens.getH2Density(position);
-     284           1 :         double nNucleon = dens.getNucleonDensity(position);
-     285           1 :         double nTotal = dens.getDensity(position);
-     286             : 
-     287             :         // Check for values
-     288           1 :         EXPECT_DOUBLE_EQ(valueFromGrid, nHI);
-     289           1 :         EXPECT_DOUBLE_EQ(nHII, 0);      // HII is set to false and should be 0
-     290           1 :         EXPECT_DOUBLE_EQ(nH2, 0);       // H2 is set to false and should be 0
-     291           1 :         EXPECT_DOUBLE_EQ(nNucleon, valueFromGrid);
-     292           1 :         EXPECT_DOUBLE_EQ(nTotal, valueFromGrid);
-     293           1 : }
-     294             : 
-     295             : 
-     296             : } //namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html b/doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html deleted file mode 100644 index 1eaa671c2..000000000 --- a/doc/coverageReport/test/testFunctionalGroups.cpp.func-sort-c.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testFunctionalGroups.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testFunctionalGroups.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:202387.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa36testFunctionalGroups_gyroradius_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testFunctionalGroups.cpp.func.html b/doc/coverageReport/test/testFunctionalGroups.cpp.func.html deleted file mode 100644 index 24b5d5269..000000000 --- a/doc/coverageReport/test/testFunctionalGroups.cpp.func.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testFunctionalGroups.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testFunctionalGroups.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:202387.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- -
- - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa36testFunctionalGroups_gyroradius_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html b/doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html deleted file mode 100644 index e6bdc1708..000000000 --- a/doc/coverageReport/test/testFunctionalGroups.cpp.gcov.html +++ /dev/null @@ -1,126 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testFunctionalGroups.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testFunctionalGroups.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:202387.0 %
Date:2024-04-08 14:58:22Functions:1250.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "CRPropa.h"
-       2             : #include "gtest/gtest.h"
-       3             : 
-       4             : namespace crpropa {
-       5             : 
-       6             : /*
-       7             :  * Functional test which calculates the particle's gyroradius in a uniform field
-       8             :  * r_g = R / (B*c) = 1 EV / (1 nG * c) \approx 1.08*Mpc
-       9             :  */
-      10           2 : TEST(testFunctionalGroups, gyroradius) {
-      11             :         double energy = 1*EeV;
-      12             :         double field = 1*nG;
-      13             : 
-      14           1 :         ParticleState p;
-      15           1 :         p.setId(nucleusId(1, 1));
-      16           1 :         p.setEnergy(energy);
-      17           1 :         p.setPosition(Vector3d(0, 0, 0));
-      18           1 :         p.setDirection(Vector3d(0, 0, 1));
-      19             : 
-      20           1 :         ref_ptr<Candidate> c = new Candidate(p);
-      21           1 :         ref_ptr<PropagationCK> propa = new PropagationCK(new UniformMagneticField(Vector3d(field, 0, 0)));
-      22           1 :         ref_ptr<ParticleCollector> collector = new ParticleCollector();
-      23           1 :         collector->setClone(true);
-      24           1 :         ref_ptr<ModuleList> sim = new ModuleList();
-      25             : 
-      26             :         Vector3d pos;
-      27             :         double max_y = 0;
-      28             : 
-      29           1 :         sim->add(propa);
-      30           1 :         sim->add(new MaximumTrajectoryLength(10*Mpc));
-      31           1 :         sim->add(collector);
-      32             : 
-      33           1 :         sim->run(c);
-      34             : 
-      35          16 :         for (ParticleCollector::iterator itr = collector->begin(); itr != collector->end(); ++itr){
-      36          15 :                 pos = (*(itr->get())).current.getPosition();
-      37          15 :                 if (max_y < pos.getY())
-      38             :                         max_y = pos.getY();
-      39             :         }
-      40             : 
-      41           1 :         EXPECT_NEAR(max_y/2.0, energy/(field * c_light * eplus), 0.01*Mpc);
-      42             : 
-      43           1 : }
-      44             : 
-      45           0 : int main(int argc, char **argv) {
-      46           0 :         ::testing::InitGoogleTest(&argc, argv);
-      47           0 :         return RUN_ALL_TESTS();
-      48             : }
-      49             : 
-      50             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testInteraction.cpp.func-sort-c.html b/doc/coverageReport/test/testInteraction.cpp.func-sort-c.html deleted file mode 100644 index e28ec63a0..000000000 --- a/doc/coverageReport/test/testInteraction.cpp.func-sort-c.html +++ /dev/null @@ -1,284 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testInteraction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testInteraction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:74378794.4 %
Date:2024-04-08 14:58:22Functions:525398.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa24Redshift_simpleTest_Test8TestBodyEv1
_ZN7crpropa25NuclearDecay_helium5_Test8TestBodyEv1
_ZN7crpropa26NuclearDecay_lithium4_Test8TestBodyEv1
_ZN7crpropa28NuclearDecay_scandium44_Test8TestBodyEv1
_ZN7crpropa29NuclearDecay_secondaries_Test8TestBodyEv1
_ZN7crpropa29PhotoDisintegration_iron_Test8TestBodyEv1
_ZN7crpropa31NuclearDecay_limitNextStep_Test8TestBodyEv1
_ZN7crpropa31PhotoDisintegration_carbon_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_helium_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_proton_Test8TestBodyEv1
_ZN7crpropa32NuclearDecay_interactionTag_Test8TestBodyEv1
_ZN7crpropa33EMPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa33PhotoPionProduction_sampling_Test8TestBodyEv1
_ZN7crpropa34ElasticScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa35EMPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa35Redshift_limitRedshiftDecrease_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_allChannelsWorking_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa36PhotoDisintegration_allIsotopes_Test8TestBodyEv1
_ZN7crpropa36PhotoPionProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa37ElasticScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesCMB_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesIRB_Test8TestBodyEv1
_ZN7crpropa38PhotoDisintegration_limitNextStep_Test8TestBodyEv1
_ZN7crpropa38PhotoPionProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa39EMDoublePairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_interactionTag_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa40EMTripletPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa40SynchrotronRadiation_interactionTag_Test8TestBodyEv1
_ZN7crpropa41EMDoublePairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa42EMTripletPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43EMInverseComptonScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43PhotoDisintegration_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa43PhotoPionProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa44ElectronPairProduction_energyDecreasing_Test8TestBodyEv1
_ZN7crpropa45EMInverseComptonScattering_limitNextStep_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_interactionTag_Test8TestBodyEv1
_ZN7crpropa46ElectronPairProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa47ElectronPairProduction_belowEnergyTreshold_Test8TestBodyEv1
_ZN7crpropa55Photodisintegration_updateParticleParentProperties_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testInteraction.cpp.func.html b/doc/coverageReport/test/testInteraction.cpp.func.html deleted file mode 100644 index ded452dfc..000000000 --- a/doc/coverageReport/test/testInteraction.cpp.func.html +++ /dev/null @@ -1,284 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testInteraction.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testInteraction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:74378794.4 %
Date:2024-04-08 14:58:22Functions:525398.1 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa24Redshift_simpleTest_Test8TestBodyEv1
_ZN7crpropa25NuclearDecay_helium5_Test8TestBodyEv1
_ZN7crpropa26NuclearDecay_lithium4_Test8TestBodyEv1
_ZN7crpropa28NuclearDecay_scandium44_Test8TestBodyEv1
_ZN7crpropa29NuclearDecay_secondaries_Test8TestBodyEv1
_ZN7crpropa29PhotoDisintegration_iron_Test8TestBodyEv1
_ZN7crpropa31NuclearDecay_limitNextStep_Test8TestBodyEv1
_ZN7crpropa31PhotoDisintegration_carbon_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_helium_Test8TestBodyEv1
_ZN7crpropa31PhotoPionProduction_proton_Test8TestBodyEv1
_ZN7crpropa32NuclearDecay_interactionTag_Test8TestBodyEv1
_ZN7crpropa33EMPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa33PhotoPionProduction_sampling_Test8TestBodyEv1
_ZN7crpropa34ElasticScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa35EMPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa35Redshift_limitRedshiftDecrease_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa36EMPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_allChannelsWorking_Test8TestBodyEv1
_ZN7crpropa36NuclearDecay_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa36PhotoDisintegration_allIsotopes_Test8TestBodyEv1
_ZN7crpropa36PhotoPionProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa37ElasticScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesCMB_Test8TestBodyEv1
_ZN7crpropa37ElectronPairProduction_valuesIRB_Test8TestBodyEv1
_ZN7crpropa38PhotoDisintegration_limitNextStep_Test8TestBodyEv1
_ZN7crpropa38PhotoPionProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa39EMDoublePairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoDisintegration_interactionTag_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa39PhotoPionProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa40EMTripletPairProduction_secondaries_Test8TestBodyEv1
_ZN7crpropa40SynchrotronRadiation_interactionTag_Test8TestBodyEv1
_ZN7crpropa41EMDoublePairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42EMDoublePairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa42EMTripletPairProduction_limitNextStep_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa42ElectronPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43EMInverseComptonScattering_secondaries_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa43EMTripletPairProduction_interactionTag_Test8TestBodyEv1
_ZN7crpropa43PhotoDisintegration_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa43PhotoPionProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa44ElectronPairProduction_energyDecreasing_Test8TestBodyEv1
_ZN7crpropa45EMInverseComptonScattering_limitNextStep_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_allBackgrounds_Test8TestBodyEv1
_ZN7crpropa46EMInverseComptonScattering_interactionTag_Test8TestBodyEv1
_ZN7crpropa46ElectronPairProduction_thisIsNotNucleonic_Test8TestBodyEv1
_ZN7crpropa47ElectronPairProduction_belowEnergyTreshold_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
_ZN7crpropa55Photodisintegration_updateParticleParentProperties_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testInteraction.cpp.gcov.html b/doc/coverageReport/test/testInteraction.cpp.gcov.html deleted file mode 100644 index a903e964c..000000000 --- a/doc/coverageReport/test/testInteraction.cpp.gcov.html +++ /dev/null @@ -1,1229 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testInteraction.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testInteraction.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:74378794.4 %
Date:2024-04-08 14:58:22Functions:525398.1 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Candidate.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/PhotonBackground.h"
-       5             : #include "crpropa/module/ElectronPairProduction.h"
-       6             : #include "crpropa/module/NuclearDecay.h"
-       7             : #include "crpropa/module/PhotoDisintegration.h"
-       8             : #include "crpropa/module/ElasticScattering.h"
-       9             : #include "crpropa/module/PhotoPionProduction.h"
-      10             : #include "crpropa/module/Redshift.h"
-      11             : #include "crpropa/module/EMPairProduction.h"
-      12             : #include "crpropa/module/EMDoublePairProduction.h"
-      13             : #include "crpropa/module/EMTripletPairProduction.h"
-      14             : #include "crpropa/module/EMInverseComptonScattering.h"
-      15             : #include "crpropa/module/SynchrotronRadiation.h"
-      16             : #include "gtest/gtest.h"
-      17             : 
-      18             : #include <fstream>
-      19             : 
-      20             : namespace crpropa {
-      21             : 
-      22             : // ElectronPairProduction -----------------------------------------------------
-      23           1 : TEST(ElectronPairProduction, allBackgrounds) {
-      24             :         // Test if interaction data files are loaded.
-      25           1 :         ref_ptr<PhotonField> cmb = new CMB();
-      26           1 :         ElectronPairProduction epp(cmb);
-      27           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-      28           1 :         epp.setPhotonField(irb);
-      29           2 :         irb = new IRB_Stecker05();
-      30           1 :         epp.setPhotonField(irb);
-      31           2 :         irb = new IRB_Franceschini08();
-      32           1 :         epp.setPhotonField(irb);
-      33           2 :         irb = new IRB_Finke10();
-      34           1 :         epp.setPhotonField(irb);
-      35           2 :         irb = new IRB_Dominguez11();
-      36           1 :         epp.setPhotonField(irb);
-      37           2 :         irb = new IRB_Gilmore12();
-      38           1 :         epp.setPhotonField(irb);
-      39           2 :         irb = new IRB_Stecker16_upper();
-      40           1 :         epp.setPhotonField(irb);
-      41           2 :         irb = new IRB_Stecker16_lower();
-      42           1 :         epp.setPhotonField(irb);
-      43           2 :     irb = new IRB_Finke22();
-      44           2 :         epp.setPhotonField(irb);
-      45           2 : }
-      46             : 
-      47           1 : TEST(ElectronPairProduction, energyDecreasing) {
-      48             :         // Test if energy loss occurs for protons with energies from 1e15 - 1e23 eV.
-      49           1 :         Candidate c;
-      50           1 :         c.setCurrentStep(2 * Mpc);
-      51           1 :         c.current.setId(nucleusId(1, 1)); // proton
-      52             : 
-      53           1 :         ref_ptr<PhotonField> cmb = new CMB();
-      54           1 :         ElectronPairProduction epp1(cmb);
-      55          81 :         for (int i = 0; i < 80; i++) {
-      56          80 :                 double E = pow(10, 15 + i * 0.1) * eV;
-      57          80 :                 c.current.setEnergy(E);
-      58          80 :                 epp1.process(&c);
-      59          80 :                 EXPECT_LE(c.current.getEnergy(), E);
-      60             :         }
-      61             : 
-      62           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-      63           2 :         ElectronPairProduction epp2(irb);
-      64          81 :         for (int i = 0; i < 80; i++) {
-      65          80 :                 double E = pow(10, 15 + i * 0.1) * eV;
-      66          80 :                 c.current.setEnergy(E);
-      67          80 :                 epp2.process(&c);
-      68          80 :                 EXPECT_LE(c.current.getEnergy(), E);
-      69             :         }
-      70           2 : }
-      71             : 
-      72           1 : TEST(ElectronPairProduction, belowEnergyTreshold) {
-      73             :         // Test if nothing happens below 1e15 eV.
-      74           1 :         ref_ptr<PhotonField> cmb = new CMB();
-      75           1 :         ElectronPairProduction epp(cmb);
-      76           1 :         Candidate c(nucleusId(1, 1), 1E14 * eV);
-      77           1 :         epp.process(&c);
-      78           1 :         EXPECT_DOUBLE_EQ(1E14 * eV, c.current.getEnergy());
-      79           2 : }
-      80             : 
-      81           1 : TEST(ElectronPairProduction, thisIsNotNucleonic) {
-      82             :         // Test if non-nuclei are skipped.
-      83           1 :         ref_ptr<PhotonField> cmb = new CMB();
-      84           1 :         ElectronPairProduction epp(cmb);
-      85           1 :         Candidate c(11, 1E20 * eV);  // electron
-      86           1 :         epp.process(&c);
-      87           1 :         EXPECT_DOUBLE_EQ(1E20 * eV, c.current.getEnergy());
-      88           2 : }
-      89             : 
-      90           2 : TEST(ElectronPairProduction, valuesCMB) {
-      91             :         // Test if energy loss corresponds to the data table.
-      92             :         std::vector<double> x;
-      93             :         std::vector<double> y;
-      94           2 :         std::ifstream infile(getDataPath("pair_CMB.txt").c_str());
-      95           1 :         while (infile.good()) {
-      96           0 :                 if (infile.peek() != '#') {
-      97             :                         double a, b;
-      98             :                         infile >> a >> b;
-      99           0 :                         if (infile) {
-     100           0 :                                 x.push_back(a * eV);
-     101           0 :                                 y.push_back(b * eV / Mpc);
-     102             :                         }
-     103             :                 }
-     104           0 :                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-     105             :         }
-     106           1 :         infile.close();
-     107             : 
-     108           1 :         Candidate c;
-     109           1 :         c.setCurrentStep(1 * Mpc);
-     110           1 :         c.current.setId(nucleusId(1, 1)); // proton
-     111           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     112             : 
-     113           1 :         ElectronPairProduction epp(cmb);
-     114           1 :         for (int i = 0; i < x.size(); i++) {
-     115           0 :                 c.current.setEnergy(x[i]);
-     116           0 :                 epp.process(&c);
-     117           0 :                 double dE = x[i] - c.current.getEnergy();
-     118           0 :                 double dE_table = y[i] * 1 * Mpc;
-     119           0 :                 EXPECT_NEAR(dE_table, dE, 1e-12);
-     120             :         }
-     121           3 : }
-     122             : 
-     123           1 : TEST(ElectronPairProduction, interactionTag) {
-     124             :         
-     125           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     126           0 :         ElectronPairProduction epp(cmb);
-     127             :         
-     128             :         // test the default interaction tag
-     129           2 :         EXPECT_TRUE(epp.getInteractionTag() == "EPP");
-     130             : 
-     131             :         // test changing the interaction tag
-     132           1 :         epp.setInteractionTag("myTag");
-     133           2 :         EXPECT_TRUE(epp.getInteractionTag() == "myTag");
-     134             : 
-     135             :         // test the tag of produced secondaries
-     136           2 :         Candidate c;
-     137           1 :         c.setCurrentStep(1 * Gpc);
-     138           1 :         c.current.setId(nucleusId(1,1));
-     139           1 :         c.current.setEnergy(100 * EeV);
-     140           1 :         epp.setHaveElectrons(true);
-     141           1 :         epp.process(&c);
-     142             :         
-     143           1 :         std::string secondaryTag = c.secondaries[0] -> getTagOrigin();
-     144           1 :         EXPECT_TRUE(secondaryTag == "myTag");
-     145           2 : }
-     146             : 
-     147           2 : TEST(ElectronPairProduction, valuesIRB) {
-     148             :         // Test if energy loss corresponds to the data table.
-     149             :         std::vector<double> x;
-     150             :         std::vector<double> y;
-     151           2 :         std::ifstream infile(getDataPath("pairIRB.txt").c_str());
-     152           1 :         while (infile.good()) {
-     153           0 :                 if (infile.peek() != '#') {
-     154             :                         double a, b;
-     155             :                         infile >> a >> b;
-     156           0 :                         if (infile) {
-     157           0 :                                 x.push_back(a * eV);
-     158           0 :                                 y.push_back(b * eV / Mpc);
-     159             :                         }
-     160             :                 }
-     161           0 :                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-     162             :         }
-     163           1 :         infile.close();
-     164             : 
-     165           1 :         Candidate c;
-     166           1 :         c.setCurrentStep(1 * Mpc);
-     167           1 :         c.current.setId(nucleusId(1, 1)); // proton
-     168           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-     169             : 
-     170           1 :         ElectronPairProduction epp(irb);
-     171           1 :         for (int i = 0; i < x.size(); i++) {
-     172           0 :                 c.current.setEnergy(x[i]);
-     173           0 :                 epp.process(&c);
-     174           0 :                 double dE = x[i] - c.current.getEnergy();
-     175           0 :                 double dE_table = y[i] * 1 * Mpc;
-     176           0 :                 EXPECT_NEAR(dE, dE_table, 1e-12);
-     177             :         }
-     178           3 : }
-     179             : 
-     180             : // NuclearDecay ---------------------------------------------------------------
-     181           1 : TEST(NuclearDecay, scandium44) {
-     182             :         // Test beta+ decay of 44Sc to 44Ca.
-     183             :         // This test can stochastically fail.
-     184           1 :         NuclearDecay d(true, true);
-     185           1 :         Candidate c(nucleusId(44, 21), 1E18 * eV);
-     186           1 :         c.setCurrentStep(100 * Mpc);
-     187           1 :         double gamma = c.current.getLorentzFactor();
-     188           1 :         d.process(&c);
-     189             :         
-     190             :         // expected decay product: 44Ca
-     191           1 :         EXPECT_EQ(nucleusId(44, 20), c.current.getId());
-     192             : 
-     193             :         // expect Lorentz factor to be conserved
-     194           1 :         EXPECT_DOUBLE_EQ(gamma, c.current.getLorentzFactor());
-     195             :         
-     196             :         // expect at least two secondaries: positron + electron neutrino
-     197           1 :         EXPECT_GE(c.secondaries.size(), 2);
-     198           1 : }
-     199             : 
-     200           1 : TEST(NuclearDecay, lithium4) {
-     201             :         // Test proton dripping of Li-4 to He-3
-     202             :         // This test can stochastically fail
-     203           1 :         NuclearDecay d;
-     204           1 :         Candidate c(nucleusId(4, 3), 4 * EeV);
-     205           1 :         c.setCurrentStep(100 * Mpc);
-     206           1 :         d.process(&c);
-     207             :         
-     208             :         // expected decay product: He-3
-     209           1 :         EXPECT_EQ(nucleusId(3, 2), c.current.getId());
-     210             : 
-     211             :         // expected secondary: proton
-     212           1 :         EXPECT_EQ(1, c.secondaries.size());
-     213           2 :         Candidate c1 = *c.secondaries[0];
-     214           1 :         EXPECT_EQ(nucleusId(1, 1), c1.current.getId());
-     215           1 :         EXPECT_EQ(1 * EeV, c1.current.getEnergy());
-     216           1 : }
-     217             : 
-     218           1 : TEST(NuclearDecay, helium5) {
-     219             :         // Test neutron dripping of He-5 to He-4.
-     220             :         // This test can stochastically fail.
-     221           1 :         NuclearDecay d;
-     222           1 :         Candidate c(nucleusId(5, 2), 5 * EeV);
-     223           1 :         c.setCurrentStep(100 * Mpc);
-     224           1 :         d.process(&c);
-     225             : 
-     226             :         // expected primary: He-4
-     227           1 :         EXPECT_EQ(nucleusId(4, 2), c.current.getId());
-     228           1 :         EXPECT_EQ(4, c.current.getEnergy() / EeV);
-     229             :         
-     230             :         // expected secondary: neutron
-     231           2 :         Candidate c2 = *c.secondaries[0];
-     232           1 :         EXPECT_EQ(nucleusId(1, 0), c2.current.getId());
-     233           1 :         EXPECT_EQ(1, c2.current.getEnergy() / EeV);
-     234           1 : }
-     235             : 
-     236           1 : TEST(NuclearDecay, limitNextStep) {
-     237             :         // Test if next step is limited in case of a neutron.
-     238           1 :         NuclearDecay decay;
-     239           1 :         Candidate c(nucleusId(1, 0), 10 * EeV);
-     240           1 :         c.setNextStep(std::numeric_limits<double>::max());
-     241           1 :         decay.process(&c);
-     242           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
-     243           1 : }
-     244             : 
-     245           1 : TEST(NuclearDecay, allChannelsWorking) {
-     246             :         // Test if all nuclear decays are working.
-     247           1 :         NuclearDecay d;
-     248           1 :         Candidate c;
-     249             : 
-     250           2 :         std::ifstream infile(getDataPath("nuclear_decay.txt").c_str());
-     251         951 :         while (infile.good()) {
-     252         950 :                 if (infile.peek() != '#') {
-     253             :                         int Z, N, channel, foo;
-     254         948 :                         infile >> Z >> N >> channel >> foo;
-     255         948 :                         c.current.setId(nucleusId(Z + N, Z));
-     256         948 :                         c.current.setEnergy(80 * EeV);
-     257         948 :                         d.performInteraction(&c, channel);
-     258             :                 }
-     259         950 :                 infile.ignore(std::numeric_limits<std::streamsize>::max(), '\n');
-     260             :         }
-     261           1 :         infile.close();
-     262           1 : }
-     263             : 
-     264           1 : TEST(NuclearDecay, secondaries) {
-     265             :         // Test if all types of secondaries are produced.
-     266           1 :         NuclearDecay d;
-     267           1 :         d.setHaveElectrons(true);
-     268           1 :         d.setHaveNeutrinos(true);
-     269           1 :         d.setHavePhotons(true);
-     270           1 :         Candidate c;
-     271             : 
-     272             :         // He-8 --> Li-8 + e- + neutrino
-     273             :         // additional photon emitted with 84% probability
-     274             :         // --> expect at least 1 photon out of 10 decays
-     275          11 :         for (int i = 0; i < 10; ++i) {
-     276          10 :                 c.current.setId(nucleusId(8, 2));
-     277          10 :                 c.current.setEnergy(5 * EeV);
-     278          10 :                 d.performInteraction(&c, 10000);
-     279             :         }
-     280             : 
-     281             :         // count number of secondaries
-     282           1 :         size_t nElectrons = 0;
-     283           1 :         size_t nNeutrinos = 0;
-     284           1 :         size_t nPhotons = 0;
-     285             : 
-     286          30 :         for(size_t i = 0; i < c.secondaries.size(); ++i) {
-     287          29 :                 int id = (*c.secondaries[i]).current.getId();
-     288          29 :                 if (id == 22) nPhotons++;
-     289          29 :                 if (id == 11) nElectrons++;
-     290          29 :                 if (id == -12) nNeutrinos++;
-     291             :         }
-     292             : 
-     293           1 :         EXPECT_EQ(nElectrons, 10);
-     294           1 :         EXPECT_EQ(nNeutrinos, 10);
-     295           1 :         EXPECT_GE(nPhotons, 1);
-     296           1 : }
-     297             : 
-     298           1 : TEST(NuclearDecay, thisIsNotNucleonic) {
-     299             :         // Test if nothing happens to an electron
-     300           1 :         NuclearDecay decay;
-     301           1 :         Candidate c(11, 10 * EeV);
-     302           1 :         c.setNextStep(std::numeric_limits<double>::max());
-     303           1 :         decay.process(&c);
-     304           1 :         EXPECT_EQ(11, c.current.getId());
-     305           1 :         EXPECT_EQ(10 * EeV, c.current.getEnergy());
-     306           1 : }
-     307             : 
-     308           1 : TEST(NuclearDecay, interactionTag) {
-     309             :         // test default interaction tag
-     310           1 :         NuclearDecay decay;
-     311           2 :         EXPECT_TRUE(decay.getInteractionTag() == "ND");
-     312             : 
-     313             :         // test secondary tag
-     314           1 :         decay.setHaveElectrons(true);
-     315           2 :         Candidate c(nucleusId(8,2), 5 * EeV);
-     316           1 :         decay.performInteraction(&c, 10000);
-     317           3 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "ND");
-     318             : 
-     319             :         // test custom tags
-     320           1 :         decay.setInteractionTag("myTag");
-     321           2 :         EXPECT_TRUE(decay.getInteractionTag() == "myTag");
-     322           1 : }
-     323             : 
-     324             : // PhotoDisintegration --------------------------------------------------------
-     325           1 : TEST(PhotoDisintegration, allBackgrounds) {
-     326             :         // Test if interaction data files are loaded.
-     327           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     328           1 :         PhotoDisintegration pd(cmb);
-     329           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-     330           1 :         pd.setPhotonField(irb);
-     331           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
-     332           1 :         pd.setPhotonField(urb);
-     333           2 :         irb = new IRB_Stecker05();
-     334           1 :         pd.setPhotonField(irb);
-     335           2 :         irb = new IRB_Franceschini08();
-     336           1 :         pd.setPhotonField(irb);
-     337           2 :         irb = new IRB_Finke10();
-     338           1 :         pd.setPhotonField(irb);
-     339           2 :         irb = new IRB_Dominguez11();
-     340           1 :         pd.setPhotonField(irb);
-     341           2 :         irb = new IRB_Gilmore12();
-     342           1 :         pd.setPhotonField(irb);
-     343           2 :         irb = new IRB_Stecker16_upper();
-     344           1 :         pd.setPhotonField(irb);
-     345           2 :         irb = new IRB_Stecker16_lower();
-     346           1 :         pd.setPhotonField(irb);
-     347           2 :     irb = new IRB_Finke22();
-     348           1 :         pd.setPhotonField(irb);
-     349           2 :         urb = new URB_Nitu21();
-     350           2 :         pd.setPhotonField(urb);
-     351           2 : }
-     352             : 
-     353           1 : TEST(PhotoDisintegration, carbon) {
-     354             :         // Test if a 100 EeV C-12 nucleus photo-disintegrates (at least once) over a distance of 1 Gpc.
-     355             :         // This test can stochastically fail.
-     356           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     357           1 :         PhotoDisintegration pd(cmb);
-     358           1 :         Candidate c;
-     359           1 :         int id = nucleusId(12, 6);
-     360           1 :         c.current.setId(id);
-     361           1 :         c.current.setEnergy(100 * EeV);
-     362           1 :         c.setCurrentStep(1000 * Mpc);
-     363           1 :         pd.process(&c);
-     364             : 
-     365           1 :         EXPECT_TRUE(c.current.getEnergy() < 100 * EeV);
-     366             :         // energy loss
-     367           1 :         EXPECT_TRUE(c.secondaries.size() > 0);
-     368             :         // secondaries produced
-     369             : 
-     370           1 :         double E = c.current.getEnergy();
-     371           1 :         id = c.current.getId();
-     372           1 :         int A = massNumber(id);
-     373           1 :         int Z = chargeNumber(id);
-     374             : 
-     375           2 :         for (int i = 0; i < c.secondaries.size(); i++) {
-     376           1 :                 E += (*c.secondaries[i]).current.getEnergy();
-     377           1 :                 id = (*c.secondaries[i]).current.getId();
-     378           1 :                 A += massNumber(id);
-     379           1 :                 Z += chargeNumber(id);
-     380             :         }
-     381           1 :         EXPECT_EQ(12, A);
-     382             :         // nucleon number conserved
-     383           1 :         EXPECT_EQ(6, Z);
-     384             :         // proton number conserved
-     385           1 :         EXPECT_DOUBLE_EQ(100 * EeV, E);
-     386             :         // energy conserved
-     387           2 : }
-     388             : 
-     389           1 : TEST(PhotoDisintegration, iron) {
-     390             :         // Test if a 200 EeV Fe-56 nucleus photo-disintegrates (at least once) over a distance of 1 Gpc.
-     391             :         // This test can stochastically fail.
-     392           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-     393           1 :         PhotoDisintegration pd(irb);
-     394           1 :         Candidate c;
-     395           1 :         int id = nucleusId(56, 26);
-     396           1 :         c.current.setId(id);
-     397           1 :         c.current.setEnergy(200 * EeV);
-     398           1 :         c.setCurrentStep(1000 * Mpc);
-     399           1 :         pd.process(&c);
-     400             : 
-     401             :         // expect energy loss
-     402           1 :         EXPECT_TRUE(c.current.getEnergy() < 200 * EeV);
-     403             :         
-     404             :         // expect secondaries produced
-     405           1 :         EXPECT_TRUE(c.secondaries.size() > 0);
-     406             : 
-     407           1 :         double E = c.current.getEnergy();
-     408           1 :         id = c.current.getId();
-     409           1 :         int A = massNumber(id);
-     410           1 :         int Z = chargeNumber(id);
-     411             : 
-     412          31 :         for (int i = 0; i < c.secondaries.size(); i++) {
-     413          30 :                 E += (*c.secondaries[i]).current.getEnergy();
-     414          30 :                 id = (*c.secondaries[i]).current.getId();
-     415          30 :                 A += massNumber(id);
-     416          30 :                 Z += chargeNumber(id);
-     417             :         }
-     418             : 
-     419             :         // nucleon number conserved
-     420           1 :         EXPECT_EQ(56, A);
-     421             :         
-     422             :         // proton number conserved (no decay active)
-     423           1 :         EXPECT_EQ(26, Z);
-     424             :         
-     425             :         // energy conserved
-     426           1 :         EXPECT_DOUBLE_EQ(200 * EeV, E);
-     427           2 : }
-     428             : 
-     429           1 : TEST(PhotoDisintegration, thisIsNotNucleonic) {
-     430             :         // Test that nothing happens to an electron.
-     431           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     432           1 :         PhotoDisintegration pd(cmb);
-     433           1 :         Candidate c;
-     434           1 :         c.setCurrentStep(1 * Mpc);
-     435           1 :         c.current.setId(11); // electron
-     436           1 :         c.current.setEnergy(10 * EeV);
-     437           1 :         pd.process(&c);
-     438           1 :         EXPECT_EQ(11, c.current.getId());
-     439           1 :         EXPECT_EQ(10 * EeV, c.current.getEnergy());
-     440           2 : }
-     441             : 
-     442           1 : TEST(PhotoDisintegration, limitNextStep) {
-     443             :         // Test if the interaction limits the next propagation step.
-     444           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     445           1 :         PhotoDisintegration pd(cmb);
-     446           1 :         Candidate c;
-     447           1 :         c.setNextStep(std::numeric_limits<double>::max());
-     448           1 :         c.current.setId(nucleusId(4, 2));
-     449           1 :         c.current.setEnergy(200 * EeV);
-     450           1 :         pd.process(&c);
-     451           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
-     452           2 : }
-     453             : 
-     454           1 : TEST(PhotoDisintegration, allIsotopes) {
-     455             :         // Test if all isotopes are handled.
-     456           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     457           1 :         PhotoDisintegration pd1(cmb);
-     458           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-     459           1 :         PhotoDisintegration pd2(irb);
-     460           1 :         Candidate c;
-     461           1 :         c.setCurrentStep(10 * Mpc);
-     462             : 
-     463          27 :         for (int Z = 1; Z <= 26; Z++) {
-     464         806 :                 for (int N = 1; N <= 30; N++) {
-     465             : 
-     466         780 :                         c.current.setId(nucleusId(Z + N, Z));
-     467         780 :                         c.current.setEnergy(80 * EeV);
-     468         780 :                         pd1.process(&c);
-     469             : 
-     470         780 :                         c.current.setId(nucleusId(Z + N, Z));
-     471         780 :                         c.current.setEnergy(80 * EeV);
-     472         780 :                         pd2.process(&c);
-     473             :                 }
-     474             :         }
-     475           3 : }
-     476             : 
-     477           1 : TEST(Photodisintegration, updateParticleParentProperties) { // Issue: #204
-     478           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     479           1 :         PhotoDisintegration pd(cmb);
-     480             : 
-     481           1 :         Candidate c(nucleusId(56,26), 500 * EeV, Vector3d(1 * Mpc, 0, 0));
-     482             : 
-     483           1 :         pd.performInteraction(&c, 1);
-     484             :         // the candidates parent is the original particle
-     485           1 :         EXPECT_EQ(c.created.getId(), nucleusId(56,26));
-     486             : 
-     487           1 :         pd.performInteraction(&c, 1);
-     488             :         // now it has to be changed
-     489           1 :         EXPECT_NE(c.created.getId(), nucleusId(56,26));
-     490           2 : }
-     491             : 
-     492           1 : TEST(PhotoDisintegration, interactionTag) {
-     493           2 :         PhotoDisintegration pd(new CMB());
-     494             : 
-     495             :         // test default interactionTag
-     496           2 :         EXPECT_TRUE(pd.getInteractionTag() == "PD");
-     497             : 
-     498             :         // test secondary tag
-     499           1 :         pd.setHavePhotons(true);
-     500           2 :         Candidate c(nucleusId(56,26), 500 * EeV);
-     501           1 :         c.setCurrentStep(1 * Gpc);
-     502           1 :         pd.process(&c);
-     503           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "PD");
-     504             : 
-     505             :         // test custom tag
-     506           1 :         pd.setInteractionTag("myTag");
-     507           2 :         EXPECT_TRUE(pd.getInteractionTag() == "myTag");
-     508           1 : }
-     509             : 
-     510             : // ElasticScattering ----------------------------------------------------------
-     511           1 : TEST(ElasticScattering, allBackgrounds) {
-     512             :         // Test if interaction data files are loaded.
-     513           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     514           1 :         ElasticScattering scattering(cmb);
-     515           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-     516           1 :         scattering.setPhotonField(irb);
-     517           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
-     518           2 :         scattering.setPhotonField(urb);
-     519           2 : }
-     520             : 
-     521           1 : TEST(ElasticScattering, secondaries) {
-     522             :         // Test the creation of cosmic ray photons.
-     523             :         // This test can stochastically fail.
-     524           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     525           1 :         ElasticScattering scattering(cmb);
-     526           1 :         Candidate c;
-     527           1 :         int id = nucleusId(12, 6);
-     528           1 :         c.current.setId(id);
-     529           1 :         c.current.setEnergy(200 * EeV);
-     530           1 :         c.setCurrentStep(400 * Mpc);
-     531           1 :         scattering.process(&c);
-     532             : 
-     533           1 :         EXPECT_GT(c.secondaries.size(), 0);
-     534             : 
-     535           8 :         for (int i = 0; i < c.secondaries.size(); i++) {
-     536           7 :                 int id = (*c.secondaries[i]).current.getId();
-     537           7 :                 EXPECT_EQ(id, 22);
-     538           7 :                 double energy = (*c.secondaries[i]).current.getEnergy();
-     539           7 :                 EXPECT_GT(energy, 0);
-     540           7 :                 EXPECT_LT(energy, 200 * EeV);
-     541             :         }
-     542           2 : }
-     543             : 
-     544             : // PhotoPionProduction --------------------------------------------------------
-     545           1 : TEST(PhotoPionProduction, allBackgrounds) {
-     546             :         // Test if all interaction data files can be loaded.
-     547           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     548           1 :         PhotoPionProduction ppp(cmb);
-     549           1 :         ref_ptr<PhotonField> irb = new IRB_Kneiske04();
-     550           1 :         ppp.setPhotonField(irb);
-     551           2 :         irb = new IRB_Stecker05();
-     552           1 :         ppp.setPhotonField(irb);
-     553           2 :         irb = new IRB_Franceschini08();
-     554           1 :         ppp.setPhotonField(irb);
-     555           2 :         irb = new IRB_Finke10();
-     556           1 :         ppp.setPhotonField(irb);
-     557           2 :         irb = new IRB_Dominguez11();
-     558           1 :         ppp.setPhotonField(irb);
-     559           2 :         irb = new IRB_Gilmore12();
-     560           1 :         ppp.setPhotonField(irb);
-     561           2 :         irb = new IRB_Stecker16_upper();
-     562           1 :         ppp.setPhotonField(irb);
-     563           2 :         irb = new IRB_Stecker16_lower();
-     564           1 :         ppp.setPhotonField(irb);
-     565           2 :     irb = new IRB_Finke22();
-     566           1 :         ppp.setPhotonField(irb);
-     567           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
-     568           1 :         ppp.setPhotonField(urb);
-     569           2 :         urb = new URB_Nitu21();
-     570           2 :         ppp.setPhotonField(urb);
-     571           2 : }
-     572             : 
-     573           1 : TEST(PhotoPionProduction, proton) {
-     574             :         // Test photopion interaction for 100 EeV proton.
-     575             :         // This test can stochastically fail.
-     576           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     577           1 :         PhotoPionProduction ppp(cmb);
-     578           1 :         Candidate c(nucleusId(1, 1), 100 * EeV);
-     579           1 :         c.setCurrentStep(1000 * Mpc);
-     580           1 :         ppp.process(&c);
-     581             : 
-     582             :         // expect energy loss
-     583           1 :         EXPECT_LT(c.current.getEnergy(), 100. * EeV);
-     584             : 
-     585             :         // expect nucleon number conservation
-     586           1 :         EXPECT_EQ(1, massNumber(c.current.getId()));
-     587             : 
-     588             :         // expect no (nucleonic) secondaries
-     589           1 :         EXPECT_EQ(0, c.secondaries.size());
-     590           2 : }
-     591             : 
-     592           1 : TEST(PhotoPionProduction, helium) {
-     593             :         // Test photo-pion interaction for 400 EeV He nucleus.
-     594             :         // This test can stochastically fail.
-     595           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     596           1 :         PhotoPionProduction ppp(cmb);
-     597           1 :         Candidate c;
-     598           1 :         c.current.setId(nucleusId(4, 2));
-     599           1 :         c.current.setEnergy(400. * EeV);
-     600           1 :         c.setCurrentStep(1000 * Mpc);
-     601           1 :         ppp.process(&c);
-     602           1 :         EXPECT_LT(c.current.getEnergy(), 400. * EeV);
-     603           1 :         int id = c.current.getId();
-     604           1 :         EXPECT_TRUE(massNumber(id) < 4);
-     605           1 :         EXPECT_TRUE(c.secondaries.size() > 0);
-     606           2 : }
-     607             : 
-     608           1 : TEST(PhotoPionProduction, thisIsNotNucleonic) {
-     609             :         // Test if nothing happens to an electron.
-     610           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     611           1 :         PhotoPionProduction ppp(cmb);
-     612           1 :         Candidate c;
-     613           1 :         c.current.setId(11); // electron
-     614           1 :         c.current.setEnergy(10 * EeV);
-     615           1 :         c.setCurrentStep(100 * Mpc);
-     616           1 :         ppp.process(&c);
-     617           1 :         EXPECT_EQ(11, c.current.getId());
-     618           1 :         EXPECT_EQ(10 * EeV, c.current.getEnergy());
-     619           2 : }
-     620             : 
-     621           1 : TEST(PhotoPionProduction, limitNextStep) {
-     622             :         // Test if the interaction limits the next propagation step.
-     623           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     624           1 :         PhotoPionProduction ppp(cmb);
-     625           1 :         Candidate c(nucleusId(1, 1), 200 * EeV);
-     626           1 :         c.setNextStep(std::numeric_limits<double>::max());
-     627           1 :         ppp.process(&c);
-     628           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
-     629           2 : }
-     630             : 
-     631           1 : TEST(PhotoPionProduction, secondaries) {
-     632             :         // Test photo-pion interaction for 100 EeV proton.
-     633             :         // This test can stochastically fail.
-     634           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     635           1 :         PhotoPionProduction ppp(cmb, true, true, true);
-     636           1 :         Candidate c(nucleusId(1, 1), 100 * EeV);
-     637           1 :         c.setCurrentStep(1000 * Mpc);
-     638           1 :         ppp.process(&c);
-     639             :         // there should be secondaries
-     640           1 :         EXPECT_GT(c.secondaries.size(), 1);
-     641           2 : }
-     642             : 
-     643           1 : TEST(PhotoPionProduction, sampling) {
-     644             :         // Specific test of photon sampling of photo-pion production
-     645             :         // by testing the calculated pEpsMax for CMB(), also indirectly
-     646             :         // testing epsMinInteraction and logSampling (default).
-     647           1 :         ref_ptr<PhotonField> cmb = new CMB(); //create CMB instance
-     648             :         double energy = 1.e10; //1e10 GeV
-     649             :         bool onProton = true; //proton
-     650             :         double z = 0; //no redshift
-     651           1 :         PhotoPionProduction ppp(cmb, true, true, true);
-     652           1 :         double correctionFactor = ppp.getCorrectionFactor(); //get current correctionFactor
-     653           1 :         double epsMin = std::max(cmb -> getMinimumPhotonEnergy(z) / eV, 0.00710614); // 0.00710614 = epsMinInteraction(onProton,energy)
-     654           1 :         double epsMax = cmb -> getMaximumPhotonEnergy(z) / eV;
-     655           1 :         double pEpsMax = ppp.probEpsMax(onProton, energy, z, epsMin, epsMax) / correctionFactor;
-     656           1 :         EXPECT_DOUBLE_EQ(pEpsMax,132673934934.922);
-     657           2 : }
-     658             : 
-     659           1 : TEST(PhotoPionProduction, interactionTag) {
-     660           2 :         PhotoPionProduction ppp(new CMB());
-     661             : 
-     662             :         // test default interactionTag
-     663           2 :         EXPECT_TRUE(ppp.getInteractionTag() == "PPP");
-     664             : 
-     665             :         // test secondary tag
-     666           1 :         ppp.setHavePhotons(true);
-     667           2 :         Candidate c(nucleusId(1,1), 100 * EeV);
-     668          11 :         for(int i = 0; i <10; i++) 
-     669          10 :                 ppp.performInteraction(&c, true);
-     670           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "PPP");
-     671             : 
-     672             :         // test custom interactionTag
-     673           1 :         ppp.setInteractionTag("myTag");
-     674           2 :         EXPECT_TRUE(ppp.getInteractionTag() == "myTag");
-     675           1 : }
-     676             : 
-     677             : // Redshift -------------------------------------------------------------------
-     678           2 : TEST(Redshift, simpleTest) {
-     679             :         // Test if redshift is decreased and adiabatic energy loss is applied.
-     680             :         Redshift redshift;
-     681             : 
-     682           1 :         Candidate c;
-     683           1 :         c.setRedshift(0.024);
-     684           1 :         c.current.setEnergy(100 * EeV);
-     685           1 :         c.setCurrentStep(1 * Mpc);
-     686             : 
-     687           1 :         redshift.process(&c);
-     688           1 :         EXPECT_GT(0.024, c.getRedshift()); // expect redshift decrease
-     689           1 :         EXPECT_GT(100, c.current.getEnergy() / EeV); // expect energy loss
-     690           2 : }
-     691             : 
-     692           2 : TEST(Redshift, limitRedshiftDecrease) {
-     693             :         // Test if the redshift decrease is limited to z_updated >= 0.
-     694             :         Redshift redshift;
-     695             : 
-     696           1 :         Candidate c;
-     697           1 :         c.setRedshift(0.024); // roughly corresponds to 100 Mpc
-     698           1 :         c.setCurrentStep(150 * Mpc);
-     699             : 
-     700           1 :         redshift.process(&c);
-     701           1 :         EXPECT_DOUBLE_EQ(0, c.getRedshift());
-     702           2 : }
-     703             : 
-     704             : // EMPairProduction -----------------------------------------------------------
-     705           1 : TEST(EMPairProduction, allBackgrounds) {
-     706             :         // Test if interaction data files are loaded.
-     707           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     708           1 :         EMPairProduction em(cmb);
-     709           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
-     710           1 :         em.setPhotonField(ebl);
-     711           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
-     712           1 :         em.setPhotonField(urb);
-     713           2 :         ebl = new IRB_Stecker05();
-     714           1 :         em.setPhotonField(ebl);
-     715           2 :         ebl = new IRB_Franceschini08();
-     716           1 :         em.setPhotonField(ebl);
-     717           2 :         ebl = new IRB_Finke10();
-     718           1 :         em.setPhotonField(ebl);
-     719           2 :         ebl = new IRB_Dominguez11();
-     720           1 :         em.setPhotonField(ebl);
-     721           2 :         ebl = new IRB_Gilmore12();
-     722           1 :         em.setPhotonField(ebl);
-     723           2 :         ebl = new IRB_Stecker16_upper();
-     724           1 :         em.setPhotonField(ebl);
-     725           2 :         ebl = new IRB_Stecker16_lower();
-     726           1 :         em.setPhotonField(ebl);
-     727           2 :         ebl = new IRB_Finke22();
-     728           1 :         em.setPhotonField(ebl);
-     729           2 :         urb = new URB_Fixsen11();
-     730           1 :         em.setPhotonField(urb);
-     731           2 :         urb = new URB_Nitu21();
-     732           2 :         em.setPhotonField(urb);
-     733           2 : }
-     734             : 
-     735           1 : TEST(EMPairProduction, limitNextStep) {
-     736             :         // Test if the interaction limits the next propagation step.
-     737           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     738           1 :         EMPairProduction m(cmb);
-     739           1 :         Candidate c(22, 1E17 * eV);
-     740           1 :         c.setNextStep(std::numeric_limits<double>::max());
-     741           1 :         m.process(&c);
-     742           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
-     743           2 : }
-     744             : 
-     745           1 : TEST(EMPairProduction, secondaries) {
-     746             :         // Test if secondaries are correctly produced.
-     747           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     748           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
-     749           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
-     750           1 :         EMPairProduction m(cmb);
-     751           1 :         m.setHaveElectrons(true);
-     752           1 :         m.setThinning(0.);
-     753             : 
-     754             :         std::vector<ref_ptr<PhotonField>> fields;
-     755           1 :         fields.push_back(cmb);
-     756           1 :         fields.push_back(irb);
-     757           1 :         fields.push_back(urb);
-     758             : 
-     759             :         // loop over photon backgrounds
-     760           4 :         for (int f = 0; f < fields.size(); f++) {
-     761           3 :                 m.setPhotonField(fields[f]);
-     762         423 :                 for (int i = 0; i < 140; i++) { // loop over energies Ep = (1e10 - 1e23) eV
-     763         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
-     764         420 :                         Candidate c(22, Ep);
-     765         420 :                         c.setCurrentStep(1e10 * Mpc);
-     766             : 
-     767         420 :                         m.process(&c);
-     768             : 
-     769             :                         // pass if no interaction has ocurred (no tabulated rates)
-     770         420 :                         if (c.isActive())
-     771             :                                 continue;
-     772             :                         
-     773             :                         // expect 2 secondaries
-     774         311 :                         EXPECT_EQ(c.secondaries.size(), 2);
-     775             : 
-     776             :                         // expect electron / positron with energies 0 < E < Ephoton
-     777             :                         double Etot = 0;
-     778         933 :                         for (int j = 0; j < c.secondaries.size(); j++) {
-     779         622 :                                 Candidate s = *c.secondaries[j];
-     780         622 :                                 EXPECT_EQ(abs(s.current.getId()), 11);
-     781         622 :                                 EXPECT_GT(s.current.getEnergy(), 0);
-     782         622 :                                 EXPECT_LT(s.current.getEnergy(), Ep);
-     783         622 :                                 Etot += s.current.getEnergy();
-     784         622 :                         }
-     785             : 
-     786             :                         // test energy conservation
-     787         311 :                         EXPECT_DOUBLE_EQ(Ep, Etot);
-     788         420 :                 }
-     789             :         }
-     790           2 : }
-     791             : 
-     792           1 : TEST(EMPairProduction, interactionTag) {
-     793           2 :         EMPairProduction m(new CMB());
-     794             : 
-     795             :         // test default interactionTag
-     796           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMPP");
-     797             : 
-     798             :         // test secondary tag
-     799           1 :         m.setHaveElectrons(true);
-     800           2 :         Candidate c(22, 1 * EeV);
-     801           1 :         m.performInteraction(&c);
-     802           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMPP");
-     803             : 
-     804             :         // test custom tag
-     805           1 :         m.setInteractionTag("myTag");
-     806           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
-     807           1 : }
-     808             : 
-     809             : // EMDoublePairProduction -----------------------------------------------------
-     810           1 : TEST(EMDoublePairProduction, allBackgrounds) {
-     811             :         // Test if interaction data files are loaded.
-     812           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     813           1 :         EMDoublePairProduction em(cmb);
-     814           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
-     815           1 :         em.setPhotonField(ebl);
-     816           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
-     817           1 :         em.setPhotonField(urb);
-     818           2 :         ebl = new IRB_Stecker05();
-     819           1 :         em.setPhotonField(ebl);
-     820           2 :         ebl = new IRB_Franceschini08();
-     821           1 :         em.setPhotonField(ebl);
-     822           2 :         ebl = new IRB_Finke10();
-     823           1 :         em.setPhotonField(ebl);
-     824           2 :         ebl = new IRB_Dominguez11();
-     825           1 :         em.setPhotonField(ebl);
-     826           2 :         ebl = new IRB_Gilmore12();
-     827           1 :         em.setPhotonField(ebl);
-     828           2 :         ebl = new IRB_Stecker16_upper();
-     829           1 :         em.setPhotonField(ebl);
-     830           2 :         ebl = new IRB_Stecker16_lower();
-     831           1 :         em.setPhotonField(ebl);
-     832           2 :         ebl = new IRB_Finke22();
-     833           1 :         em.setPhotonField(ebl);
-     834           2 :         urb = new URB_Fixsen11();
-     835           1 :         em.setPhotonField(urb);
-     836           2 :         urb = new URB_Nitu21();
-     837           2 :         em.setPhotonField(urb);
-     838           2 : }
-     839             : 
-     840           1 : TEST(EMDoublePairProduction, limitNextStep) {
-     841             :         // Test if the interaction limits the next propagation step.
-     842           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     843           1 :         EMDoublePairProduction m(cmb);
-     844           1 :         Candidate c(22, 1E17 * eV);
-     845           1 :         c.setNextStep(std::numeric_limits<double>::max());
-     846           1 :         m.process(&c);
-     847           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
-     848           2 : }
-     849             : 
-     850           1 : TEST(EMDoublePairProduction, secondaries) {
-     851             :         // Test if secondaries are correctly produced.
-     852           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     853           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
-     854           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
-     855           1 :         EMPairProduction m(cmb);
-     856           1 :         m.setHaveElectrons(true);
-     857           1 :         m.setThinning(0.);
-     858             : 
-     859             :         std::vector<ref_ptr<PhotonField>> fields;
-     860           1 :         fields.push_back(cmb);
-     861           1 :         fields.push_back(irb);
-     862           1 :         fields.push_back(urb);
-     863             : 
-     864             :         // loop over photon backgrounds
-     865           4 :         for (int f = 0; f < fields.size(); f++) {
-     866           3 :                 m.setPhotonField(fields[f]);
-     867             :                 
-     868             :                 // loop over energies Ep = (1e9 - 1e23) eV
-     869         423 :                 for (int i = 0; i < 140; i++) {
-     870         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
-     871         420 :                         Candidate c(22, Ep);
-     872         420 :                         c.setCurrentStep(1e4 * Mpc); // use lower value so that the test can run faster
-     873         420 :                         m.process(&c);
-     874             : 
-     875             :                         // pass if no interaction has occured (no tabulated rates)
-     876         420 :                         if (c.isActive())
-     877             :                                 continue;
-     878             :                         
-     879             :                         // expect 2 secondaries (only one pair is considered)
-     880         251 :                         EXPECT_EQ(c.secondaries.size(), 2);
-     881             : 
-     882             :                         // expect electron / positron with energies 0 < E < Ephoton
-     883             :                         double Etot = 0;
-     884         753 :                         for (int j = 0; j < c.secondaries.size(); j++) {
-     885         502 :                                 Candidate s = *c.secondaries[j];
-     886         502 :                                 EXPECT_EQ(abs(s.current.getId()), 11);
-     887         502 :                                 EXPECT_GT(s.current.getEnergy(), 0);
-     888         502 :                                 EXPECT_LT(s.current.getEnergy(), Ep);
-     889         502 :                                 Etot += s.current.getEnergy();
-     890         502 :                         }
-     891             : 
-     892             :                         // test energy conservation
-     893         251 :                         EXPECT_NEAR(Ep, Etot, 1E-9);
-     894         420 :                 }
-     895             :         }
-     896           2 : }
-     897             : 
-     898           1 : TEST(EMDoublePairProduction, interactionTag) {
-     899           2 :         EMDoublePairProduction m(new CMB());
-     900             : 
-     901             :         // test default interactionTag
-     902           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMDP");
-     903             : 
-     904             :         // test secondary tag
-     905           1 :         m.setHaveElectrons(true);
-     906           2 :         Candidate c(22, 1 * EeV);
-     907           1 :         m.performInteraction(&c);
-     908           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMDP");
-     909             : 
-     910             :         // test custom tag
-     911           1 :         m.setInteractionTag("myTag");
-     912           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
-     913           1 : }
-     914             : 
-     915             : // EMTripletPairProduction ----------------------------------------------------
-     916           1 : TEST(EMTripletPairProduction, allBackgrounds) {
-     917             :         // Test if interaction data files are loaded.
-     918           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     919           1 :         EMTripletPairProduction em(cmb);
-     920           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
-     921           1 :         em.setPhotonField(ebl);
-     922           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
-     923           1 :         em.setPhotonField(urb);
-     924           2 :         ebl = new IRB_Stecker05();
-     925           1 :         em.setPhotonField(ebl);
-     926           2 :         ebl = new IRB_Franceschini08();
-     927           1 :         em.setPhotonField(ebl);
-     928           2 :         ebl = new IRB_Finke10();
-     929           1 :         em.setPhotonField(ebl);
-     930           2 :         ebl = new IRB_Dominguez11();
-     931           1 :         em.setPhotonField(ebl);
-     932           2 :         ebl = new IRB_Gilmore12();
-     933           1 :         em.setPhotonField(ebl);
-     934           2 :         ebl = new IRB_Stecker16_upper();
-     935           1 :         em.setPhotonField(ebl);
-     936           2 :         ebl = new IRB_Stecker16_lower();
-     937           1 :         em.setPhotonField(ebl);
-     938           2 :         ebl = new IRB_Finke22();
-     939           1 :         em.setPhotonField(ebl);
-     940           2 :         urb = new URB_Fixsen11();
-     941           1 :         em.setPhotonField(urb);
-     942           2 :         urb = new URB_Nitu21();
-     943           2 :         em.setPhotonField(urb);
-     944           2 : }
-     945             : 
-     946           1 : TEST(EMTripletPairProduction, limitNextStep) {
-     947             :         // Test if the interaction limits the next propagation step.
-     948           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     949           1 :         EMTripletPairProduction m(cmb);
-     950           1 :         Candidate c(11, 1E17 * eV);
-     951           1 :         c.setNextStep(std::numeric_limits<double>::max());
-     952           1 :         m.process(&c);
-     953           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
-     954           2 : }
-     955             : 
-     956           1 : TEST(EMTripletPairProduction, secondaries) {
-     957             :         // Test if secondaries are correctly produced.
-     958           1 :         ref_ptr<PhotonField> cmb = new CMB();
-     959           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
-     960           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
-     961           1 :         EMPairProduction m(cmb);
-     962           1 :         m.setHaveElectrons(true);
-     963           1 :         m.setThinning(0.);
-     964             : 
-     965             :         std::vector<ref_ptr<PhotonField>> fields;
-     966           1 :         fields.push_back(cmb);
-     967           1 :         fields.push_back(irb);
-     968           1 :         fields.push_back(urb);
-     969             : 
-     970             :         // loop over photon backgrounds
-     971           4 :         for (int f = 0; f < fields.size(); f++) {
-     972           3 :                 m.setPhotonField(fields[f]);
-     973             :                 
-     974             :                 // loop over energies Ep = (1e9 - 1e23) eV
-     975         423 :                 for (int i = 0; i < 140; i++) {
-     976             : 
-     977         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
-     978         420 :                         Candidate c(11, Ep);
-     979         420 :                         c.setCurrentStep(1e4 * Mpc); // use lower value so that the test can run faster
-     980         420 :                         m.process(&c);
-     981             : 
-     982             :                         // pass if no interaction has occured (no tabulated rates)
-     983         420 :                         if (c.current.getEnergy() == Ep)
-     984             :                                 continue;
-     985             : 
-     986             :                         // expect positive energy of primary electron
-     987           0 :                         EXPECT_GT(c.current.getEnergy(), 0);
-     988           0 :                         double Etot = c.current.getEnergy();
-     989             : 
-     990             :                         // expect electron / positron with energies 0 < E < Ephoton
-     991           0 :                         for (int j = 0; j < c.secondaries.size(); j++) {
-     992           0 :                                 Candidate s = *c.secondaries[j];
-     993           0 :                                 EXPECT_EQ(abs(s.current.getId()), 11);
-     994           0 :                                 EXPECT_GT(s.current.getEnergy(), 0);
-     995           0 :                                 EXPECT_LT(s.current.getEnergy(), Ep);
-     996           0 :                                 Etot += s.current.getEnergy();
-     997           0 :                         }
-     998             : 
-     999             :                         // test energy conservation
-    1000           0 :                         EXPECT_NEAR(Ep, Etot, 1e-9);
-    1001         420 :                 }
-    1002             :         }
-    1003           2 : }
-    1004             : 
-    1005           1 : TEST(EMTripletPairProduction, interactionTag) {
-    1006           2 :         EMTripletPairProduction m(new CMB());
-    1007             : 
-    1008             :         // test default interactionTag
-    1009           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMTP");
-    1010             : 
-    1011             :         // test secondary tag
-    1012           1 :         m.setHaveElectrons(true);
-    1013           2 :         Candidate c(11, 1 * EeV);
-    1014           1 :         m.performInteraction(&c);
-    1015           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMTP");
-    1016             : 
-    1017             :         // test custom tag
-    1018           1 :         m.setInteractionTag("myTag");
-    1019           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
-    1020           1 : }
-    1021             : 
-    1022             : // EMInverseComptonScattering -------------------------------------------------
-    1023           1 : TEST(EMInverseComptonScattering, allBackgrounds) {
-    1024             :         // Test if interaction data files are loaded.
-    1025           1 :         ref_ptr<PhotonField> cmb = new CMB();
-    1026           1 :         EMInverseComptonScattering em(cmb);
-    1027           1 :         ref_ptr<PhotonField> ebl = new IRB_Kneiske04();
-    1028           1 :         em.setPhotonField(ebl);
-    1029           1 :         ref_ptr<PhotonField> urb = new URB_Protheroe96();
-    1030           1 :         em.setPhotonField(urb);
-    1031           2 :         ebl = new IRB_Stecker05();
-    1032           1 :         em.setPhotonField(ebl);
-    1033           2 :         ebl = new IRB_Franceschini08();
-    1034           1 :         em.setPhotonField(ebl);
-    1035           2 :         ebl = new IRB_Finke10();
-    1036           1 :         em.setPhotonField(ebl);
-    1037           2 :         ebl = new IRB_Dominguez11();
-    1038           1 :         em.setPhotonField(ebl);
-    1039           2 :         ebl = new IRB_Gilmore12();
-    1040           1 :         em.setPhotonField(ebl);
-    1041           2 :         ebl = new IRB_Stecker16_upper();
-    1042           1 :         em.setPhotonField(ebl);
-    1043           2 :         ebl = new IRB_Stecker16_lower();
-    1044           1 :         em.setPhotonField(ebl);
-    1045           2 :         ebl = new IRB_Finke22();
-    1046           1 :         em.setPhotonField(ebl);
-    1047           2 :         urb = new URB_Fixsen11();
-    1048           1 :         em.setPhotonField(urb);
-    1049           2 :         urb = new URB_Nitu21();
-    1050           2 :         em.setPhotonField(urb);
-    1051           2 : }
-    1052             : 
-    1053           1 : TEST(EMInverseComptonScattering, limitNextStep) {
-    1054             :         // Test if the interaction limits the next propagation step.
-    1055           1 :         ref_ptr<PhotonField> cmb = new CMB();
-    1056           1 :         EMInverseComptonScattering m(cmb);
-    1057           1 :         Candidate c(11, 1E17 * eV);
-    1058           1 :         c.setNextStep(std::numeric_limits<double>::max());
-    1059           1 :         m.process(&c);
-    1060           1 :         EXPECT_LT(c.getNextStep(), std::numeric_limits<double>::max());
-    1061           2 : }
-    1062             : 
-    1063           1 : TEST(EMInverseComptonScattering, secondaries) {
-    1064             :         // Test if secondaries are correctly produced.
-    1065           1 :         ref_ptr<PhotonField> cmb = new CMB();
-    1066           1 :         ref_ptr<PhotonField> irb = new IRB_Saldana21();
-    1067           1 :         ref_ptr<PhotonField> urb = new URB_Nitu21();
-    1068           1 :         EMPairProduction m(cmb);
-    1069           1 :         m.setHaveElectrons(true);
-    1070           1 :         m.setThinning(0.);
-    1071             : 
-    1072             :         std::vector<ref_ptr<PhotonField>> fields;
-    1073           1 :         fields.push_back(cmb);
-    1074           1 :         fields.push_back(irb);
-    1075           1 :         fields.push_back(urb);
-    1076             : 
-    1077             :         // loop over photon backgrounds
-    1078           4 :         for (int f = 0; f < fields.size(); f++) {
-    1079           3 :                 m.setPhotonField(fields[f]);
-    1080             :                 
-    1081             :                 // loop over energies Ep = (1e9 - 1e23) eV
-    1082         423 :                 for (int i = 0; i < 140; i++) {
-    1083         420 :                         double Ep = pow(10, 9.05 + 0.1 * i) * eV;
-    1084         420 :                         Candidate c(11, Ep);
-    1085         420 :                         c.setCurrentStep(1e3 * Mpc); // use lower value so that the test can run faster
-    1086         420 :                         m.process(&c);
-    1087             : 
-    1088             :                         // pass if no interaction has occured (no tabulated rates)
-    1089         420 :                         if (c.current.getEnergy() == Ep)
-    1090             :                                 continue;
-    1091             :                         
-    1092             :                         // expect positive energy of primary electron
-    1093           0 :                         EXPECT_GT(c.current.getEnergy(), 0);
-    1094             : 
-    1095             :                         // expect photon with energy 0 < E < Ephoton
-    1096           0 :                         Candidate s = *c.secondaries[0];
-    1097           0 :                         EXPECT_EQ(abs(s.current.getId()), 22);
-    1098           0 :                         EXPECT_TRUE(s.current.getEnergy() >= 0.);
-    1099           0 :                         EXPECT_TRUE(s.current.getEnergy() < Ep);
-    1100             : 
-    1101             : 
-    1102           0 :                         double Etot = c.current.getEnergy();
-    1103           0 :                         for (int j = 0; j < c.secondaries.size(); j++) {
-    1104           0 :                                 s = *c.secondaries[j];
-    1105           0 :                                 Etot += s.current.getEnergy();
-    1106             :                         }
-    1107           0 :                         EXPECT_NEAR(Ep, Etot, 1e-9); 
-    1108         420 :                 }
-    1109             :         }
-    1110           2 : }
-    1111             : 
-    1112           1 : TEST(EMInverseComptonScattering, interactionTag) {
-    1113           2 :         EMInverseComptonScattering m(new CMB());
-    1114             : 
-    1115             :         // test default interactionTag
-    1116           2 :         EXPECT_TRUE(m.getInteractionTag() == "EMIC");
-    1117             : 
-    1118             :         // test secondary tag
-    1119           1 :         m.setHavePhotons(true);
-    1120           2 :         Candidate c(11, 1 * PeV);
-    1121           1 :         m.performInteraction(&c);
-    1122           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "EMIC");
-    1123             : 
-    1124             :         // test custom tag
-    1125           1 :         m.setInteractionTag("myTag");
-    1126           2 :         EXPECT_TRUE(m.getInteractionTag() == "myTag");
-    1127           1 : }
-    1128             : 
-    1129             : // SynchrotronRadiation -------------------------------------------------
-    1130           1 : TEST(SynchrotronRadiation, interactionTag) {
-    1131           1 :         SynchrotronRadiation s(1 * muG, true);
-    1132             : 
-    1133             :         // test default interactionTag
-    1134           2 :         EXPECT_TRUE(s.getInteractionTag() == "SYN");
-    1135             : 
-    1136             :         // test secondary tag
-    1137           2 :         Candidate c(11, 10 * PeV);
-    1138           1 :         c.setCurrentStep(1 * pc);
-    1139           1 :         s.process(&c);
-    1140           2 :         EXPECT_TRUE(c.secondaries[0] -> getTagOrigin() == "SYN");
-    1141             : 
-    1142             :         // test custom tag
-    1143           1 :         s.setInteractionTag("myTag");
-    1144           2 :         EXPECT_TRUE(s.getInteractionTag() == "myTag");
-    1145           1 : }
-    1146             : 
-    1147             : 
-    1148           0 : int main(int argc, char **argv) {
-    1149           0 :         ::testing::InitGoogleTest(&argc, argv);
-    1150           0 :         return RUN_ALL_TESTS();
-    1151             : }
-    1152             : 
-    1153             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html b/doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html deleted file mode 100644 index aaf4ebc36..000000000 --- a/doc/coverageReport/test/testMagneticField.cpp.func-sort-c.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testMagneticField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:138138100.0 %
Date:2024-04-08 14:58:22Functions:1616100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN36testCMZMagneticField_SimpleTest_Test8TestBodyEv1
_ZN37testMagneticFieldList_SimpleTest_Test8TestBodyEv1
_ZN37testToroidalHaloField_SimpleTest_Test8TestBodyEv1
_ZN38testCMZMagneticField_TestNTFField_Test8TestBodyEv1
_ZN39testMagneticDipoleField_SimpleTest_Test8TestBodyEv1
_ZN40testUniformMagneticField_SimpleTest_Test8TestBodyEv1
_ZN41testCMZMagneticField_TestICComponent_Test8TestBodyEv1
_ZN41testPeriodicMagneticField_Exceptions_Test8TestBodyEv1
_ZN42testLogarithmicSpiralField_SimpleTest_Test8TestBodyEv1
_ZN42testMagneticFieldEvolution_SimpleTest_Test8TestBodyEv1
_ZN43testCMZMagneticField_TestRaidoArcField_Test8TestBodyEv1
_ZN44testRenormalizeMagneticField_simpleTest_Test8TestBodyEv1
_ZN47testCMZMagneticField_TestAzimutalComponent_Test8TestBodyEv1
_ZN52testPolarizedSingleModeMagneticField_SimpleTest_Test8TestBodyEv1
main1
_ZNK17EchoMagneticField8getFieldERKN7crpropa7Vector3IdEE3
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testMagneticField.cpp.func.html b/doc/coverageReport/test/testMagneticField.cpp.func.html deleted file mode 100644 index 4842756d7..000000000 --- a/doc/coverageReport/test/testMagneticField.cpp.func.html +++ /dev/null @@ -1,136 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testMagneticField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:138138100.0 %
Date:2024-04-08 14:58:22Functions:1616100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN36testCMZMagneticField_SimpleTest_Test8TestBodyEv1
_ZN37testMagneticFieldList_SimpleTest_Test8TestBodyEv1
_ZN37testToroidalHaloField_SimpleTest_Test8TestBodyEv1
_ZN38testCMZMagneticField_TestNTFField_Test8TestBodyEv1
_ZN39testMagneticDipoleField_SimpleTest_Test8TestBodyEv1
_ZN40testUniformMagneticField_SimpleTest_Test8TestBodyEv1
_ZN41testCMZMagneticField_TestICComponent_Test8TestBodyEv1
_ZN41testPeriodicMagneticField_Exceptions_Test8TestBodyEv1
_ZN42testLogarithmicSpiralField_SimpleTest_Test8TestBodyEv1
_ZN42testMagneticFieldEvolution_SimpleTest_Test8TestBodyEv1
_ZN43testCMZMagneticField_TestRaidoArcField_Test8TestBodyEv1
_ZN44testRenormalizeMagneticField_simpleTest_Test8TestBodyEv1
_ZN47testCMZMagneticField_TestAzimutalComponent_Test8TestBodyEv1
_ZN52testPolarizedSingleModeMagneticField_SimpleTest_Test8TestBodyEv1
_ZNK17EchoMagneticField8getFieldERKN7crpropa7Vector3IdEE3
main1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testMagneticField.cpp.gcov.html b/doc/coverageReport/test/testMagneticField.cpp.gcov.html deleted file mode 100644 index 1da471524..000000000 --- a/doc/coverageReport/test/testMagneticField.cpp.gcov.html +++ /dev/null @@ -1,292 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testMagneticField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testMagneticField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:138138100.0 %
Date:2024-04-08 14:58:22Functions:1616100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include <stdexcept>
-       2             : 
-       3             : #include "crpropa/magneticField/MagneticFieldGrid.h"
-       4             : #include "crpropa/magneticField/CMZField.h"
-       5             : #include "crpropa/magneticField/PolarizedSingleModeMagneticField.h"
-       6             : #include "crpropa/magneticField/GalacticMagneticField.h"
-       7             : #include "crpropa/Grid.h"
-       8             : #include "crpropa/Units.h"
-       9             : #include "crpropa/Common.h"
-      10             : 
-      11             : #include "gtest/gtest.h"
-      12             : 
-      13             : using namespace crpropa;
-      14             : 
-      15           1 : TEST(testUniformMagneticField, SimpleTest) {
-      16             :         UniformMagneticField B(Vector3d(-1, 5, 3));
-      17             :         Vector3d b = B.getField(Vector3d(1, 0, 0));
-      18           1 :         EXPECT_DOUBLE_EQ(b.getX(), -1);
-      19           1 :         EXPECT_DOUBLE_EQ(b.getY(), 5);
-      20           1 :         EXPECT_DOUBLE_EQ(b.getZ(), 3);
-      21           1 : }
-      22             : 
-      23           2 : TEST(testMagneticDipoleField, SimpleTest) {
-      24             :         // Test magnetic dipole
-      25             :         // mu0 / (4*M_PI) * m / r^3 (2*cos(theta)*e_r + sin(theta)*e_theta)
-      26             :         MagneticDipoleField B(Vector3d(0,0,0), Vector3d(0,0,1), 1);
-      27           1 :         Vector3d b1 = B.getField(Vector3d(0, 0, 1)); // theta = 0
-      28           1 :         Vector3d b2 = B.getField(Vector3d(1, 0, 0)); // theta = 0
-      29           1 :         EXPECT_NEAR(b1.getX(), 0, 1E-8);
-      30           1 :         EXPECT_NEAR(b1.getY(), 0, 1E-8);
-      31           1 :         EXPECT_NEAR(b1.getZ(), mu0 / (4*M_PI) * 2, 1E-8);
-      32           1 :         EXPECT_NEAR(b2.getX(), 0, 1E-8);
-      33           1 :         EXPECT_NEAR(b2.getY(), 0, 1E-8);
-      34           1 :         EXPECT_NEAR(b2.getZ(), -1 * mu0 / (4*M_PI), 1E-8);
-      35           1 : }
-      36             : 
-      37             : #ifdef CRPROPA_HAVE_MUPARSER
-      38           1 : TEST(testRenormalizeMagneticField, simpleTest) {
-      39           1 :         ref_ptr<UniformMagneticField> field = new UniformMagneticField(Vector3d(2*nG, 0, 0));
-      40           2 :         RenormalizeMagneticField modField(field, "B^2-1*nG");
-      41           1 :         Vector3d b = modField.getField(Vector3d(5, 5, 5));
-      42           1 :         EXPECT_NEAR(b.getR(), 3*nG, 0.001);
-      43           2 : }
-      44             : #endif
-      45             : 
-      46           2 : TEST(testMagneticFieldList, SimpleTest) {
-      47             :         // Test a list of three magnetic fields
-      48             :         MagneticFieldList B;
-      49           1 :         B.addField(new UniformMagneticField(Vector3d(1, 0, 0)));
-      50           1 :         B.addField(new UniformMagneticField(Vector3d(0, 2, 0)));
-      51           2 :         B.addField(new UniformMagneticField(Vector3d(0, 0, 3)));
-      52           1 :         Vector3d b = B.getField(Vector3d(0.));
-      53           1 :         EXPECT_DOUBLE_EQ(b.x, 1);
-      54           1 :         EXPECT_DOUBLE_EQ(b.y, 2);
-      55           1 :         EXPECT_DOUBLE_EQ(b.z, 3);
-      56           1 : }
-      57             : 
-      58           1 : TEST(testMagneticFieldEvolution, SimpleTest) {
-      59             :         // Test if this decorator scales the underlying field as (1+z)^m
-      60           1 :         ref_ptr<UniformMagneticField> B = new UniformMagneticField(Vector3d(1,0,0));
-      61             :         double z = 1.2;
-      62             :         double m = 3;
-      63           2 :         MagneticFieldEvolution Bz(B, m);
-      64             : 
-      65             :         // scaled field
-      66           1 :         Vector3d b = Bz.getField(Vector3d(0,0,0), z);
-      67           1 :         EXPECT_DOUBLE_EQ(b.x, pow(1+z, m));
-      68             : 
-      69             :         // unscaled field
-      70           1 :         b = Bz.getField(Vector3d(0,0,0));
-      71           1 :         EXPECT_DOUBLE_EQ(b.x, 1);
-      72           1 : }
-      73             : 
-      74           1 : class EchoMagneticField: public MagneticField {
-      75             : public:
-      76           3 :         Vector3d getField(const Vector3d &position) const {
-      77           3 :                 return position;
-      78             :         }
-      79             : };
-      80             : 
-      81           1 : TEST(testPeriodicMagneticField, Exceptions) {
-      82           1 :         ref_ptr<EchoMagneticField> f = new EchoMagneticField();
-      83             :         ref_ptr<PeriodicMagneticField> p = new PeriodicMagneticField(f,
-      84           1 :                         Vector3d(10000, 10000, 10000), Vector3d(1000, 1000, 1000), true);
-      85             : 
-      86             :         // box 0, 0, 0
-      87           1 :         Vector3d v = p->getField(Vector3d(1000, 2000, 3000));
-      88           1 :         EXPECT_DOUBLE_EQ(0, v.x);
-      89           1 :         EXPECT_DOUBLE_EQ(1000, v.y);
-      90           1 :         EXPECT_DOUBLE_EQ(2000, v.z);
-      91             : 
-      92             :         // box 1, 2, 3
-      93           1 :         v = p->getField(Vector3d(12000, 23000, 34000));
-      94           1 :         EXPECT_DOUBLE_EQ(9000, v.x);
-      95           1 :         EXPECT_DOUBLE_EQ(2000, v.y);
-      96           1 :         EXPECT_DOUBLE_EQ(7000, v.z);
-      97             : 
-      98             :         // box -1, -2, -3
-      99           1 :         v = p->getField(Vector3d(0, -10000, -20000));
-     100           1 :         EXPECT_DOUBLE_EQ(1000, v.x);
-     101           1 :         EXPECT_DOUBLE_EQ(9000, v.y);
-     102           1 :         EXPECT_DOUBLE_EQ(1000, v.z);
-     103             : 
-     104           1 : }
-     105             : 
-     106           1 : TEST(testCMZMagneticField, SimpleTest) {
-     107           1 :         ref_ptr<CMZField> field = new CMZField();
-     108             :         
-     109             :         // check use-Values
-     110           1 :         EXPECT_FALSE(field->getUseMCField());
-     111           1 :         EXPECT_TRUE(field->getUseICField());
-     112           1 :         EXPECT_FALSE(field->getUseNTFField());
-     113           1 :         EXPECT_FALSE(field->getUseRadioArc());
-     114             : 
-     115             :         // check set function
-     116           1 :         field->setUseMCField(true);
-     117           1 :         EXPECT_TRUE(field->getUseMCField());
-     118           1 :         field->setUseICField(false);
-     119           1 :         EXPECT_FALSE(field->getUseICField());
-     120           1 :         field->setUseNTFField(true);
-     121           1 :         EXPECT_TRUE(field->getUseNTFField());
-     122           1 :         field->setUseRadioArc(true);
-     123           1 :         EXPECT_TRUE(field->getUseRadioArc());
-     124           1 : }
-     125             : 
-     126           1 : TEST(testCMZMagneticField, TestICComponent) {
-     127           1 :         ref_ptr<CMZField> field = new CMZField();
-     128             :         Vector3d pos(10*pc,15*pc,-5*pc);        
-     129             : 
-     130             :         // check IC field at given position
-     131           1 :         Vector3d bVec = field->getField(pos);
-     132           1 :         EXPECT_NEAR(bVec.getR(), 10.501*muG, 1E-3*muG);
-     133           1 :         EXPECT_NEAR(bVec.x, 0.225*muG, 1E-3*muG);
-     134           1 :         EXPECT_NEAR(bVec.y, 0.524*muG, 1E-3*muG);
-     135           1 :         EXPECT_NEAR(bVec.z, 10.486*muG, 1E-3*muG);
-     136           1 : }
-     137           1 : TEST(testCMZMagneticField, TestNTFField){
-     138           1 :         ref_ptr<CMZField> field = new CMZField();
-     139             :         Vector3d pos(10*pc,15*pc,-5*pc);        
-     140             :         
-     141             :         // check NFTField at given position
-     142           1 :         Vector3d bVec = field->getNTFField(pos);
-     143           1 :         EXPECT_NEAR(bVec.getR(),1.692*muG, 1e-3*muG);
-     144           1 :         EXPECT_NEAR(bVec.x, -0.584*muG, 1e-3*muG);
-     145           1 :         EXPECT_NEAR(bVec.y, -1.185*muG, 1e-3*muG);
-     146           1 :         EXPECT_NEAR(bVec.z, 1.057*muG, 1e-3*muG);
-     147           1 : }
-     148           1 : TEST(testCMZMagneticField, TestRaidoArcField){
-     149           1 :         ref_ptr<CMZField> field = new CMZField();
-     150             :         Vector3d pos(10*pc,15*pc,-5*pc);        
-     151             : 
-     152             :         // check RadioArcField at given position
-     153           1 :         Vector3d bVec = field->getRadioArcField(pos);
-     154           1 :         EXPECT_NEAR(bVec.getR(), 31.616*muG, 1e-3*muG);
-     155           1 :         EXPECT_NEAR(bVec.x, -4.671*muG, 1e-3*muG);
-     156           1 :         EXPECT_NEAR(bVec.y, 5.465*muG, 1e-3*muG);
-     157           1 :         EXPECT_NEAR(bVec.z, 30.788*muG, 1e-3*muG);
-     158           1 : }
-     159             : 
-     160           1 : TEST(testCMZMagneticField, TestAzimutalComponent){
-     161           1 :         ref_ptr<CMZField> field = new CMZField();
-     162             :         Vector3d mid(12*pc, 9*pc, 20*pc);
-     163             :         Vector3d pos(9*pc, 10*pc, 25*pc);       
-     164             : 
-     165             :         // simple Test for inner part
-     166           1 :         Vector3d bVec = field->BAz(pos, mid, 100, 0.2, 60*pc);
-     167           1 :         EXPECT_NEAR(bVec.x, 3939.782, 1e-3);
-     168           1 :         EXPECT_NEAR(bVec.y, 14347.304, 1e-3);
-     169           1 :         EXPECT_DOUBLE_EQ(bVec.z, 0);
-     170             : 
-     171             :         // simple Test for outer part
-     172           1 :         bVec = field->BAz(pos, mid, 100, 0.2, 10*pc);
-     173           1 :         EXPECT_NEAR(bVec.x, -164.659, 1e-3);
-     174           1 :         EXPECT_NEAR(bVec.y, -1317.270, 1e-3);
-     175           1 :         EXPECT_DOUBLE_EQ(bVec.z, 0);
-     176             : 
-     177             :         // test for molecular Clouds
-     178           1 :         bVec = field->getMCField(pos);
-     179           1 :         EXPECT_NEAR(bVec.x, -8.339*muG, 1e-3*muG);
-     180           1 :         EXPECT_NEAR(bVec.y, -0.850*muG, 1e-3*muG);
-     181           1 :         EXPECT_DOUBLE_EQ(bVec.z, 0);
-     182           1 : }
-     183             : 
-     184           1 : TEST(testToroidalHaloField, SimpleTest) {
-     185           1 :         ref_ptr<ToroidalHaloField> field = new ToroidalHaloField();
-     186           1 :         Vector3d b = field->getField(Vector3d(0.));
-     187           1 :         EXPECT_DOUBLE_EQ(b.x, 0);
-     188           1 :         EXPECT_DOUBLE_EQ(b.y, 0);
-     189           1 :         EXPECT_DOUBLE_EQ(b.z, 0);
-     190             : 
-     191           1 :         b = field->getField(Vector3d(1,0,0));
-     192           1 :         EXPECT_DOUBLE_EQ(b.x, 0.5);
-     193           1 :         EXPECT_DOUBLE_EQ(b.y, 0);
-     194           1 :         EXPECT_DOUBLE_EQ(b.z, 0);
-     195           1 : }
-     196             : 
-     197           1 : TEST(testLogarithmicSpiralField, SimpleTest) {
-     198           1 :         ref_ptr<LogarithmicSpiralField> field = new LogarithmicSpiralField();
-     199           1 :         Vector3d b = field->getField(Vector3d(8.5, 0, 0)*kpc);
-     200           1 :         EXPECT_NEAR(b.x, -1., 1E-2);
-     201           1 :         EXPECT_NEAR(b.y, 0, 1E-10);
-     202           1 :         EXPECT_NEAR(b.z, 0, 1E-10);
-     203           1 : }
-     204             : 
-     205           1 : TEST(testPolarizedSingleModeMagneticField, SimpleTest) {
-     206           1 :         PolarizedSingleModeMagneticField B(2, 4, 0.5, Vector3d(1,1,1), Vector3d(0,1,0), Vector3d(1,0,0), "amplitude", "polarization", "elliptical");
-     207           1 :         Vector3d b = B.getField(Vector3d(1,1,2));
-     208           1 :         EXPECT_DOUBLE_EQ(b.x, 1);
-     209           1 :         EXPECT_NEAR(b.y, 0, 1E-10);
-     210           1 :         EXPECT_NEAR(b.z, 0, 1E-10);
-     211           1 : }
-     212             : 
-     213           1 : int main(int argc, char **argv) {
-     214           1 :         ::testing::InitGoogleTest(&argc, argv);
-     215             :         return RUN_ALL_TESTS();
-     216             : }
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html b/doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html deleted file mode 100644 index d114bd5b9..000000000 --- a/doc/coverageReport/test/testMagneticLens.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testMagneticLens.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testMagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8787100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN28MagneticLens_Deflection_Test8TestBodyEv1
_ZN33Pixelization_angularDistance_Test8TestBodyEv1
_ZN35MagneticLens_OutOfBoundsEnergy_Test8TestBodyEv1
_ZN35MagneticLens_Vector3Deflection_Test8TestBodyEv1
_ZN38ParticleMapsContainer_addParticle_Test8TestBodyEv1
_ZN40Pixelization_randomDirectionInPixel_Test8TestBodyEv1
_ZN45ParticleMapsContainer_getRandomParticles_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testMagneticLens.cpp.func.html b/doc/coverageReport/test/testMagneticLens.cpp.func.html deleted file mode 100644 index 8fc41a1d4..000000000 --- a/doc/coverageReport/test/testMagneticLens.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testMagneticLens.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testMagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8787100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN28MagneticLens_Deflection_Test8TestBodyEv1
_ZN33Pixelization_angularDistance_Test8TestBodyEv1
_ZN35MagneticLens_OutOfBoundsEnergy_Test8TestBodyEv1
_ZN35MagneticLens_Vector3Deflection_Test8TestBodyEv1
_ZN38ParticleMapsContainer_addParticle_Test8TestBodyEv1
_ZN40Pixelization_randomDirectionInPixel_Test8TestBodyEv1
_ZN45ParticleMapsContainer_getRandomParticles_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testMagneticLens.cpp.gcov.html b/doc/coverageReport/test/testMagneticLens.cpp.gcov.html deleted file mode 100644 index e293783f6..000000000 --- a/doc/coverageReport/test/testMagneticLens.cpp.gcov.html +++ /dev/null @@ -1,248 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testMagneticLens.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testMagneticLens.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:8787100.0 %
Date:2024-04-08 14:58:22Functions:77100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /// Tests gamale with a test lense from file and demonstrating basic
-       2             : /// usage
-       3             : 
-       4             : //--------------------------------------------
-       5             : // Project: Galactic magnetic Lense (GaMaLe) -
-       6             : // Copyright (C) 2009 Tobias Winchen         -
-       7             : //               RWTH Aachen, Germany        -
-       8             : // Contact: winchen@physik.rwth-achen.de     -
-       9             : // Licensed under the GNU GPL v2             - 
-      10             : //--------------------------------------------
-      11             : 
-      12             : #include <string>
-      13             : #include "gtest/gtest.h"
-      14             : 
-      15             : #include "crpropa/magneticLens/MagneticLens.h"
-      16             : #include "crpropa/magneticLens/ModelMatrix.h"
-      17             : #include "crpropa/magneticLens/Pixelization.h"
-      18             : #include "crpropa/magneticLens/ParticleMapsContainer.h"
-      19             : #include "crpropa/Common.h"
-      20             : 
-      21             : using namespace std;
-      22             : using namespace crpropa;
-      23             : 
-      24           1 : TEST(MagneticLens, Deflection)
-      25             : {
-      26           1 :         MagneticLens magneticLens(5);
-      27           1 :         Pixelization P(5);
-      28           1 :         ModelMatrixType M;
-      29           1 :         M.resize(P.nPix(), P.nPix());
-      30           1 :         M.reserve(P.nPix());
-      31             : 
-      32             :         // Map any direction (p,t) to (p, -t)
-      33       12289 :         for (int i=0;i<P.nPix();i++)
-      34             :         {
-      35             :                 double theta, phi;
-      36       12288 :                 P.pix2Direction(i, phi, theta);
-      37       12288 :                 theta*= -1;
-      38       12288 :                 int j = P.direction2Pix(phi, theta);
-      39       12288 :                 M.insert(i,j) =1;
-      40             :         }
-      41             : 
-      42           1 :         magneticLens.setLensPart(M, 10 * EeV, 100 * EeV);
-      43             : 
-      44       12289 :         for (int i=0; i < P.nPix(); i++)
-      45             :         {
-      46             :                 double theta, phi;
-      47       12288 :                 P.pix2Direction(i, phi, theta);
-      48       12288 :                 double theta0 = theta;
-      49             : 
-      50             :                 // No CR is allowed to be lost in this lens
-      51       12288 :                 EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, phi, theta));
-      52       12288 :                 EXPECT_NEAR(theta+theta0,0., 0.05);
-      53             :         }
-      54           2 : }
-      55             : 
-      56           1 : TEST(MagneticLens, Vector3Deflection)
-      57             : {
-      58           1 :         MagneticLens magneticLens(5);
-      59           1 :         Pixelization P(5);
-      60           1 :         ModelMatrixType M;
-      61           1 :         M.resize(P.nPix(), P.nPix());
-      62           1 :         M.reserve(P.nPix());
-      63             : 
-      64             :         // No deflection 
-      65       12289 :         for (int i=0;i<P.nPix();i++)
-      66             :         {
-      67       12288 :                 M.insert(i,i) = 1;
-      68             :         }
-      69             : 
-      70           1 :         magneticLens.setLensPart(M, 10 * EeV, 100 * EeV);
-      71             : 
-      72             :         Vector3d u(1,0,0);
-      73             :         Vector3d v(u);
-      74           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
-      75           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
-      76             : 
-      77           1 :         u.x = 0; u.y = 1; u.z = 0; v = u;
-      78           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
-      79           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
-      80             : 
-      81           1 :         u.x = 0; u.y = 0; u.z = 1; v = u;
-      82           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
-      83           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
-      84             : 
-      85           1 :         u.x = 1; u.y = -2; u.z = 3; v = u;
-      86           1 :         EXPECT_TRUE(magneticLens.transformCosmicRay(20 * EeV, v));
-      87           1 :         EXPECT_NEAR(u.getAngleTo(v), 0., 2. / 180 * M_PI);
-      88           2 : }
-      89             : 
-      90           1 : TEST(MagneticLens, OutOfBoundsEnergy)
-      91             : {
-      92           1 :         MagneticLens magneticLens(5);
-      93           1 :         Pixelization P(5);
-      94           1 :         ModelMatrixType M;
-      95           1 :         M.resize(P.nPix(), P.nPix());
-      96           1 :         M.reserve(P.nPix());
-      97           1 :         magneticLens.setLensPart(M,10. * EeV, 100. * EeV);
-      98           1 :         double theta = 0, phi = 0;
-      99           1 :         EXPECT_FALSE(magneticLens.transformCosmicRay(1. * EeV, phi, theta));
-     100           2 : }
-     101             : 
-     102             : 
-     103           1 : TEST(Pixelization, angularDistance)
-     104             : {
-     105             :         // test for correct angular distance in case of same vectors 
-     106           1 :         Pixelization P(6);
-     107       49153 :         for (int idx =0; idx < P.nPix(); idx++)
-     108             :         {
-     109       49152 :                 double ang = P.angularDistance(idx,idx);
-     110       49152 :                 EXPECT_TRUE(ang == ang);
-     111             :         }
-     112           1 : }
-     113             : 
-     114             : 
-     115           1 : TEST(ParticleMapsContainer, addParticle)
-     116             : {
-     117           1 :   ParticleMapsContainer maps;
-     118           1 :   maps.addParticle(1000010010, 1 * EeV, 0 , 0 );
-     119           1 :   std::vector<int> pids = maps.getParticleIds();
-     120           1 :   EXPECT_EQ(pids.size(), 1);
-     121           1 :   EXPECT_EQ(pids[0], 1000010010);
-     122             : 
-     123           1 :   std::vector<double> energies = maps.getEnergies(1000010010);
-     124           1 :   EXPECT_EQ(energies.size(), 1);
-     125           1 : }
-     126             : 
-     127           1 : TEST(ParticleMapsContainer, getRandomParticles)
-     128             : {
-     129           1 :   ParticleMapsContainer maps(0.002);
-     130           1 :   maps.addParticle(1000010010, 1 * EeV, 0 , 0 );
-     131             :   std::vector<double> energies;
-     132             :   std::vector<double> lons;
-     133             :   std::vector<double> lats;
-     134             :   std::vector<int> particleIds;
-     135             : 
-     136           1 :   size_t N = 420;
-     137           1 :         maps.getRandomParticles(N, particleIds, energies, lons, lats);
-     138             :                         
-     139           1 :   EXPECT_EQ(energies.size(), N);
-     140           1 :   EXPECT_EQ(lons.size(), N);
-     141           1 :   EXPECT_EQ(lats.size(), N);
-     142           1 :   EXPECT_EQ(particleIds.size(), N);
-     143             : 
-     144         421 :   for(size_t i = 0; i < N; i++)
-     145             :   {
-     146         420 :     EXPECT_NEAR(log10(energies[i]), 18, 0.002);
-     147         420 :     EXPECT_EQ(particleIds[i], 1000010010);
-     148         420 :     EXPECT_NEAR(lons[i], 0, 2./180*M_PI);
-     149         420 :     EXPECT_NEAR(lats[i], 0, 2./180*M_PI);
-     150             :   }
-     151             : 
-     152           1 : }
-     153             : 
-     154           1 : TEST(Pixelization, randomDirectionInPixel)
-     155             : {
-     156           1 :   Pixelization p(6);
-     157             :   const double long0 = -35./180 * M_PI;
-     158             :   const double lat0 =  12.08/180 * M_PI;
-     159             : 
-     160           1 :   int pix = p.direction2Pix(long0, lat0);
-     161             : 
-     162             :   double rlon, rlat;
-     163           1 :   p.getRandomDirectionInPixel(pix, rlon, rlat);
-     164             : 
-     165             :   // new direction should be inside the pixel
-     166           1 :   EXPECT_EQ(pix, p.direction2Pix(rlon, rlat));
-     167             : 
-     168             :   // new direction should be different from input 
-     169           1 :   EXPECT_FALSE(long0 == rlon);
-     170           1 :   EXPECT_FALSE(lat0 == rlat);
-     171             : 
-     172           1 : }
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testModuleList.cpp.func-sort-c.html b/doc/coverageReport/test/testModuleList.cpp.func-sort-c.html deleted file mode 100644 index 923a232e2..000000000 --- a/doc/coverageReport/test/testModuleList.cpp.func-sort-c.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testModuleList.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testModuleList.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:525594.5 %
Date:2024-04-08 14:58:22Functions:6785.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa23ModuleList_process_Test8TestBodyEv1
_ZN7crpropa25ModuleList_getModule_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runOpenMP_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runSource_Test8TestBodyEv1
_ZN7crpropa28ModuleList_removeModule_Test8TestBodyEv1
_ZN7crpropa32ModuleList_runCandidateList_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testModuleList.cpp.func.html b/doc/coverageReport/test/testModuleList.cpp.func.html deleted file mode 100644 index 1ac5ff9e1..000000000 --- a/doc/coverageReport/test/testModuleList.cpp.func.html +++ /dev/null @@ -1,100 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testModuleList.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testModuleList.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:525594.5 %
Date:2024-04-08 14:58:22Functions:6785.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa23ModuleList_process_Test8TestBodyEv1
_ZN7crpropa25ModuleList_getModule_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runOpenMP_Test8TestBodyEv1
_ZN7crpropa25ModuleList_runSource_Test8TestBodyEv1
_ZN7crpropa28ModuleList_removeModule_Test8TestBodyEv1
_ZN7crpropa32ModuleList_runCandidateList_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testModuleList.cpp.gcov.html b/doc/coverageReport/test/testModuleList.cpp.gcov.html deleted file mode 100644 index 63abd27da..000000000 --- a/doc/coverageReport/test/testModuleList.cpp.gcov.html +++ /dev/null @@ -1,155 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testModuleList.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testModuleList.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:525594.5 %
Date:2024-04-08 14:58:22Functions:6785.7 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/ModuleList.h"
-       2             : #include "crpropa/Source.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : #include "crpropa/module/SimplePropagation.h"
-       5             : #include "crpropa/module/BreakCondition.h"
-       6             : 
-       7             : #include "gtest/gtest.h"
-       8             : 
-       9             : namespace crpropa {
-      10             : 
-      11           1 : TEST(ModuleList, process) {
-      12           1 :         ModuleList modules;
-      13           2 :         modules.add(new SimplePropagation());
-      14           1 :         ParticleState initial;
-      15           1 :         ref_ptr<Candidate> candidate = new Candidate(initial);
-      16           2 :         modules.process(candidate);
-      17           1 : }
-      18             : 
-      19           1 : TEST(ModuleList, getModule) {
-      20           1 :         ModuleList modules;
-      21           1 :         ref_ptr<SimplePropagation> prop = new SimplePropagation();
-      22           1 :         modules.add(prop);
-      23           2 :         EXPECT_TRUE(modules[0] == prop);
-      24           1 : }
-      25             : 
-      26           1 : TEST(ModuleList, removeModule) {
-      27           1 :         ModuleList modules;
-      28           1 :         ref_ptr<SimplePropagation> prop = new SimplePropagation();
-      29           1 :         modules.add(prop);
-      30           1 :         modules.remove(0);
-      31           1 :         EXPECT_EQ(modules.size(), 0);
-      32           1 : }
-      33             : 
-      34           1 : TEST(ModuleList, runCandidateList) {
-      35           1 :         ModuleList modules;
-      36           2 :         modules.add(new SimplePropagation());
-      37           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
-      38           1 :         ParticleState initial;
-      39           1 :         ref_ptr<Candidate> candidate = new Candidate(initial);
-      40           1 :         modules.run(candidate);
-      41           1 :         EXPECT_DOUBLE_EQ(1 * Mpc, candidate->getTrajectoryLength());
-      42           1 :         EXPECT_TRUE(candidate->isActive() == false);
-      43           1 : }
-      44             : 
-      45           1 : TEST(ModuleList, runSource) {
-      46           1 :         ModuleList modules;
-      47           2 :         modules.add(new SimplePropagation());
-      48           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
-      49             :         Source source;
-      50           1 :         source.add(new SourcePosition(Vector3d(10, 0, 0) * Mpc));
-      51           2 :         source.add(new SourceIsotropicEmission());
-      52           1 :         source.add(new SourcePowerLawSpectrum(5 * EeV, 100 * EeV, -2));
-      53           1 :         source.add(new SourceParticleType(nucleusId(1, 1)));
-      54           1 :         modules.setShowProgress(true);
-      55           1 :         modules.run(&source, 100, false);
-      56           1 : }
-      57             : 
-      58             : #if _OPENMP
-      59             : #include <omp.h>
-      60           1 : TEST(ModuleList, runOpenMP) {
-      61           1 :         ModuleList modules;
-      62           2 :         modules.add(new SimplePropagation());
-      63           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
-      64             :         Source source;
-      65           1 :         source.add(new SourcePosition(Vector3d(10, 0, 0) * Mpc));
-      66           2 :         source.add(new SourceIsotropicEmission());
-      67           1 :         source.add(new SourcePowerLawSpectrum(5 * EeV, 100 * EeV, -2));
-      68           1 :         source.add(new SourceParticleType(nucleusId(1, 1)));
-      69           1 :         omp_set_num_threads(2);
-      70           1 :         modules.run(&source, 1000, false);
-      71           1 : }
-      72             : #endif
-      73             : 
-      74           0 : int main(int argc, char **argv) {
-      75           0 :         ::testing::InitGoogleTest(&argc, argv);
-      76           0 :         return RUN_ALL_TESTS();
-      77             : }
-      78             : 
-      79             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testOutput.cpp.func-sort-c.html b/doc/coverageReport/test/testOutput.cpp.func-sort-c.html deleted file mode 100644 index f1f61fe38..000000000 --- a/doc/coverageReport/test/testOutput.cpp.func-sort-c.html +++ /dev/null @@ -1,144 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testOutput.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15716296.9 %
Date:2024-04-08 14:58:22Functions:171894.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_Z11ArraysMatchIiLm10EEN7testing15AssertionResultERAT0__KT_S5_1
_ZN7crpropa16Output_size_Test8TestBodyEv1
_ZN7crpropa27ParticleCollector_size_Test8TestBodyEv1
_ZN7crpropa29TextOutput_printProperty_Test8TestBodyEv1
_ZN7crpropa31ParticleCollector_dumpload_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_fetchItem_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_reprocess_Test8TestBodyEv1
_ZN7crpropa34TextOutput_printHeader_Custom_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event1D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event3D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Version_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_getTrajectory_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_runModuleList_Test8TestBodyEv1
_ZN7crpropa39HDF5Output_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa39TextOutput_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory1D_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory3D_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testOutput.cpp.func.html b/doc/coverageReport/test/testOutput.cpp.func.html deleted file mode 100644 index 9920b9d67..000000000 --- a/doc/coverageReport/test/testOutput.cpp.func.html +++ /dev/null @@ -1,144 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testOutput.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15716296.9 %
Date:2024-04-08 14:58:22Functions:171894.4 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_Z11ArraysMatchIiLm10EEN7testing15AssertionResultERAT0__KT_S5_1
_ZN7crpropa16Output_size_Test8TestBodyEv1
_ZN7crpropa27ParticleCollector_size_Test8TestBodyEv1
_ZN7crpropa29TextOutput_printProperty_Test8TestBodyEv1
_ZN7crpropa31ParticleCollector_dumpload_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_fetchItem_Test8TestBodyEv1
_ZN7crpropa32ParticleCollector_reprocess_Test8TestBodyEv1
_ZN7crpropa34TextOutput_printHeader_Custom_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event1D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Event3D_Test8TestBodyEv1
_ZN7crpropa35TextOutput_printHeader_Version_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_getTrajectory_Test8TestBodyEv1
_ZN7crpropa36ParticleCollector_runModuleList_Test8TestBodyEv1
_ZN7crpropa39HDF5Output_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa39TextOutput_failOnIllegalOutputFile_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory1D_Test8TestBodyEv1
_ZN7crpropa40TextOutput_printHeader_Trajectory3D_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testOutput.cpp.gcov.html b/doc/coverageReport/test/testOutput.cpp.gcov.html deleted file mode 100644 index 3a91eb777..000000000 --- a/doc/coverageReport/test/testOutput.cpp.gcov.html +++ /dev/null @@ -1,355 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testOutput.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testOutput.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:15716296.9 %
Date:2024-04-08 14:58:22Functions:171894.4 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : /** Unit tests for Output modules of CRPropa
-       2             :     Output
-       3             :     TextOutput
-       4             :     ParticleCollector
-       5             :  */
-       6             : 
-       7             : #include "CRPropa.h"
-       8             : 
-       9             : #include "gtest/gtest.h"
-      10             : #include <iostream>
-      11             : #include <string>
-      12             : 
-      13             : 
-      14             : #ifdef CRPROPA_HAVE_HDF5
-      15             : #include <hdf5.h>
-      16             : #endif
-      17             : 
-      18             : // compare two arrays (intead of using Google Mock)
-      19             : // https://stackoverflow.com/a/10062016/6819103
-      20             : template <typename T, size_t size>
-      21           1 : ::testing::AssertionResult ArraysMatch(const T (&expected)[size],
-      22             :                                        const T (&actual)[size]) {
-      23          11 :         for (size_t i(0); i < size; ++i) {
-      24          10 :                 if (expected[i] != actual[i]) {
-      25             :                         return ::testing::AssertionFailure()
-      26           0 :                                << "array[" << i << "] (" << actual[i] << ") != expected["
-      27           0 :                                << i << "] (" << expected[i] << ")";
-      28             :                 }
-      29             :         }
-      30             : 
-      31           1 :         return ::testing::AssertionSuccess();
-      32             : }
-      33             : 
-      34             : namespace crpropa {
-      35             : 
-      36             : //-- Output
-      37           1 : TEST(Output, size) {
-      38           1 :         Candidate c;
-      39           1 :         Output output;
-      40           6 :         for (int it = 0; it < 5; ++it, output.process(&c));
-      41             : 
-      42           1 :         EXPECT_EQ(output.size(), 5);
-      43           1 : }
-      44             : 
-      45             : //-- TextOutput
-      46           1 : TEST(TextOutput, printHeader_Trajectory1D) {
-      47           1 :         Candidate c;
-      48           1 :         TextOutput output(Output::Trajectory1D);
-      49             : 
-      50           1 :         ::testing::internal::CaptureStdout();
-      51           1 :         output.process(&c);
-      52           1 :         std::string captured = testing::internal::GetCapturedStdout();
-      53             : 
-      54           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")), "#\tID\tE\tX");
-      55           1 : }
-      56             : 
-      57           1 : TEST(TextOutput, printHeader_Event1D) {
-      58           1 :         Candidate c;
-      59           1 :         TextOutput output(Output::Event1D);
-      60             : 
-      61           1 :         ::testing::internal::CaptureStdout();
-      62           1 :         output.process(&c);
-      63           1 :         std::string captured = testing::internal::GetCapturedStdout();
-      64             : 
-      65           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")), "#\tD\tID\tE\tID0\tE0");
-      66           1 : }
-      67             : 
-      68           1 : TEST(TextOutput, printHeader_Trajectory3D) {
-      69           1 :         Candidate c;
-      70           1 :         TextOutput output(Output::Trajectory3D);
-      71             : 
-      72           1 :         ::testing::internal::CaptureStdout();
-      73           1 :         output.process(&c);
-      74           1 :         std::string captured = testing::internal::GetCapturedStdout();
-      75             : 
-      76           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")),
-      77             :                   "#\tD\tID\tE\tX\tY\tZ\tPx\tPy\tPz");
-      78           1 : }
-      79             : 
-      80           1 : TEST(TextOutput, printHeader_Event3D) {
-      81           1 :         Candidate c;
-      82           1 :         TextOutput output(Output::Event3D);
-      83             : 
-      84           1 :         ::testing::internal::CaptureStdout();
-      85           1 :         output.process(&c);
-      86           1 :         std::string captured = testing::internal::GetCapturedStdout();
-      87             : 
-      88           2 :         EXPECT_EQ(
-      89             :             captured.substr(0, captured.find("\n")),
-      90             :             "#\tD\tID\tE\tX\tY\tZ\tPx\tPy\tPz\tID0\tE0\tX0\tY0\tZ0\tP0x\tP0y\tP0z");
-      91           1 : }
-      92             : 
-      93           1 : TEST(TextOutput, printHeader_Custom) {
-      94           1 :         Candidate c;
-      95           1 :         TextOutput output(Output::Event1D);
-      96             : 
-      97           1 :         output.enable(Output::SerialNumberColumn);
-      98           1 :         output.disable(Output::TrajectoryLengthColumn);
-      99           1 :         output.set(Output::RedshiftColumn, false);
-     100           1 :         output.enable(Output::CandidateTagColumn);
-     101             : 
-     102           1 :         ::testing::internal::CaptureStdout();
-     103           1 :         output.process(&c);
-     104           1 :         std::string captured = testing::internal::GetCapturedStdout();
-     105             : 
-     106           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")),
-     107             :                   "#\tSN\tID\tE\tSN0\tID0\tE0\tSN1\ttag");
-     108           1 : }
-     109             : 
-     110           1 : TEST(TextOutput, printProperty) {
-     111           1 :         Candidate c;
-     112           1 :         TextOutput output(Output::Event1D);
-     113           1 :         output.disableAll();
-     114           2 :         output.enableProperty("foo", 2.0, "Bar");
-     115             : 
-     116           1 :         ::testing::internal::CaptureStdout();
-     117           1 :         output.process(&c);
-     118           1 :         std::string captured = testing::internal::GetCapturedStdout();
-     119             : 
-     120             :         // name in first line of header
-     121           2 :         EXPECT_EQ(captured.substr(0, captured.find("\n")), "#\tfoo");
-     122           1 : }
-     123             : 
-     124           1 : TEST(TextOutput, printHeader_Version) {
-     125           1 :         Candidate c;
-     126           1 :         TextOutput output(Output::Event1D);
-     127             : 
-     128           1 :         ::testing::internal::CaptureStdout();
-     129           1 :         output.process(&c);
-     130           1 :         std::string captured = testing::internal::GetCapturedStdout();
-     131             : 
-     132             :         // length of the prefix is 19 chars
-     133           1 :         size_t version_pos = captured.find("# CRPropa version: ") + 19;
-     134             : 
-     135           2 :         EXPECT_EQ(captured.substr(version_pos,
-     136             :                                   captured.find("\n", version_pos) - version_pos),
-     137             :                   g_GIT_DESC);
-     138           1 : }
-     139             : 
-     140             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
-     141           1 : TEST(TextOutput, failOnIllegalOutputFile) {
-     142           2 :         EXPECT_THROW(
-     143             :             TextOutput output("THIS_FOLDER_MUST_NOT_EXISTS_12345+/FILE.txt"),
-     144             :             std::runtime_error);
-     145           1 : }
-     146             : #endif
-     147             : 
-     148             : #ifdef CRPROPA_HAVE_HDF5
-     149             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
-     150           1 : TEST(HDF5Output, failOnIllegalOutputFile) {
-     151           1 :         HDF5Output out;
-     152             :         // disable default error output of HDF5
-     153           1 :         H5Eset_auto2(H5E_DEFAULT, NULL, NULL);
-     154           2 :         EXPECT_THROW(out.open("THIS_FOLDER_MUST_NOT_EXISTS_12345+/FILE.h5"),
-     155             :                      std::runtime_error);
-     156           1 : }
-     157             : #endif
-     158             : #endif
-     159             : 
-     160             : //-- ParticleCollector
-     161           2 : TEST(ParticleCollector, size) {
-     162           2 :         ref_ptr<Candidate> c = new Candidate();
-     163           1 :         ParticleCollector output;
-     164             : 
-     165           6 :         for (int it = 0; it < 5; ++it, output.process(c))
-     166             :                 ;
-     167             : 
-     168           1 :         EXPECT_EQ(output.size(), 5);
-     169           2 : }
-     170             : 
-     171           1 : TEST(ParticleCollector, fetchItem) {
-     172           2 :         ref_ptr<Candidate> c = new Candidate(nucleusId(1, 1), 1 * EeV);
-     173           1 :         ParticleCollector output;
-     174             : 
-     175           1 :         output.process(c);
-     176             : 
-     177           2 :         EXPECT_EQ(output[0], c);
-     178           2 : }
-     179             : 
-     180           1 : TEST(ParticleCollector, reprocess) {
-     181           2 :         ref_ptr<Candidate> c = new Candidate(nucleusId(1, 1), 1 * EeV);
-     182           1 :         ParticleCollector collector;
-     183           1 :         ParticleCollector output;
-     184             : 
-     185           1 :         collector.process(c);
-     186           1 :         collector.reprocess(&output);
-     187             : 
-     188           2 :         EXPECT_EQ(output[0], c);
-     189           2 : }
-     190             : 
-     191           1 : TEST(ParticleCollector, dumpload) {
-     192           2 :         ref_ptr<Candidate> c = new Candidate(nucleusId(1, 1), 1.234 * EeV);
-     193           1 :         c->current.setPosition(Vector3d(1, 2, 3));
-     194           1 :         c->current.setDirection(Vector3d(-1, -1, -1));
-     195           1 :         c->setTrajectoryLength(1 * Mpc);
-     196           1 :         c->setRedshift(2);
-     197             : 
-     198           1 :         ParticleCollector input;
-     199           1 :         ParticleCollector output;
-     200             : 
-     201          12 :         for (int i = 0; i <= 10; ++i) {
-     202          22 :                 input.process(c);
-     203             :         }
-     204             : 
-     205             :         // Well, it would be nicer if we don't need to receate any file
-     206           1 :         input.dump("ParticleCollector_DumpTest.txt");
-     207           1 :         output.load("ParticleCollector_DumpTest.txt");
-     208             : 
-     209           1 :         EXPECT_EQ(input.size(), output.size());
-     210           2 :         EXPECT_EQ(output[0]->current.getEnergy(), c->current.getEnergy());
-     211           2 :         EXPECT_EQ(output[1]->getTrajectoryLength(), c->getTrajectoryLength());
-     212           2 :         EXPECT_EQ(output[2]->current.getId(), c->current.getId());
-     213           2 :         EXPECT_EQ(output[3]->getRedshift(), c->getRedshift());
-     214           2 : }
-     215             : 
-     216             : // Just test if the trajectory is on a line for rectilinear propagation
-     217           1 : TEST(ParticleCollector, getTrajectory) {
-     218             :         int pos_x[10];
-     219           1 :         int pos_x_expected[] = {9, 8, 7, 6, 5, 4, 3, 2, 1, 0};
-     220             : 
-     221           1 :         ParticleState p;
-     222           1 :         p.setPosition(Vector3d(10, 0, 0));
-     223           1 :         p.setDirection(Vector3d(-1, 0, 0));
-     224           1 :         ref_ptr<Candidate> c = new Candidate(p);
-     225             : 
-     226           1 :         ref_ptr<ParticleCollector> output = new ParticleCollector();
-     227           1 :         ref_ptr<ParticleCollector> trajectory = new ParticleCollector();
-     228           1 :         trajectory->setClone(true);
-     229             : 
-     230           1 :         ref_ptr<ModuleList> sim = new ModuleList();
-     231           1 :         sim->add(new SimplePropagation(1, 1));
-     232             : 
-     233           1 :         ref_ptr<Observer> obs = new Observer();
-     234           1 :         obs->add(new Observer1D());
-     235           1 :         obs->onDetection(output);
-     236           1 :         sim->add(obs);
-     237             : 
-     238           2 :         sim->run(c);
-     239             : 
-     240           2 :         output->getTrajectory(sim, 0, trajectory);
-     241             : 
-     242             :         Vector3d pos;
-     243             :         int i = 0;
-     244             : 
-     245           1 :         for (ParticleCollector::iterator itr = trajectory->begin();
-     246          11 :              itr != trajectory->end(); ++itr) {
-     247          10 :                 pos = (*(itr->get())).current.getPosition();
-     248          10 :                 pos_x[i] = pos.getX();
-     249          10 :                 ++i;
-     250             :         }
-     251             : 
-     252           1 :         EXPECT_TRUE(ArraysMatch(pos_x_expected, pos_x));
-     253           1 : }
-     254             : 
-     255           1 : TEST(ParticleCollector, runModuleList) {
-     256           1 :         ModuleList modules;
-     257           2 :         modules.add(new SimplePropagation());
-     258           1 :         modules.add(new MaximumTrajectoryLength(1 * Mpc));
-     259             : 
-     260           1 :         ParticleState p;
-     261           1 :         p.setPosition(Vector3d(10, 0, 0));
-     262           1 :         p.setDirection(Vector3d(-1, 0, 0));
-     263           1 :         ref_ptr<Candidate> c = new Candidate(p);
-     264             : 
-     265           1 :         ref_ptr<ParticleCollector> collector = new ParticleCollector();
-     266             : 
-     267           1 :         collector->process(c);
-     268             : 
-     269           1 :         modules.setShowProgress(false);
-     270           1 :         auto candidates = collector->getContainer();
-     271           1 :         modules.run(&candidates);
-     272           2 : }
-     273             : 
-     274           0 : int main(int argc, char **argv) {
-     275           0 :         ::testing::InitGoogleTest(&argc, argv);
-     276           0 :         return RUN_ALL_TESTS();
-     277             : }
-     278             : 
-     279             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testPropagation.cpp.func-sort-c.html b/doc/coverageReport/test/testPropagation.cpp.func-sort-c.html deleted file mode 100644 index 15ff4021f..000000000 --- a/doc/coverageReport/test/testPropagation.cpp.func-sort-c.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testPropagation.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testPropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:33734099.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa29testPropagationBP_proton_Test8TestBodyEv1
_ZN7crpropa29testPropagationCK_proton_Test8TestBodyEv1
_ZN7crpropa30testPropagationBP_neutron_Test8TestBodyEv1
_ZN7crpropa30testPropagationCK_neutron_Test8TestBodyEv1
_ZN7crpropa31testPropagationBP_gyration_Test8TestBodyEv1
_ZN7crpropa31testPropagationCK_gyration_Test8TestBodyEv1
_ZN7crpropa31testSimplePropagation_step_Test8TestBodyEv1
_ZN7crpropa32testPropagationBP_zeroField_Test8TestBodyEv1
_ZN7crpropa32testPropagationCK_zeroField_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_reduceStep_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_reduceStep_Test8TestBodyEv1
_ZN7crpropa34testPropagationBP_constructor_Test8TestBodyEv1
_ZN7crpropa34testPropagationCK_constructor_Test8TestBodyEv1
_ZN7crpropa35testPropagationBP_increaseStep_Test8TestBodyEv1
_ZN7crpropa35testPropagationCK_increaseStep_Test8TestBodyEv1
_ZN7crpropa44testPropagationBP_fixedStepOptimization_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testPropagation.cpp.func.html b/doc/coverageReport/test/testPropagation.cpp.func.html deleted file mode 100644 index 586d6fcc2..000000000 --- a/doc/coverageReport/test/testPropagation.cpp.func.html +++ /dev/null @@ -1,148 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testPropagation.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testPropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:33734099.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa29testPropagationBP_proton_Test8TestBodyEv1
_ZN7crpropa29testPropagationCK_proton_Test8TestBodyEv1
_ZN7crpropa30testPropagationBP_neutron_Test8TestBodyEv1
_ZN7crpropa30testPropagationCK_neutron_Test8TestBodyEv1
_ZN7crpropa31testPropagationBP_gyration_Test8TestBodyEv1
_ZN7crpropa31testPropagationCK_gyration_Test8TestBodyEv1
_ZN7crpropa31testSimplePropagation_step_Test8TestBodyEv1
_ZN7crpropa32testPropagationBP_zeroField_Test8TestBodyEv1
_ZN7crpropa32testPropagationCK_zeroField_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationBP_reduceStep_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_exceptions_Test8TestBodyEv1
_ZN7crpropa33testPropagationCK_reduceStep_Test8TestBodyEv1
_ZN7crpropa34testPropagationBP_constructor_Test8TestBodyEv1
_ZN7crpropa34testPropagationCK_constructor_Test8TestBodyEv1
_ZN7crpropa35testPropagationBP_increaseStep_Test8TestBodyEv1
_ZN7crpropa35testPropagationCK_increaseStep_Test8TestBodyEv1
_ZN7crpropa44testPropagationBP_fixedStepOptimization_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testPropagation.cpp.gcov.html b/doc/coverageReport/test/testPropagation.cpp.gcov.html deleted file mode 100644 index f3e80ad45..000000000 --- a/doc/coverageReport/test/testPropagation.cpp.gcov.html +++ /dev/null @@ -1,632 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testPropagation.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testPropagation.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:33734099.1 %
Date:2024-04-08 14:58:22Functions:181994.7 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Candidate.h"
-       2             : #include "crpropa/ParticleID.h"
-       3             : #include "crpropa/module/SimplePropagation.h"
-       4             : #include "crpropa/module/PropagationBP.h"
-       5             : #include "crpropa/module/PropagationCK.h"
-       6             : #include "crpropa/magneticField/turbulentField/PlaneWaveTurbulence.h"
-       7             : 
-       8             : #include "gtest/gtest.h"
-       9             : 
-      10             : #include <string>
-      11             : #include <iostream>
-      12             : 
-      13             : namespace crpropa {
-      14             : 
-      15           1 : TEST(testSimplePropagation, step) {
-      16           1 :         double minStep = 20;
-      17           1 :         double maxStep = 100;
-      18           1 :         SimplePropagation propa(minStep, maxStep);
-      19             : 
-      20           1 :         ParticleState p;
-      21           1 :         p.setPosition(Vector3d(0, 0, 0));
-      22           1 :         p.setDirection(Vector3d(0, 1, 0));
-      23             : 
-      24           1 :         Candidate c(p);
-      25           1 :         c.setNextStep(10);
-      26             : 
-      27           1 :         propa.process(&c);
-      28             : 
-      29           1 :         EXPECT_EQ(minStep, c.getCurrentStep());
-      30           1 :         EXPECT_EQ(maxStep, c.getNextStep());
-      31           2 :         EXPECT_EQ(Vector3d(0,  0, 0), c.created.getPosition());
-      32           2 :         EXPECT_EQ(Vector3d(0,  1, 0), c.created.getDirection());
-      33           2 :         EXPECT_EQ(Vector3d(0,  0, 0), c.previous.getPosition());
-      34           2 :         EXPECT_EQ(Vector3d(0,  1, 0), c.previous.getDirection());
-      35           2 :         EXPECT_EQ(Vector3d(0, 20, 0), c.current.getPosition());
-      36           2 :         EXPECT_EQ(Vector3d(0,  1, 0), c.current.getDirection());
-      37           2 : }
-      38             : 
-      39             : 
-      40           1 : TEST(testPropagationCK, zeroField) {
-      41           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 0)));
-      42             : 
-      43             :         double minStep = 0.1 * kpc;
-      44           1 :         propa.setMinimumStep(minStep);
-      45             : 
-      46           1 :         ParticleState p;
-      47           1 :         p.setId(nucleusId(1, 1));
-      48           1 :         p.setEnergy(100 * EeV);
-      49           1 :         p.setPosition(Vector3d(0, 0, 0));
-      50           1 :         p.setDirection(Vector3d(0, 1, 0));
-      51           1 :         Candidate c(p);
-      52           1 :         c.setNextStep(0);
-      53             : 
-      54           1 :         propa.process(&c);
-      55             : 
-      56           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step
-      57           1 :         EXPECT_DOUBLE_EQ(5 * minStep, c.getNextStep());  // acceleration by factor 5
-      58           1 : }
-      59             : 
-      60             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
-      61           1 : TEST(testPropagationCK, exceptions) {
-      62             :         // minStep should be smaller than maxStep
-      63           2 :         EXPECT_THROW(PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 0.42, 10 , 0), std::runtime_error);
-      64             :         // Too large tolerance: tolerance should be between 0 and 1
-      65           2 :         EXPECT_THROW(PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 42., 10 * kpc , 20 * kpc), std::runtime_error);
-      66             : 
-      67           2 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-      68             : 
-      69             :         // set maximum step, so that it can be tested what happens if a larger minStep is set.
-      70           1 :         propa.setMaximumStep(1 * Mpc);
-      71             : 
-      72             :         // this tests _that_ the expected exception is thrown
-      73           1 :         EXPECT_THROW(propa.setTolerance(2.), std::runtime_error);
-      74           1 :         EXPECT_THROW(propa.setMinimumStep(-1.), std::runtime_error);
-      75           1 :         EXPECT_THROW(propa.setMinimumStep(2 * Mpc), std::runtime_error);
-      76             : 
-      77             :         // set minimum step, so that it can be tested what happens if a smaller maxStep is set.
-      78           1 :         propa.setMinimumStep(0.5 * Mpc);
-      79             : 
-      80           1 :         EXPECT_THROW(propa.setMaximumStep(0.1 * Mpc), std::runtime_error);
-      81           1 : }
-      82             : #endif
-      83             : 
-      84           1 : TEST(testPropagationCK, constructor) {
-      85             :         // Test construction and parameters
-      86           1 :         ref_ptr<MagneticField> bField = new UniformMagneticField(Vector3d(0, 0, 1 * nG));
-      87             : 
-      88           1 :         double minStep = 1.;
-      89           1 :         double maxStep = 100.;
-      90           1 :         double tolerance = 0.01;
-      91             : 
-      92           1 :         PropagationCK propa(bField, tolerance, minStep, maxStep);
-      93             : 
-      94           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
-      95           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
-      96           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
-      97           2 :         EXPECT_EQ(bField, propa.getField());
-      98             : 
-      99             :         // Update parameters
-     100           1 :         minStep = 10.;
-     101           1 :         maxStep = 10.;
-     102           1 :         propa.setTolerance(0.0001);
-     103           1 :         bField = new UniformMagneticField(Vector3d(10 * nG, 0, 1 * nG));
-     104             : 
-     105           1 :         propa.setTolerance(tolerance);
-     106           1 :         propa.setMinimumStep(minStep);
-     107           1 :         propa.setMaximumStep(maxStep);
-     108           1 :         propa.setField(bField);
-     109             : 
-     110           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
-     111           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
-     112           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
-     113           2 :         EXPECT_EQ(bField, propa.getField());
-     114             : 
-     115             :         // The propagation should be initialized with the default constructor
-     116           2 :         PropagationCK propaCKField(bField);
-     117           1 :         EXPECT_EQ(propaCKField.getMaximumStep(), 1 * Gpc);
-     118           2 : }
-     119             : 
-     120             : 
-     121             : // Test if the step size is reduced correctly if the error is too large with respect to the tolerance: r > 1
-     122           1 : TEST(testPropagationCK, reduceStep) {
-     123           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 100 * nG)));
-     124             : 
-     125             :         double minStep = 0.1 * kpc;
-     126             :         double maxStep = 1 * Gpc;
-     127           1 :         propa.setMinimumStep(minStep);
-     128           1 :         propa.setMaximumStep(maxStep);
-     129             :         // small tolerance leads to large values of r
-     130           1 :         propa.setTolerance(1e-15);
-     131             : 
-     132           1 :         ParticleState p;
-     133           1 :         p.setId(nucleusId(1, 1));
-     134           1 :         p.setEnergy(100 * TeV);
-     135           1 :         p.setPosition(Vector3d(0, 0, 0));
-     136           1 :         p.setDirection(Vector3d(0, 1, 0));
-     137           1 :         Candidate c(p);
-     138             :         // large step leads to large errors and thus in combination with the low tolerance to high values of r
-     139           1 :         c.setNextStep(maxStep);
-     140             : 
-     141           1 :         propa.process(&c);
-     142             : 
-     143             :         // adaptive algorithm should propagate particle with minimum step size due to the low value for the tolerance
-     144           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step because of large r due to small tolerance
-     145           1 :         EXPECT_DOUBLE_EQ(minStep, c.getNextStep());  // stay at minimum step because of large r due to small tolerance
-     146           1 : }
-     147             : 
-     148             : 
-     149             : // Test if the step size is increased correctly if the error is small with respect to the tolerance: r < 1
-     150           1 : TEST(testPropagationCK, increaseStep) {
-     151           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     152             : 
-     153             :         double minStep = 0.001 * pc;
-     154             :         double maxStep = 3.125 * pc;
-     155           1 :         propa.setMinimumStep(minStep);
-     156           1 :         propa.setMaximumStep(maxStep);
-     157             :         // large tolerance leads to small values of r. Consequently, the step size can be increased.
-     158           1 :         propa.setTolerance(0.9);
-     159             : 
-     160           1 :         ParticleState p;
-     161           1 :         p.setId(nucleusId(1, 1));
-     162           1 :         p.setEnergy(100 * EeV);
-     163           1 :         p.setPosition(Vector3d(0, 0, 0));
-     164           1 :         p.setDirection(Vector3d(0, 1, 0));
-     165           1 :         Candidate c(p);
-     166             : 
-     167             :         // each step the step size can be increased by a factor of 5.
-     168           6 :         for (int i = 1; i < 6; i++){
-     169           5 :                 propa.process(&c);
-     170           5 :                 EXPECT_DOUBLE_EQ(minStep*pow(5, i) / pc, c.getNextStep()/pc);
-     171             :         }
-     172             :         // after 5 steps the maxStep is reached. The current step is, however, less.
-     173           1 :         EXPECT_DOUBLE_EQ(maxStep/pc/5., c.getCurrentStep()/pc);
-     174           1 :         EXPECT_DOUBLE_EQ(maxStep/pc, c.getNextStep()/pc);
-     175           1 : }
-     176             : 
-     177             : 
-     178           1 : TEST(testPropagationCK, proton) {
-     179           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     180             : 
-     181             :         double minStep = 0.1 * kpc;
-     182           1 :         propa.setMinimumStep(minStep);
-     183             : 
-     184           1 :         ParticleState p;
-     185           1 :         p.setId(nucleusId(1, 1));
-     186           1 :         p.setEnergy(100 * EeV);
-     187           1 :         p.setPosition(Vector3d(0, 0, 0));
-     188           1 :         p.setDirection(Vector3d(0, 1, 0));
-     189           1 :         Candidate c(p);
-     190           1 :         c.setNextStep(0);
-     191             : 
-     192           1 :         propa.process(&c);
-     193             : 
-     194           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step
-     195           1 :         EXPECT_DOUBLE_EQ(5 * minStep, c.getNextStep());  // acceleration by factor 5
-     196           1 : }
-     197             : 
-     198             : 
-     199             : // Test the numerical results for parallel magnetic field lines along the z-axis
-     200           1 : TEST(testPropagationCK, gyration) {
-     201           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     202             : 
-     203             :         double step = 10. * Mpc;  // gyroradius is 108.1 Mpc
-     204           1 :         propa.setMaximumStep(step);
-     205           1 :         propa.setMinimumStep(step);
-     206             : 
-     207             : 
-     208           1 :         ParticleState p;
-     209           1 :         p.setId(nucleusId(1, 1));
-     210           1 :         p.setEnergy(100 * EeV);
-     211           1 :         p.setPosition(Vector3d(0, 0, 0));
-     212           1 :         p.setDirection(Vector3d(1, 1, 1));
-     213           1 :         Candidate c(p);
-     214           1 :         c.setNextStep(0);
-     215           1 :         propa.process(&c);
-     216             : 
-     217           1 :         double dirX = c.current.getDirection().x;
-     218           1 :         double dirY = c.current.getDirection().y;
-     219           1 :         double dirZ = c.current.getDirection().z;
-     220           1 :         double posZ = c.current.getPosition().z;
-     221             : 
-     222             :         // Test if the analytical solution is achieved for the components of the momentum with the CK method as expected in
-     223             :         // the background magnetic field.
-     224             :         double precision = 1e-7;
-     225             :         double expected = 2 / 3.;
-     226           1 :         EXPECT_NEAR(expected, dirX * dirX + dirY * dirY, expected * precision);  // constant momentum in the plane perpendicular to background magnetic field field
-     227             :         expected = 1 / 3.;
-     228           1 :         EXPECT_NEAR(expected, dirZ * dirZ, expected * precision);  // constant momentum parallel to the background magnetic field
-     229             :         expected = step * step / 3.;
-     230           1 :         EXPECT_NEAR(expected, posZ * posZ, expected * precision);  // constant velocity parallel to the background magnetic field
-     231             : 
-     232             :         // Nine new steps to have finally propagated the particle ten times
-     233          10 :         for (int i = 0; i < 9; i++){
-     234           9 :                 propa.process(&c);
-     235             :         }
-     236             : 
-     237           1 :         dirX = c.current.getDirection().x;
-     238           1 :         dirY = c.current.getDirection().y;
-     239           1 :         dirZ = c.current.getDirection().z;
-     240           1 :         posZ = c.current.getPosition().z;
-     241             : 
-     242             :         // Compare the numerical solutions after ten steps with the analytical solution of the trajectories
-     243             :         expected = 2 / 3.;
-     244           1 :         EXPECT_NEAR(expected, dirX * dirX + dirY * dirY, expected * precision);  // constant momentum in the plane perpendicular to background magnetic field field
-     245             :         expected = 1 / 3.;
-     246           1 :         EXPECT_NEAR(expected, dirZ * dirZ, expected * precision);  // constant momentum parallel to the background magnetic field
-     247             :         expected = 100 * step * step / 3.;
-     248           1 :         EXPECT_NEAR(expected, posZ * posZ, expected * precision);  // constant velocity parallel to the background magnetic field
-     249           1 : }
-     250             : 
-     251             : 
-     252           1 : TEST(testPropagationCK, neutron) {
-     253           1 :         PropagationCK propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     254           1 :         propa.setMinimumStep(1 * kpc);
-     255           1 :         propa.setMaximumStep(42 * Mpc);
-     256             : 
-     257           1 :         ParticleState p;
-     258           1 :         p.setId(nucleusId(1, 0));
-     259           1 :         p.setEnergy(100 * EeV);
-     260           1 :         p.setPosition(Vector3d(0, 0, 0));
-     261           1 :         p.setDirection(Vector3d(0, 1, 0));
-     262           1 :         Candidate c(p);
-     263             : 
-     264           1 :         propa.process(&c);
-     265             : 
-     266           1 :         EXPECT_DOUBLE_EQ(1 * kpc, c.getCurrentStep());
-     267           1 :         EXPECT_DOUBLE_EQ(42 * Mpc, c.getNextStep());
-     268           2 :         EXPECT_EQ(Vector3d(0, 1 * kpc, 0), c.current.getPosition());
-     269           2 :         EXPECT_EQ(Vector3d(0, 1, 0), c.current.getDirection());
-     270           1 : }
-     271             : 
-     272             : 
-     273           1 : TEST(testPropagationBP, zeroField) {
-     274           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 0)), 1 * kpc);
-     275             : 
-     276             :         double minStep = 0.1 * kpc;
-     277           1 :         propa.setMinimumStep(minStep);
-     278           1 :         propa.setTolerance(0.42);
-     279             : 
-     280           1 :         ParticleState p;
-     281           1 :         p.setId(nucleusId(1, 1));
-     282           1 :         p.setEnergy(100 * EeV);
-     283           1 :         p.setPosition(Vector3d(0, 0, 0));
-     284           1 :         p.setDirection(Vector3d(0, 1, 0));
-     285           1 :         Candidate c(p);
-     286           1 :         c.setNextStep(0);
-     287             : 
-     288           1 :         propa.process(&c);
-     289             : 
-     290           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step
-     291           1 :         EXPECT_DOUBLE_EQ(5 * minStep, c.getNextStep());  // acceleration by factor 5
-     292           1 : }
-     293             : 
-     294             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
-     295           1 : TEST(testPropagationBP, exceptions) {
-     296             :         // minStep should be smaller than maxStep
-     297           2 :         EXPECT_THROW(PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 0.42, 10 , 0), std::runtime_error);
-     298             :         // Too large tolerance: tolerance should be between 0 and 1
-     299           2 :         EXPECT_THROW(PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 42., 10 * kpc , 20 * kpc), std::runtime_error);
-     300             : 
-     301           2 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     302             : 
-     303             :         // set maximum step, so that it can be tested what happens if a larger minStep is set.
-     304           1 :         propa.setMaximumStep(1 * Mpc);
-     305             : 
-     306             :         // this tests _that_ the expected exception is thrown
-     307           1 :         EXPECT_THROW(propa.setTolerance(2.), std::runtime_error);
-     308           1 :         EXPECT_THROW(propa.setMinimumStep(-1.), std::runtime_error);
-     309           1 :         EXPECT_THROW(propa.setMinimumStep(2 * Mpc), std::runtime_error);
-     310             : 
-     311             :         // set minimum step, so that it can be tested what happens if a smaller maxStep is set.
-     312           1 :         propa.setMinimumStep(0.5 * Mpc);
-     313             : 
-     314           1 :         EXPECT_THROW(propa.setMaximumStep(0.1 * Mpc), std::runtime_error);
-     315           1 : }
-     316             : #endif
-     317             : 
-     318             : 
-     319           1 : TEST(testPropagationBP, constructor) {
-     320             :         // Test construction and parameters
-     321           1 :         ref_ptr<MagneticField> bField = new UniformMagneticField(Vector3d(0, 0, 1 * nG));
-     322             : 
-     323           1 :         double minStep = 1.;
-     324           1 :         double maxStep = 100.;
-     325           1 :         double tolerance = 0.01;
-     326             : 
-     327           1 :         PropagationBP propa(bField, tolerance, minStep, maxStep);
-     328             : 
-     329           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
-     330           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
-     331           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
-     332           2 :         EXPECT_EQ(bField, propa.getField());
-     333             : 
-     334             :         // Update parameters
-     335           1 :         minStep = 10.;
-     336           1 :         maxStep = 10.;
-     337           1 :         propa.setTolerance(0.0001);
-     338           1 :         bField = new UniformMagneticField(Vector3d(10 * nG, 0, 1 * nG));
-     339             : 
-     340           1 :         propa.setTolerance(tolerance);
-     341           1 :         propa.setMinimumStep(minStep);
-     342           1 :         propa.setMaximumStep(maxStep);
-     343           1 :         propa.setField(bField);
-     344             : 
-     345           1 :         EXPECT_EQ(minStep, propa.getMinimumStep());
-     346           1 :         EXPECT_EQ(maxStep, propa.getMaximumStep());
-     347           1 :         EXPECT_EQ(tolerance, propa.getTolerance());
-     348           2 :         EXPECT_EQ(bField, propa.getField());
-     349             : 
-     350             :         // Test the fixed step size version of the Boris push
-     351           1 :         minStep = 10. * kpc;
-     352           2 :         PropagationBP propaBP(bField, minStep);
-     353           1 :         EXPECT_EQ(propaBP.getMaximumStep(), propaBP.getMaximumStep());
-     354             : 
-     355             :         // The propagation should be initialized with the default constructor
-     356           2 :         PropagationBP propaBPField(bField);
-     357           1 :         EXPECT_EQ(propaBPField.getMaximumStep(), 1 * kpc);
-     358           2 : }
-     359             : 
-     360             : 
-     361             : // Test if the step size is reduced correctly if the error is too large with respect to the tolerance: r > 1
-     362           1 : TEST(testPropagationBP, reduceStep) {
-     363           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 100 * nG)), 1 * kpc);
-     364             : 
-     365             :         double minStep = 0.1 * kpc;
-     366             :         double maxStep = 1 * Gpc;
-     367           1 :         propa.setMinimumStep(minStep);
-     368           1 :         propa.setMaximumStep(maxStep);
-     369             :         // small tolerance leads to large values of r
-     370           1 :         propa.setTolerance(1e-15);
-     371             : 
-     372           1 :         ParticleState p;
-     373           1 :         p.setId(nucleusId(1, 1));
-     374           1 :         p.setEnergy(100 * TeV);
-     375           1 :         p.setPosition(Vector3d(0, 0, 0));
-     376           1 :         p.setDirection(Vector3d(0, 1, 0));
-     377           1 :         Candidate c(p);
-     378             :         // large step leads to large errors and thus in combination with the low tolerance to high values of r
-     379           1 :         c.setNextStep(maxStep);
-     380             : 
-     381           1 :         propa.process(&c);
-     382             : 
-     383             :         // adaptive algorithm should propagate particle with minimum step size due to the low value for the tolerance
-     384           1 :         EXPECT_DOUBLE_EQ(minStep, c.getCurrentStep());  // perform minimum step because of large r due to small tolerance
-     385           1 :         EXPECT_DOUBLE_EQ(minStep, c.getNextStep());  // stay at minimum step because of large r due to small tolerance
-     386           1 : }
-     387             : 
-     388             : 
-     389             : // Test if the step size is increased correctly if the error is small with respect to the tolerance: r < 1
-     390           1 : TEST(testPropagationBP, increaseStep) {
-     391           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)), 1 * kpc);
-     392             : 
-     393             :         double minStep = 0.001 * pc;
-     394             :         double maxStep = 3.125 * pc;
-     395           1 :         propa.setMinimumStep(minStep);
-     396           1 :         propa.setMaximumStep(maxStep);
-     397             :         // large tolerance leads to small values of r. Consequently, the step size can be increased.
-     398           1 :         propa.setTolerance(0.9);
-     399             : 
-     400           1 :         ParticleState p;
-     401           1 :         p.setId(nucleusId(1, 1));
-     402           1 :         p.setEnergy(100 * EeV);
-     403           1 :         p.setPosition(Vector3d(0, 0, 0));
-     404           1 :         p.setDirection(Vector3d(0, 1, 0));
-     405           1 :         Candidate c(p);
-     406             : 
-     407             :         // each step the step size can be increased by a factor of 5.
-     408           6 :         for (int i = 1; i < 6; i++){
-     409           5 :                 propa.process(&c);
-     410           5 :                 EXPECT_DOUBLE_EQ(minStep*pow(5, i) / pc, c.getNextStep()/pc);
-     411             :         }
-     412             :         // after 5 steps the maxStep is reached. The current step is, however, less.
-     413           1 :         EXPECT_DOUBLE_EQ(maxStep/pc/5., c.getCurrentStep()/pc);
-     414           1 :         EXPECT_DOUBLE_EQ(maxStep/pc, c.getNextStep()/pc);
-     415           1 : }
-     416             : 
-     417             : 
-     418           1 : TEST(testPropagationBP, proton) {
-     419           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     420             : 
-     421             :         double step = 0.01 * kpc;
-     422           1 :         propa.setMinimumStep(step);
-     423           1 :         propa.setMaximumStep(10*step);
-     424           1 :         propa.setTolerance(0.00001);
-     425             : 
-     426           1 :         ParticleState p;
-     427           1 :         p.setId(nucleusId(1, 1));
-     428           1 :         p.setEnergy(100 * EeV);
-     429           1 :         p.setPosition(Vector3d(0, 0, 0));
-     430           1 :         p.setDirection(Vector3d(0, 1, 0));
-     431           1 :         Candidate c(p);
-     432           1 :         c.setNextStep(0);
-     433             : 
-     434           1 :         propa.process(&c);
-     435             : 
-     436           1 :         EXPECT_DOUBLE_EQ(step, c.getCurrentStep());  // perform step
-     437           1 :         EXPECT_DOUBLE_EQ(5 * step, c.getNextStep());  // acceleration by factor 5
-     438           1 : }
-     439             : 
-     440             : 
-     441             : // Test the numerical results for parallel magnetic field lines along the z-axis
-     442           1 : TEST(testPropagationBP, gyration) {
-     443           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     444             : 
-     445             :         double step = 10. * Mpc;  // gyroradius is 108.1 Mpc
-     446           1 :         propa.setMaximumStep(step);
-     447           1 :         propa.setMinimumStep(step);
-     448             : 
-     449             : 
-     450           1 :         ParticleState p;
-     451           1 :         p.setId(nucleusId(1, 1));
-     452           1 :         p.setEnergy(100 * EeV);
-     453           1 :         p.setPosition(Vector3d(0, 0, 0));
-     454           1 :         p.setDirection(Vector3d(1, 1, 1));
-     455           1 :         Candidate c(p);
-     456           1 :         c.setNextStep(0);
-     457           1 :         propa.process(&c);
-     458             : 
-     459           1 :         double dirX = c.current.getDirection().x;
-     460           1 :         double dirY = c.current.getDirection().y;
-     461           1 :         double dirZ = c.current.getDirection().z;
-     462           1 :         double posZ = c.current.getPosition().z;
-     463             : 
-     464             :         // Test if the analytical solution is achieved for the components of the momentum with the Boris push as expected in
-     465             :         // the background magnetic field.
-     466           1 :         EXPECT_DOUBLE_EQ(2 / 3., dirX * dirX + dirY * dirY);  // constant momentum in the perpendicular plane to background magnetic field field
-     467           1 :         EXPECT_DOUBLE_EQ(1 / 3., dirZ * dirZ);  // constant momentum parallel to the background magnetic field
-     468           1 :         EXPECT_DOUBLE_EQ( step * step / 3., posZ * posZ);  // constant velocity parallel to the background magnetic field
-     469             : 
-     470             :         // Nine new steps to have finally propagated the particle ten times
-     471          10 :         for (int i = 0; i < 9; i++){
-     472           9 :                 propa.process(&c);
-     473             :         }
-     474             : 
-     475           1 :         dirX = c.current.getDirection().x;
-     476           1 :         dirY = c.current.getDirection().y;
-     477           1 :         dirZ = c.current.getDirection().z;
-     478           1 :         posZ = c.current.getPosition().z;
-     479             : 
-     480             :         // Compare the numerical solutions after ten steps with the analytical solution of the trajectories
-     481           1 :         EXPECT_DOUBLE_EQ(2 / 3., dirX * dirX + dirY * dirY);  // constant momentum in the perpendicular plane to background magnetic field field
-     482           1 :         EXPECT_DOUBLE_EQ(1 / 3., dirZ * dirZ);  // constant momentum parallel to the background magnetic field
-     483           1 :         EXPECT_DOUBLE_EQ(100 * step * step / 3., posZ * posZ);  // constant velocity parallel to the background magnetic field
-     484           1 : }
-     485             : 
-     486             : 
-     487             : // Test the that the optimization for fixed step sizes works
-     488           1 : TEST(testPropagationBP, fixedStepOptimization) {
-     489             :         // particle 1 with fixed step sizes
-     490             :         double fixed_step = pc;
-     491           2 :         PropagationBP propa1(new PlaneWaveTurbulence(TurbulenceSpectrum(gauss, pc, 100*pc), 10, 1), fixed_step);
-     492           1 :         ParticleState p1;
-     493           1 :         p1.setId(nucleusId(1, 1));
-     494           1 :         p1.setEnergy(100 * EeV);
-     495           1 :         p1.setPosition(Vector3d(0, 0, 0));
-     496           1 :         p1.setDirection(Vector3d(1, 1, 1));
-     497           1 :         Candidate c1(p1);
-     498           1 :         c1.setNextStep(0);
-     499             :         // Nine new steps to have finally propagated the particle ten times
-     500          10 :         for (int i = 0; i < 9; i++){
-     501           9 :                 propa1.process(&c1);
-     502             :         }
-     503             : 
-     504             :         // particle 2 with different min and max steps. The tolerance is chosen such that particle 2 will be
-     505             :         // propagated with the same step as particle 1, however not using the optimization for fixed step sizes
-     506             :         double tolerance = 1;
-     507           2 :         PropagationBP propa2(new PlaneWaveTurbulence(TurbulenceSpectrum(gauss, pc, 100*pc), 10, 1), tolerance, fixed_step, 1.1*fixed_step);
-     508           1 :         ParticleState p2;
-     509           1 :         p2.setId(nucleusId(1, 1));
-     510           1 :         p2.setEnergy(100 * EeV);
-     511           1 :         p2.setPosition(Vector3d(0, 0, 0));
-     512           1 :         p2.setDirection(Vector3d(1, 1, 1));
-     513           1 :         Candidate c2(p2);
-     514           1 :         c1.setNextStep(0);
-     515             :         // Nine new steps to have finally propagated the particle ten times
-     516          10 :         for (int i = 0; i < 9; i++){
-     517           9 :                 propa2.process(&c2);
-     518             :         }
-     519             : 
-     520           1 :         EXPECT_DOUBLE_EQ(c1.current.getDirection().x, c2.current.getDirection().x);
-     521           1 :         EXPECT_DOUBLE_EQ(c1.current.getDirection().y, c2.current.getDirection().y);
-     522           1 :         EXPECT_DOUBLE_EQ(c1.current.getDirection().z, c2.current.getDirection().z);
-     523           1 :         EXPECT_DOUBLE_EQ(c1.current.getPosition().x, c2.current.getPosition().x);
-     524           1 :         EXPECT_DOUBLE_EQ(c1.current.getPosition().y, c2.current.getPosition().y);
-     525           1 :         EXPECT_DOUBLE_EQ(c1.current.getPosition().z, c2.current.getPosition().z);
-     526           1 : }
-     527             : 
-     528             : 
-     529           1 : TEST(testPropagationBP, neutron) {
-     530           1 :         PropagationBP propa(new UniformMagneticField(Vector3d(0, 0, 1 * nG)));
-     531             : 
-     532           1 :         propa.setMinimumStep(1 * kpc);
-     533           1 :         propa.setMaximumStep(1 * kpc);
-     534             : 
-     535           1 :         ParticleState p;
-     536           1 :         p.setId(nucleusId(1, 0));
-     537           1 :         p.setEnergy(100 * EeV);
-     538           1 :         p.setPosition(Vector3d(0, 0, 0));
-     539           1 :         p.setDirection(Vector3d(0, 1, 0));
-     540           1 :         Candidate c(p);
-     541             : 
-     542           1 :         propa.process(&c);
-     543             : 
-     544           1 :         EXPECT_DOUBLE_EQ(1 * kpc, c.getCurrentStep());
-     545           1 :         EXPECT_DOUBLE_EQ(1 * kpc, c.getNextStep());
-     546           2 :         EXPECT_EQ(Vector3d(0, 1 * kpc, 0), c.current.getPosition());
-     547           2 :         EXPECT_EQ(Vector3d(0, 1, 0), c.current.getDirection());
-     548           1 : }
-     549             : 
-     550             : 
-     551           0 : int main(int argc, char **argv) {
-     552           0 :         ::testing::InitGoogleTest(&argc, argv);
-     553           0 :         return RUN_ALL_TESTS();
-     554             : }
-     555             : 
-     556             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testSource.cpp.func-sort-c.html b/doc/coverageReport/test/testSource.cpp.func-sort-c.html deleted file mode 100644 index d2aaccaf2..000000000 --- a/doc/coverageReport/test/testSource.cpp.func-sort-c.html +++ /dev/null @@ -1,168 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testSource.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testSource.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:27928398.6 %
Date:2024-04-08 14:58:22Functions:232495.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa24SourceList_noSource_Test8TestBodyEv1
_ZN7crpropa24SourceTag_sourceTag_Test8TestBodyEv1
_ZN7crpropa26SourceList_luminosity_Test8TestBodyEv1
_ZN7crpropa26SourceList_simpleTest_Test8TestBodyEv1
_ZN7crpropa29Source_allPropertiesUsed_Test8TestBodyEv1
_ZN7crpropa30SourcePosition_simpleTest_Test8TestBodyEv1
_ZN7crpropa32SourceUniformBox_simpleTest_Test8TestBodyEv1
_ZN7crpropa33SourceComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa34SourceDensityGrid_withInRange_Test8TestBodyEv1
_ZN7crpropa34SourceEmissionCone_simpleTest_Test8TestBodyEv1
_ZN7crpropa35SourceUniformSphere_simpleTest_Test8TestBodyEv1
_ZN7crpropa36SourceDensityGrid1D_withInRange_Test8TestBodyEv1
_ZN7crpropa37SourceComposition_throwNoIsotope_Test8TestBodyEv1
_ZN7crpropa37SourceDensityGrid_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa37SourceSNRDistribution_simpleTest_Test8TestBodyEv1
_ZN7crpropa37SourceUniformCylinder_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourceDirectedEmission_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourcePowerLawSpectrum_simpleTest_Test8TestBodyEv1
_ZN7crpropa39SourceDensityGrid1D_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa39SourceMultiplePositions_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceGenericComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceRedshiftEvolution_testInRange_Test8TestBodyEv1
_ZN7crpropa41SourceUniformHollowSphere_simpleTest_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testSource.cpp.func.html b/doc/coverageReport/test/testSource.cpp.func.html deleted file mode 100644 index 03ae49b49..000000000 --- a/doc/coverageReport/test/testSource.cpp.func.html +++ /dev/null @@ -1,168 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testSource.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testSource.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:27928398.6 %
Date:2024-04-08 14:58:22Functions:232495.8 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa24SourceList_noSource_Test8TestBodyEv1
_ZN7crpropa24SourceTag_sourceTag_Test8TestBodyEv1
_ZN7crpropa26SourceList_luminosity_Test8TestBodyEv1
_ZN7crpropa26SourceList_simpleTest_Test8TestBodyEv1
_ZN7crpropa29Source_allPropertiesUsed_Test8TestBodyEv1
_ZN7crpropa30SourcePosition_simpleTest_Test8TestBodyEv1
_ZN7crpropa32SourceUniformBox_simpleTest_Test8TestBodyEv1
_ZN7crpropa33SourceComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa34SourceDensityGrid_withInRange_Test8TestBodyEv1
_ZN7crpropa34SourceEmissionCone_simpleTest_Test8TestBodyEv1
_ZN7crpropa35SourceUniformSphere_simpleTest_Test8TestBodyEv1
_ZN7crpropa36SourceDensityGrid1D_withInRange_Test8TestBodyEv1
_ZN7crpropa37SourceComposition_throwNoIsotope_Test8TestBodyEv1
_ZN7crpropa37SourceDensityGrid_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa37SourceSNRDistribution_simpleTest_Test8TestBodyEv1
_ZN7crpropa37SourceUniformCylinder_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourceDirectedEmission_simpleTest_Test8TestBodyEv1
_ZN7crpropa38SourcePowerLawSpectrum_simpleTest_Test8TestBodyEv1
_ZN7crpropa39SourceDensityGrid1D_OneAllowedCell_Test8TestBodyEv1
_ZN7crpropa39SourceMultiplePositions_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceGenericComposition_simpleTest_Test8TestBodyEv1
_ZN7crpropa40SourceRedshiftEvolution_testInRange_Test8TestBodyEv1
_ZN7crpropa41SourceUniformHollowSphere_simpleTest_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testSource.cpp.gcov.html b/doc/coverageReport/test/testSource.cpp.gcov.html deleted file mode 100644 index 5c0300eea..000000000 --- a/doc/coverageReport/test/testSource.cpp.gcov.html +++ /dev/null @@ -1,516 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testSource.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testSource.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:27928398.6 %
Date:2024-04-08 14:58:22Functions:232495.8 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Source.h"
-       2             : #include "crpropa/Units.h"
-       3             : #include "crpropa/ParticleID.h"
-       4             : 
-       5             : #include "gtest/gtest.h"
-       6             : #include <stdexcept>
-       7             : 
-       8             : namespace crpropa {
-       9             : 
-      10           2 : TEST(SourcePosition, simpleTest) {
-      11             :         Vector3d position(1, 2, 3);
-      12           1 :         SourcePosition source(position);
-      13           1 :         ParticleState ps;
-      14           1 :         source.prepareParticle(ps);
-      15           2 :         EXPECT_EQ(position, ps.getPosition());
-      16           1 : }
-      17             : 
-      18           1 : TEST(SourceMultiplePositions, simpleTest) {
-      19           1 :         SourceMultiplePositions source;
-      20           1 :         source.add(Vector3d(1, 0, 0), 0.25);
-      21           1 :         source.add(Vector3d(2, 0, 0), 0.75);
-      22           1 :         ParticleState ps;
-      23             :         int n1 = 0;
-      24             :         int n2 = 0;
-      25       10001 :         for (int i = 0; i < 10000; i++) {
-      26       10000 :                 source.prepareParticle(ps);
-      27       10000 :                 if (ps.getPosition().x == 1)
-      28        2585 :                         n1++;
-      29        7415 :                 else if (ps.getPosition().x == 2)
-      30        7415 :                         n2++;
-      31             :         }
-      32           1 :         EXPECT_NEAR(n1, 2500, 5 * sqrt(2500));
-      33           1 :         EXPECT_NEAR(n2, 7500, 5 * sqrt(7500));
-      34           1 : }
-      35             : 
-      36           2 : TEST(SourceUniformSphere, simpleTest) {
-      37             :         Vector3d center(0, 0, 0);
-      38           1 :         double radius = 110;
-      39           1 :         SourceUniformSphere source(center, radius);
-      40           1 :         ParticleState ps;
-      41           1 :         source.prepareParticle(ps);
-      42           1 :         double distance = ps.getPosition().getDistanceTo(center);
-      43           1 :         EXPECT_GE(radius, distance);
-      44           1 : }
-      45             : 
-      46           2 : TEST(SourceUniformHollowSphere, simpleTest) {
-      47             :         Vector3d center(0, 0, 0);
-      48           1 :         double radius_inner = 50;
-      49           1 :         double radius_outer = 110;
-      50             :         SourceUniformHollowSphere source(center,
-      51             :                         radius_inner,
-      52           1 :                         radius_outer);
-      53         101 :         for (int i=0; i < 100; ++i) {
-      54         100 :                 ParticleState ps;
-      55         100 :                 source.prepareParticle(ps);
-      56         100 :                 double distance = ps.getPosition().getDistanceTo(center);
-      57         100 :                 EXPECT_GE(radius_outer, distance);
-      58         100 :                 EXPECT_LE(radius_inner, distance);
-      59             :         }
-      60           1 : }
-      61             : 
-      62           2 : TEST(SourceUniformBox, simpleTest) {
-      63             :         Vector3d origin(-7, -2, 0);
-      64             :         Vector3d size(13, 55, 192);
-      65           1 :         SourceUniformBox box(origin, size);
-      66           1 :         ParticleState p;
-      67           1 :         box.prepareParticle(p);
-      68           1 :         Vector3d pos = p.getPosition();
-      69           1 :         EXPECT_LE(origin.x, pos.x);
-      70           1 :         EXPECT_LE(origin.y, pos.y);
-      71           1 :         EXPECT_LE(origin.z, pos.z);
-      72           1 :         EXPECT_GE(size.x, pos.x);
-      73           1 :         EXPECT_GE(size.y, pos.y);
-      74           1 :         EXPECT_GE(size.z, pos.z);
-      75           1 : }
-      76             : 
-      77           2 : TEST(SourceUniformCylinder, simpleTest) {
-      78             :         Vector3d center(0, 0, 0);
-      79             :         double radius = 15;
-      80             :         double height = 2;
-      81           1 :         SourceUniformCylinder cylinder(center, height, radius);
-      82           1 :         ParticleState ps;
-      83           1 :         cylinder.prepareParticle(ps);
-      84           1 :         Vector3d pos = ps.getPosition();
-      85           1 :         double R2 = pos.x*pos.x+pos.y*pos.y;
-      86           1 :         double H = pow(pos.z*pos.z, 0.5);
-      87           1 :         EXPECT_GE(radius*radius, R2);
-      88           1 :         EXPECT_GE(height/2., H);
-      89           1 : }
-      90             : 
-      91           1 : TEST(SourceSNRDistribution, simpleTest) {
-      92             :         double R_earth = 8.5*kpc;
-      93             :         double alpha = 2.0;
-      94             :         double beta = 3.53;
-      95             :         double Z_G = 0.3*kpc;
-      96           1 :         SourceSNRDistribution snr(R_earth,alpha, beta, Z_G);
-      97           1 :         ParticleState ps;
-      98           1 :         snr.prepareParticle(ps);
-      99           1 :         Vector3d pos = ps.getPosition();
-     100           1 :         double R2 = pos.x*pos.x+pos.y*pos.y;
-     101           1 :         EXPECT_GE(20*kpc*20*kpc, R2); // radius must be smaller than 20 kpc
-     102             :         
-     103             :         double R2_mean = 0.;
-     104             :         double Z_mean = 0.;
-     105      100001 :         for (size_t i=0; i<100000; i++) {
-     106      100000 :                 snr.prepareParticle(ps);
-     107      100000 :                 Vector3d pos = ps.getPosition();
-     108      100000 :                 R2_mean += pow(pos.x/kpc, 2.)+pow(pos.y/kpc, 2.);
-     109      100000 :                 Z_mean += pos.z/kpc;
-     110             :         }
-     111           1 :         R2_mean/=100000.;
-     112           1 :         Z_mean/=100000.;
-     113           1 :         EXPECT_NEAR(100.306, R2_mean, 1);
-     114           1 :         EXPECT_NEAR(0., Z_mean, 0.1);
-     115           1 : }
-     116             : 
-     117           2 : TEST(SourceDensityGrid, withInRange) {
-     118             :         // Create a grid with 10^3 cells ranging from (0, 0, 0) to (10, 10, 10)
-     119             :         Vector3d origin(0, 0, 0);
-     120             :         int cells = 10;
-     121             :         double spacing = 1;
-     122           1 :         auto grid = new Grid1f(origin, cells, spacing);
-     123          11 :         for (int ix = 0; ix < cells; ix++)
-     124         110 :                 for (int iy = 0; iy < cells; iy++)
-     125        1100 :                         for (int iz = 0; iz < cells; iz++)
-     126        1000 :                                 grid->get(ix, iy, iz) = ix * iy * iz;
-     127             : 
-     128           2 :         SourceDensityGrid source(grid);
-     129           1 :         ParticleState p;
-     130             : 
-     131           1 :         source.prepareParticle(p);
-     132           1 :         Vector3d pos = p.getPosition();
-     133             : 
-     134             :         // dialed positions should be within the volume (0, 0, 0) - (10, 10, 10)
-     135           1 :         EXPECT_LE(0, pos.x);
-     136           1 :         EXPECT_GE(10, pos.x);
-     137           1 :         EXPECT_LE(0, pos.y);
-     138           1 :         EXPECT_GE(10, pos.y);
-     139           1 :         EXPECT_LE(0, pos.z);
-     140           1 :         EXPECT_GE(10, pos.z);
-     141           1 : }
-     142             : 
-     143           2 : TEST(SourceDensityGrid, OneAllowedCell) {
-     144             :         // Create a grid with 2^3 cells ranging from (0, 0, 0) to (4, 4, 4)
-     145             :         Vector3d origin(0, 0, 0);
-     146             :         int cells = 2;
-     147             :         double spacing = 2;
-     148           1 :         auto grid = new Grid1f(origin, cells, spacing);
-     149             :         
-     150             :         // set all but one cells to 0
-     151           3 :         for (int ix = 0; ix < cells; ix++)
-     152           6 :                 for (int iy = 0; iy < cells; iy++)
-     153          12 :                         for (int iz = 0; iz < cells; iz++)
-     154           8 :                                 grid->get(ix, iy, iz) = 0;
-     155             : 
-     156             :         // set the first cell ((0, 0, 0) to (2, 2, 2))
-     157           1 :         grid->get(0, 0, 0) = 1;
-     158             : 
-     159           2 :         SourceDensityGrid source(grid);
-     160           1 :         ParticleState p;
-     161             : 
-     162           1 :         int nFalse = 0;
-     163             :         Vector3d mean(0, 0, 0);
-     164       10001 :         for (int i = 0; i < 10000; i++) {
-     165       10000 :                 source.prepareParticle(p);
-     166       10000 :                 Vector3d pos = p.getPosition();
-     167             :                 mean += pos;
-     168       10000 :                 if ((pos.x < 0) or (pos.x > 2) or (pos.y < 0) or (pos.y > 2)
-     169       10000 :                                 or (pos.z < 0) or (pos.z > 2))
-     170           0 :                         nFalse++;
-     171             :         }
-     172             : 
-     173             :         // only the first bin should get dialed
-     174           1 :         EXPECT_EQ(0, nFalse);
-     175             : 
-     176             :         // mean should be close to (1, 1, 1) if random positions are uniform in (0, 0, 0) - (2, 2, 2)
-     177             :         mean /= 10000;
-     178           1 :         EXPECT_NEAR(1, mean.x, 0.2);
-     179           1 :         EXPECT_NEAR(1, mean.y, 0.2);
-     180           1 :         EXPECT_NEAR(1, mean.z, 0.2);
-     181           1 : }
-     182             : 
-     183           2 : TEST(SourceDensityGrid1D, withInRange) {
-     184             :         // Create a grid with 10 cells ranging from 0 to 10
-     185             :         Vector3d origin(0, 0, 0);
-     186             :         int nCells = 10;
-     187             :         double spacing = 1.;
-     188           1 :         auto grid = new Grid1f(origin, nCells, 1, 1, spacing);
-     189             : 
-     190             :         // set some values
-     191          11 :         for (int i = 0; i < 10; i++) {
-     192          10 :                 grid->get(i, 0, 0) = 2;
-     193             :         }
-     194             : 
-     195           2 :         SourceDensityGrid1D source(grid);
-     196           1 :         ParticleState p;
-     197             : 
-     198           1 :         source.prepareParticle(p);
-     199           1 :         Vector3d pos = p.getPosition();
-     200             :         // dialed position should be within the range 0 - 10
-     201           1 :         EXPECT_LE(0, pos.x);
-     202           1 :         EXPECT_GE(10, pos.x);
-     203           1 : }
-     204             : 
-     205           2 : TEST(SourceDensityGrid1D, OneAllowedCell) {
-     206             :         // Test if the only allowed cells is repeatedly selected
-     207             :         Vector3d origin(0, 0, 0);
-     208             :         int nCells = 10;
-     209             :         double spacing = 1.;
-     210           1 :         auto grid = new Grid1f(origin, nCells, 1, 1, spacing);
-     211             : 
-     212             :         // set some values
-     213          11 :         for (int i = 0; i < 10; i++) {
-     214          10 :                 grid->get(i, 0, 0) = 0;
-     215             :         }
-     216           1 :         grid->get(5, 0, 0) = 1;
-     217             : 
-     218           2 :         SourceDensityGrid1D source(grid);
-     219           1 :         ParticleState p;
-     220             : 
-     221         101 :         for (int i = 0; i < 100; i++) {
-     222         100 :                 source.prepareParticle(p);
-     223             :                 // dialed position should be in range 5-6
-     224         100 :                 Vector3d pos = p.getPosition();
-     225         100 :                 EXPECT_LE(5, pos.x);
-     226         100 :                 EXPECT_GE(6, pos.x);
-     227             :         }
-     228           1 : }
-     229             : 
-     230           1 : TEST(SourcePowerLawSpectrum, simpleTest) {
-     231           1 :         double Emin = 4 * EeV;
-     232           1 :         double Emax = 200 * EeV;
-     233             :         double index = -2.7;
-     234           1 :         SourcePowerLawSpectrum spectrum(Emin, Emax, index);
-     235           1 :         ParticleState ps;
-     236           1 :         spectrum.prepareParticle(ps);
-     237             : 
-     238             :         // energy should be within Emin - Emax
-     239           1 :         EXPECT_LE(Emin, ps.getEnergy());
-     240           1 :         EXPECT_GE(Emax, ps.getEnergy());
-     241           1 : }
-     242             : 
-     243           1 : TEST(SourceComposition, simpleTest) {
-     244           1 :         double Emin = 10;
-     245             :         double Rmax = 100;
-     246             :         double index = -1;
-     247           1 :         SourceComposition source(Emin, Rmax, index);
-     248           1 :         source.add(nucleusId(6, 3), 1);
-     249           1 :         ParticleState p;
-     250           1 :         source.prepareParticle(p);
-     251           1 :         EXPECT_EQ(nucleusId(6, 3), p.getId());
-     252           1 :         EXPECT_LE(Emin, p.getEnergy());
-     253           1 :         EXPECT_GE(6 * Rmax, p.getEnergy());
-     254           1 : }
-     255             : 
-     256           2 : TEST(SourceDirectedEmission, simpleTest) {
-     257             :         Vector3d mu(1., 0., 0.);
-     258             :         double kappa = 1000.;
-     259           1 :         SourceDirectedEmission source(mu, kappa);
-     260           1 :         Candidate c;
-     261             :         Vector3d meanDir(0., 0., 0.);
-     262        1001 :         for (size_t i = 0; i < 1000; i++) {
-     263        1000 :                 source.prepareCandidate(c);
-     264        1000 :                 meanDir += c.source.getDirection();
-     265        1000 :                 double w = c.getWeight();
-     266        1000 :                 EXPECT_GE(w, 0.);
-     267             :         }
-     268             :         meanDir /= 1000.;
-     269           1 :         EXPECT_NEAR(meanDir.x, 1., 0.1);
-     270           1 :         EXPECT_NEAR(meanDir.y, 0., 0.01);
-     271           1 :         EXPECT_NEAR(meanDir.z, 0., 0.01);
-     272           2 : }
-     273             : 
-     274           2 : TEST(SourceEmissionCone, simpleTest) {
-     275             :         Vector3d direction(42., 0., 0.);
-     276           1 :         double aperture = 1/42.;
-     277             :         
-     278           1 :         SourceEmissionCone source(direction, aperture);
-     279             :         
-     280           1 :         ParticleState p;
-     281           1 :         source.prepareParticle(p);
-     282           1 :         double angle = direction.getAngleTo(p.getDirection());
-     283           1 :         EXPECT_LE(angle, aperture);
-     284           1 : }
-     285             : 
-     286             : #ifdef CRPROPA_HAVE_MUPARSER
-     287           1 : TEST(SourceGenericComposition, simpleTest) {
-     288             :         double Emin = 10;
-     289             :         double Emax = 100;
-     290           1 :         SourceGenericComposition source(Emin, Emax, "E^-2");
-     291           1 :         int id1 = nucleusId(6, 3);
-     292           1 :         int id2 = nucleusId(12, 6);
-     293           1 :         source.add(id1, 1);
-     294           1 :         source.add(id2, 10);
-     295           1 :         ParticleState p;
-     296             :         size_t id1Count = 0, id2Count = 0;
-     297             :         size_t ElowCount = 0, EhighCount = 0;
-     298           1 :         size_t n = 100000;
-     299      100001 :         for (size_t i = 0; i < n; i++) {
-     300      100000 :                 source.prepareParticle(p);
-     301      100000 :                 if (p.getId() == id1)
-     302        8964 :                         id1Count++;
-     303      100000 :                 if (p.getId() == id2)
-     304       91036 :                         id2Count++;
-     305      100000 :                 double e = p.getEnergy();
-     306      100000 :                 if ( (e >= Emin) && (e < 20))
-     307       55702 :                         ElowCount++;
-     308      100000 :                 if ( (e >= 20) && (e <= Emax))
-     309       44298 :                         EhighCount++;
-     310             : 
-     311             :         }
-     312           1 :         EXPECT_EQ(n, id1Count + id2Count);
-     313           1 :         EXPECT_EQ(n, ElowCount + EhighCount);
-     314           1 :         EXPECT_NEAR((float)id1Count/(float)id2Count, 0.1, 0.01);
-     315           1 :         EXPECT_NEAR((float)ElowCount/(float)EhighCount, 1.25, 0.1);
-     316           1 : }
-     317             : #endif
-     318             : 
-     319           1 : TEST(SourceComposition, throwNoIsotope) {
-     320           1 :         SourceComposition source(1, 10, -1);
-     321           1 :         ParticleState ps;
-     322           1 :         EXPECT_THROW(source.prepareParticle(ps), std::runtime_error);
-     323           1 : }
-     324             : 
-     325           1 : TEST(SourceRedshiftEvolution, testInRange) {
-     326           1 :         Candidate c;
-     327             : 
-     328           1 :         double zmin = 0.5;
-     329           1 :         double zmax = 2.5;
-     330             : 
-     331             :         // general case: m
-     332           1 :         SourceRedshiftEvolution source1(3.2, zmin, zmax);
-     333         101 :         for (int i = 0; i < 100; i++) {
-     334         100 :                 source1.prepareCandidate(c);
-     335         100 :                 EXPECT_LE(zmin, c.getRedshift());
-     336         100 :                 EXPECT_GE(zmax, c.getRedshift());
-     337             :         }
-     338             : 
-     339             :         // general case: m = -1
-     340           1 :         SourceRedshiftEvolution source2(-1, zmin, zmax);
-     341         101 :         for (int i = 0; i < 100; i++) {
-     342         100 :                 source2.prepareCandidate(c);
-     343         100 :                 EXPECT_LE(zmin, c.getRedshift());
-     344         100 :                 EXPECT_GE(zmax, c.getRedshift());
-     345             :         }
-     346           1 : }
-     347             : 
-     348           2 : TEST(Source, allPropertiesUsed) {
-     349             :         Source source;
-     350           1 :         source.add(new SourcePosition(Vector3d(10, 0, 0) * Mpc));
-     351           2 :         source.add(new SourceIsotropicEmission());
-     352           1 :         source.add(new SourcePowerLawSpectrum(5 * EeV, 100 * EeV, -2));
-     353           1 :         source.add(new SourceParticleType(nucleusId(8, 4)));
-     354           1 :         source.add(new SourceRedshift(2));
-     355             : 
-     356           1 :         Candidate c = *source.getCandidate();
-     357             : 
-     358           1 :         EXPECT_EQ(2, c.getRedshift());
-     359             : 
-     360           1 :         ParticleState p;
-     361             : 
-     362             :         p = c.source;
-     363           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
-     364           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
-     365           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
-     366           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
-     367             : 
-     368             :         p = c.created;
-     369           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
-     370           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
-     371           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
-     372           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
-     373             : 
-     374             :         p = c.previous;
-     375           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
-     376           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
-     377           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
-     378           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
-     379             : 
-     380             :         p = c.current;
-     381           1 :         EXPECT_EQ(nucleusId(8, 4), p.getId());
-     382           1 :         EXPECT_LE(5 * EeV, p.getEnergy());
-     383           1 :         EXPECT_GE(100 * EeV, p.getEnergy());
-     384           2 :         EXPECT_EQ(Vector3d(10, 0, 0) * Mpc, p.getPosition());
-     385           2 : }
-     386             : 
-     387           2 : TEST(SourceList, simpleTest) {
-     388             :         // test if source list works with one source
-     389             :         SourceList sourceList;
-     390           1 :         ref_ptr<Source> source = new Source;
-     391           1 :         source->add(new SourcePosition(Vector3d(10, 0, 0)));
-     392           1 :         sourceList.add(source);
-     393             : 
-     394           1 :         ref_ptr<Candidate> c = sourceList.getCandidate();
-     395             : 
-     396           2 :         EXPECT_EQ(Vector3d(10, 0, 0), c->created.getPosition());
-     397           2 :         EXPECT_EQ(Vector3d(10, 0, 0), c->previous.getPosition());
-     398           2 :         EXPECT_EQ(Vector3d(10, 0, 0), c->current.getPosition());
-     399           1 : }
-     400             : 
-     401           2 : TEST(SourceList, noSource) {
-     402             :         // test if an error is thrown when source list empty
-     403             :         SourceList sourceList;
-     404           1 :         EXPECT_THROW(sourceList.getCandidate(), std::runtime_error);
-     405           1 : }
-     406             : 
-     407           2 : TEST(SourceList, luminosity) {
-     408             :         // test if the sources are dialed according to their luminosities
-     409             :         SourceList sourceList;
-     410             : 
-     411           1 :         ref_ptr<Source> source1 = new Source;
-     412           1 :         source1->add(new SourceEnergy(100));
-     413           1 :         sourceList.add(source1, 80);
-     414             : 
-     415           1 :         ref_ptr<Source> source2 = new Source;
-     416           1 :         source2->add(new SourceEnergy(0));
-     417           1 :         sourceList.add(source2, 20);
-     418             : 
-     419             :         double meanE = 0;
-     420        1001 :         for (int i = 0; i < 1000; i++) {
-     421        1000 :                 ref_ptr<Candidate> c = sourceList.getCandidate();
-     422        1000 :                 meanE += c->created.getEnergy();
-     423             :         }
-     424           1 :         meanE /= 1000;
-     425           1 :         EXPECT_NEAR(80, meanE, 4); // this test can stochastically fail
-     426           1 : }
-     427             : 
-     428           1 : TEST(SourceTag, sourceTag) {
-     429           1 :         SourceTag tag("mySourceTag");
-     430           1 :         Candidate c;
-     431           1 :         tag.prepareCandidate(c);
-     432           2 :         EXPECT_TRUE(c.getTagOrigin() == "mySourceTag");
-     433           1 : }
-     434             : 
-     435           0 : int main(int argc, char **argv) {
-     436           0 :         ::testing::InitGoogleTest(&argc, argv);
-     437           0 :         return RUN_ALL_TESTS();
-     438             : }
-     439             : 
-     440             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html b/doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html deleted file mode 100644 index f9a2c170f..000000000 --- a/doc/coverageReport/test/testTurbulentField.cpp.func-sort-c.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testTurbulentField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testTurbulentField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4646100.0 %
Date:2024-04-08 14:58:22Functions:88100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN39testGridTurbulence_Turbulence_seed_Test8TestBodyEv1
_ZN39testTurbulenceSpectrum_constructor_Test8TestBodyEv1
_ZN40testVectorFieldGrid_Turbulence_seed_Test8TestBodyEv1
_ZN45testTurbulenceSpectrum_correlationLength_Test8TestBodyEv1
_ZN46testVectorFieldGrid_Turbulence_bmean_brms_Test8TestBodyEv1
_ZN46testVectorFieldGrid_turbulence_Exceptions_Test8TestBodyEv1
_ZN60testSimpleGridTurbulence_oldFunctionForCrrelationLength_Test8TestBodyEv1
main1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testTurbulentField.cpp.func.html b/doc/coverageReport/test/testTurbulentField.cpp.func.html deleted file mode 100644 index 4a96c6309..000000000 --- a/doc/coverageReport/test/testTurbulentField.cpp.func.html +++ /dev/null @@ -1,104 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testTurbulentField.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testTurbulentField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4646100.0 %
Date:2024-04-08 14:58:22Functions:88100.0 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN39testGridTurbulence_Turbulence_seed_Test8TestBodyEv1
_ZN39testTurbulenceSpectrum_constructor_Test8TestBodyEv1
_ZN40testVectorFieldGrid_Turbulence_seed_Test8TestBodyEv1
_ZN45testTurbulenceSpectrum_correlationLength_Test8TestBodyEv1
_ZN46testVectorFieldGrid_Turbulence_bmean_brms_Test8TestBodyEv1
_ZN46testVectorFieldGrid_turbulence_Exceptions_Test8TestBodyEv1
_ZN60testSimpleGridTurbulence_oldFunctionForCrrelationLength_Test8TestBodyEv1
main1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testTurbulentField.cpp.gcov.html b/doc/coverageReport/test/testTurbulentField.cpp.gcov.html deleted file mode 100644 index 642a3acef..000000000 --- a/doc/coverageReport/test/testTurbulentField.cpp.gcov.html +++ /dev/null @@ -1,218 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testTurbulentField.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testTurbulentField.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:4646100.0 %
Date:2024-04-08 14:58:22Functions:88100.0 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include <stdexcept>
-       2             : 
-       3             : #include "crpropa/Grid.h"
-       4             : #include "crpropa/Units.h"
-       5             : #include "crpropa/Common.h"
-       6             : #include "crpropa/GridTools.h"
-       7             : #include "crpropa/magneticField/turbulentField/TurbulentField.h"
-       8             : #include "crpropa/magneticField/turbulentField/GridTurbulence.h"
-       9             : #include "crpropa/magneticField/turbulentField/PlaneWaveTurbulence.h"
-      10             : #include "crpropa/magneticField/turbulentField/SimpleGridTurbulence.h"
-      11             : 
-      12             : #include "gtest/gtest.h"
-      13             : 
-      14             : using namespace crpropa;
-      15             : 
-      16             : //check problems brought up in https://github.com/CRPropa/CRPropa3/issues/322
-      17           1 : TEST(testTurbulenceSpectrum, constructor) {
-      18             :         double sIndex = 5./3.;
-      19             :         double qIndex = 4.;
-      20             :         double bendOver = 1.;
-      21             :         double lMin = 1.; 
-      22             :         double lMax = 10.; 
-      23             :         double brms = 1*muG;
-      24           1 :         auto spectrum = TurbulenceSpectrum(brms, lMin, lMax);
-      25           1 :         EXPECT_DOUBLE_EQ(spectrum.getBrms(), brms);
-      26           1 :         EXPECT_DOUBLE_EQ(spectrum.getLmin(), lMin);
-      27           1 :         EXPECT_DOUBLE_EQ(spectrum.getLmax(), lMax);
-      28           1 :         EXPECT_DOUBLE_EQ(spectrum.getLbendover(), bendOver); //default
-      29           1 :         EXPECT_DOUBLE_EQ(spectrum.getSindex(), sIndex); //default
-      30           1 :         EXPECT_DOUBLE_EQ(spectrum.getQindex(), qIndex); //default
-      31           1 : }
-      32             : 
-      33           1 : TEST(testTurbulenceSpectrum, correlationLength) {
-      34             :         double lMin = 0.00001; // not used for Lc
-      35             :         double lMax = 9999999; // not used for Lc
-      36             :         double lBo = 100;
-      37           1 :         auto spectrum = TurbulenceSpectrum(1*muG, lMin, lMax, lBo);
-      38             :         auto Lc = spectrum.getCorrelationLength();
-      39           1 :     EXPECT_NEAR(Lc, 0.498*lBo, 0.001*lBo);
-      40           1 : }
-      41             : 
-      42             : #ifdef CRPROPA_HAVE_FFTW3F
-      43             : 
-      44           1 : TEST(testSimpleGridTurbulence, oldFunctionForCrrelationLength) { //TODO: remove in future
-      45             :         double lMin = 1*kpc;
-      46             :         double lMax = 1*Gpc;
-      47             :         double alpha = -11/3.;
-      48           1 :         auto Lc = turbulentCorrelationLength(lMin, lMax, alpha);
-      49           1 :     EXPECT_NEAR(Lc, lMax/5, 1*Mpc);
-      50           1 : }
-      51             : 
-      52           2 : TEST(testVectorFieldGrid, Turbulence_bmean_brms) {
-      53             :         // Test for zero mean: <B> = 0
-      54             :         size_t n = 64;
-      55             :         double spacing = 10 * Mpc / n;
-      56             :         double Brms = 1;
-      57             :         double lMin = 2 * spacing;
-      58             :         double lMax = 8 * spacing;
-      59             : 
-      60             :         auto spectrum = SimpleTurbulenceSpectrum(Brms, lMin, lMax);
-      61             :         auto gp = GridProperties(Vector3d(0, 0, 0), n, spacing);
-      62           1 :     auto tf = SimpleGridTurbulence(spectrum, gp);
-      63           1 :         auto grid = tf.getGrid();
-      64             : 
-      65             :         double precision = 1e-7;
-      66           1 :         Vector3f bMean = meanFieldVector(grid);
-      67           1 :         EXPECT_NEAR(0, bMean.x, precision);
-      68           1 :         EXPECT_NEAR(0, bMean.y, precision);
-      69           1 :         EXPECT_NEAR(0, bMean.z, precision);
-      70           2 :         EXPECT_NEAR(1, rmsFieldStrength(grid), precision);
-      71           1 : }
-      72             : 
-      73           2 : TEST(testVectorFieldGrid, Turbulence_seed) {
-      74             :         // Test if seeding produces 2 identical fields
-      75             :         size_t n = 64;
-      76             :         double spacing = 1 * Mpc;
-      77             :         double Brms = 1;
-      78             :         double lMin = 2 * spacing;
-      79             :         double lMax = 8 * spacing;
-      80             :         int seed = 753;
-      81             :         
-      82             :         auto spectrum = SimpleTurbulenceSpectrum(Brms, lMin, lMax);
-      83             : 
-      84             :         auto gp1 = GridProperties(Vector3d(0, 0, 0), n, spacing);
-      85           1 :     auto tf1 = SimpleGridTurbulence(spectrum, gp1,  seed);
-      86             : 
-      87             :         auto gp2 = GridProperties(Vector3d(0, 0, 0), n, spacing);
-      88           1 :     auto tf2 = SimpleGridTurbulence(spectrum, gp2, seed);
-      89             : 
-      90             :         Vector3d pos(22 * Mpc);
-      91           1 :         EXPECT_FLOAT_EQ(tf1.getField(pos).x, tf2.getField(pos).x);
-      92           1 : }
-      93             : 
-      94             : #ifndef CRPROPA_TESTS_SKIP_EXCEPTIONS
-      95           2 : TEST(testVectorFieldGrid, turbulence_Exceptions) {
-      96             :         // Test exceptions
-      97             :         size_t n = 64;
-      98             :         double spacing = 10 * Mpc / n;
-      99             :         double brms = 1;
-     100           1 :         ref_ptr<Grid3f> grid = new Grid3f(Vector3d(0, 0, 0), n, spacing);
-     101             : 
-     102             :         // should be fine
-     103           2 :         EXPECT_NO_THROW(initTurbulence(grid, brms, 2 * spacing, 8 * spacing));
-     104             :         // lMin too small
-     105           2 :         EXPECT_THROW(initTurbulence(grid, brms, 1.5 * spacing, 8 * spacing),
-     106             :                         std::runtime_error);
-     107             :         // lMin > lMax
-     108           2 :         EXPECT_THROW(initTurbulence(grid, brms, 8.1 * spacing, 8 * spacing),
-     109             :                         std::runtime_error);
-     110             :         // lMax too large
-     111           2 :         EXPECT_THROW(initTurbulence(grid, brms, 2 * spacing, 65 * spacing),
-     112             :                         std::runtime_error);
-     113           1 : }
-     114             : #endif
-     115             : 
-     116           1 : TEST(testGridTurbulence, Turbulence_seed) {
-     117             :         // Test if seeding produces 2 identical fields
-     118             :         size_t n = 64;
-     119             :         double spacing = 1 * Mpc;
-     120             :         double Brms = 1;
-     121             :         double lMin = 2 * spacing;
-     122             :         double lMax = 8 * spacing;
-     123             :         double lBo = lMax/6;
-     124             :         int seed = 137;
-     125             :         
-     126           1 :         auto spectrum = TurbulenceSpectrum(Brms, lMin, lMax, lBo);
-     127             : 
-     128             :         auto gp1 = GridProperties(Vector3d(0, 0, 0), n, spacing);
-     129           1 :     auto tf1 = GridTurbulence(spectrum, gp1, seed);
-     130             : 
-     131             :         auto gp2 = GridProperties(Vector3d(0, 0, 0), n, spacing);
-     132           1 :     auto tf2 = GridTurbulence(spectrum, gp2, seed);
-     133             : 
-     134             :         Vector3d pos(22 * Mpc);
-     135           1 :         EXPECT_FLOAT_EQ(tf1.getField(pos).x, tf2.getField(pos).x);
-     136           1 : }
-     137             : #endif // CRPROPA_HAVE_FFTW3F
-     138             : 
-     139           1 : int main(int argc, char **argv) {
-     140           1 :         ::testing::InitGoogleTest(&argc, argv);
-     141             :         return RUN_ALL_TESTS();
-     142             : }
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testVector3.cpp.func-sort-c.html b/doc/coverageReport/test/testVector3.cpp.func-sort-c.html deleted file mode 100644 index b7177d48e..000000000 --- a/doc/coverageReport/test/testVector3.cpp.func-sort-c.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testVector3.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testVector3.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:909396.8 %
Date:2024-04-08 14:58:22Functions:121392.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa4mainEiPPc0
_ZN7crpropa16Vector3_dot_Test8TestBodyEv1
_ZN7crpropa16Vector3_mod_Test8TestBodyEv1
_ZN7crpropa18Vector3_angle_Test8TestBodyEv1
_ZN7crpropa18Vector3_cross_Test8TestBodyEv1
_ZN7crpropa21Vector3_distance_Test8TestBodyEv1
_ZN7crpropa21Vector3_division_Test8TestBodyEv1
_ZN7crpropa21Vector3_rotation_Test8TestBodyEv1
_ZN7crpropa22Vector3_magnitude_Test8TestBodyEv1
_ZN7crpropa23Vector3_comparison_Test8TestBodyEv1
_ZN7crpropa24Vector3_unitVectors_Test8TestBodyEv1
_ZN7crpropa27Vector3_multiplication_Test8TestBodyEv1
_ZN7crpropa34Vector3_parallelPerpendicular_Test8TestBodyEv1
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testVector3.cpp.func.html b/doc/coverageReport/test/testVector3.cpp.func.html deleted file mode 100644 index f79586ce3..000000000 --- a/doc/coverageReport/test/testVector3.cpp.func.html +++ /dev/null @@ -1,124 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testVector3.cpp - functions - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testVector3.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:909396.8 %
Date:2024-04-08 14:58:22Functions:121392.3 %
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -

Function Name Sort by function nameHit count Sort by hit count
_ZN7crpropa16Vector3_dot_Test8TestBodyEv1
_ZN7crpropa16Vector3_mod_Test8TestBodyEv1
_ZN7crpropa18Vector3_angle_Test8TestBodyEv1
_ZN7crpropa18Vector3_cross_Test8TestBodyEv1
_ZN7crpropa21Vector3_distance_Test8TestBodyEv1
_ZN7crpropa21Vector3_division_Test8TestBodyEv1
_ZN7crpropa21Vector3_rotation_Test8TestBodyEv1
_ZN7crpropa22Vector3_magnitude_Test8TestBodyEv1
_ZN7crpropa23Vector3_comparison_Test8TestBodyEv1
_ZN7crpropa24Vector3_unitVectors_Test8TestBodyEv1
_ZN7crpropa27Vector3_multiplication_Test8TestBodyEv1
_ZN7crpropa34Vector3_parallelPerpendicular_Test8TestBodyEv1
_ZN7crpropa4mainEiPPc0
-
-
- - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/test/testVector3.cpp.gcov.html b/doc/coverageReport/test/testVector3.cpp.gcov.html deleted file mode 100644 index a1e919522..000000000 --- a/doc/coverageReport/test/testVector3.cpp.gcov.html +++ /dev/null @@ -1,238 +0,0 @@ - - - - - - - LCOV - coverage.info.cleaned - test/testVector3.cpp - - - - - - - - - - - - - - -
LCOV - code coverage report
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Current view:top level - test - testVector3.cpp (source / functions)HitTotalCoverage
Test:coverage.info.cleanedLines:909396.8 %
Date:2024-04-08 14:58:22Functions:121392.3 %
-
- - - - - - - - -

-
          Line data    Source code
-
-       1             : #include "crpropa/Vector3.h"
-       2             : #include "gtest/gtest.h"
-       3             : 
-       4             : namespace crpropa {
-       5             : 
-       6           2 : TEST(Vector3, comparison) {
-       7             :         EXPECT_TRUE(Vector3d(1, 2, 3) == Vector3d(1, 2, 3));
-       8             :         EXPECT_FALSE(Vector3d(1, 2, 3) == Vector3d(2, 3, 4));
-       9           1 : }
-      10             : 
-      11           1 : TEST(Vector3, multiplication) {
-      12             :         Vector3d v(1);
-      13             :         v *= 10;
-      14           1 :         EXPECT_DOUBLE_EQ(v.x, 10);
-      15           1 :         EXPECT_DOUBLE_EQ(v.y, 10);
-      16           1 :         EXPECT_DOUBLE_EQ(v.z, 10);
-      17             :         v = Vector3d(1) * Vector3d(2); // element-wise multiplication
-      18           1 :         EXPECT_DOUBLE_EQ(v.x, 2);
-      19           1 :         EXPECT_DOUBLE_EQ(v.y, 2);
-      20           1 :         EXPECT_DOUBLE_EQ(v.z, 2);
-      21           1 : }
-      22             : 
-      23           1 : TEST(Vector3, division) {
-      24             :         Vector3d v(10);
-      25             :         v /= 10;
-      26           1 :         EXPECT_DOUBLE_EQ(v.x, 1);
-      27           1 :         EXPECT_DOUBLE_EQ(v.y, 1);
-      28           1 :         EXPECT_DOUBLE_EQ(v.z, 1);
-      29             :         v = Vector3d(10) / Vector3d(2); // element-wise division
-      30           1 :         EXPECT_DOUBLE_EQ(v.x, 5);
-      31           1 :         EXPECT_DOUBLE_EQ(v.y, 5);
-      32           1 :         EXPECT_DOUBLE_EQ(v.z, 5);
-      33           1 : }
-      34             : 
-      35           2 : TEST(Vector3, mod) {
-      36             :         Vector3d v(10.1, 10.2, 10.3);
-      37           1 :         v %= 10.2;
-      38           1 :         EXPECT_NEAR(v.x, 10.1, 1e-10); // mod doesn't preserve double precision
-      39           1 :         EXPECT_NEAR(v.y, 0, 1e-10);
-      40           1 :         EXPECT_NEAR(v.z, 0.1, 1e-10);
-      41           1 : }
-      42             : 
-      43           1 : TEST(Vector3, dot) {
-      44             :         double a = Vector3d(1, 0, 0).dot(Vector3d(0, 1, 0));
-      45           1 :         EXPECT_DOUBLE_EQ(a, 0);
-      46             :         double b = Vector3d(-1, 10, 2).dot(Vector3d(5, 1, -3));
-      47           1 :         EXPECT_DOUBLE_EQ(b, -1);
-      48           1 : }
-      49             : 
-      50           2 : TEST(Vector3, cross) {
-      51             :         Vector3d v = Vector3d(1, 0, 0).cross(Vector3d(0, 1, 0));
-      52             :         EXPECT_TRUE(v == Vector3d(0, 0, 1));
-      53           1 : }
-      54             : 
-      55           2 : TEST(Vector3, angle) {
-      56             :         // 45 degrees
-      57           1 :         double a = Vector3d(1, 1, 0).getAngleTo(Vector3d(1, 0, 0));
-      58           1 :         EXPECT_DOUBLE_EQ(a, 45 * M_PI / 180);
-      59             :         // perpendicular vectors
-      60           1 :         double b = Vector3d(0, 0, 1).getAngleTo(Vector3d(0, 0, 1));
-      61           1 :         EXPECT_DOUBLE_EQ(b, 0);
-      62           1 : }
-      63             : 
-      64           2 : TEST(Vector3, unitVectors) {
-      65             :         Vector3d v = Vector3d(2, 0, 0);
-      66           1 :         Vector3d er = v.getUnitVector();
-      67           1 :         Vector3d et = v.getUnitVectorTheta();
-      68           1 :         Vector3d ep = v.getUnitVectorPhi();
-      69             : 
-      70             :         // trigonometrical functions don't preserve double precision
-      71             :         double eps = 1e-16;
-      72           1 :         EXPECT_NEAR(er.x, 1, eps);
-      73           1 :         EXPECT_NEAR(er.y, 0, eps);
-      74           1 :         EXPECT_NEAR(er.z, 0, eps);
-      75             : 
-      76           1 :         EXPECT_NEAR(et.x, 0, eps);
-      77           1 :         EXPECT_NEAR(et.y, 0, eps);
-      78           1 :         EXPECT_NEAR(et.z, -1, eps);
-      79             : 
-      80           1 :         EXPECT_NEAR(ep.x, 0, eps);
-      81           1 :         EXPECT_NEAR(ep.y, 1, eps);
-      82           1 :         EXPECT_NEAR(ep.z, 0, eps);
-      83           1 : }
-      84             : 
-      85           1 : TEST(Vector3, magnitude) {
-      86             :         Vector3d v = Vector3d(1, 2, -2);
-      87           1 :         EXPECT_DOUBLE_EQ(v.getR(), 3);
-      88           1 :         EXPECT_DOUBLE_EQ(v.getR2(), 9);
-      89           1 : }
-      90             : 
-      91           2 : TEST(Vector3, distance) {
-      92           1 :         double a = Vector3d(10, 0, 10).getDistanceTo(Vector3d(10, 0, 0));
-      93           1 :         EXPECT_DOUBLE_EQ(a, 10);
-      94           1 : }
-      95             : 
-      96           2 : TEST(Vector3, rotation) {
-      97             :         Vector3d v, w;
-      98             : 
-      99             :         // rotation by 180 degrees
-     100             :         v = Vector3d(10, 0, 0);
-     101           1 :         w = v.getRotated(Vector3d(0, 2, 0), M_PI);
-     102           1 :         EXPECT_NEAR(w.x, -10, 1e-9);
-     103           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
-     104           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
-     105             : 
-     106             :         // rotation axis parallel to vector --> no rotation
-     107             :         v = Vector3d(10, 0, 0);
-     108           1 :         w = v.getRotated(Vector3d(1, 0, 0), M_PI);
-     109           1 :         EXPECT_NEAR(w.x, 10, 1e-9);
-     110           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
-     111           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
-     112             : 
-     113             :         // rotation by 360 degrees
-     114             :         v = Vector3d(5, 2, 7);
-     115           1 :         w = v.getRotated(Vector3d(1, 8, -4), 2 * M_PI);
-     116           1 :         EXPECT_NEAR(w.x, 5, 1e-9);
-     117           1 :         EXPECT_NEAR(w.y, 2, 1e-9);
-     118           1 :         EXPECT_NEAR(w.z, 7, 1e-9);
-     119             : 
-     120             :         // rotation by zero degrees
-     121             :         v = Vector3d(1, 0, 0);
-     122           1 :         w = v.getRotated(Vector3d(0,1,0), 0);
-     123             : 
-     124           1 :         EXPECT_NEAR(w.x, 1, 1e-9);
-     125           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
-     126           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
-     127             : 
-     128             :         // rotation around zero axis
-     129             :         v = Vector3d(1, 0, 0);
-     130             :         Vector3d a = v.cross(v);
-     131           1 :         w = v.getRotated(a, 0);
-     132             : 
-     133           1 :         EXPECT_NEAR(w.x, 1, 1e-9);
-     134           1 :         EXPECT_NEAR(w.y, 0, 1e-9);
-     135           1 :         EXPECT_NEAR(w.z, 0, 1e-9);
-     136             : 
-     137             : 
-     138             : 
-     139             : 
-     140           1 : }
-     141             : 
-     142           2 : TEST(Vector3, parallelPerpendicular) {
-     143             :         Vector3d v(3, 2, 1);
-     144             :         Vector3d w(0, 1, 0);
-     145             : 
-     146           1 :         Vector3d vpara = v.getParallelTo(w);
-     147           1 :         Vector3d vperp = v.getPerpendicularTo(w);
-     148             : 
-     149           1 :         EXPECT_DOUBLE_EQ(vpara.x, 0);
-     150           1 :         EXPECT_DOUBLE_EQ(vpara.y, 2);
-     151           1 :         EXPECT_DOUBLE_EQ(vpara.z, 0);
-     152           1 :         EXPECT_DOUBLE_EQ(vperp.x, 3);
-     153           1 :         EXPECT_DOUBLE_EQ(vperp.y, 0);
-     154           1 :         EXPECT_DOUBLE_EQ(vperp.z, 1);
-     155           1 : }
-     156             : 
-     157           0 : int main(int argc, char **argv) {
-     158           0 :         ::testing::InitGoogleTest(&argc, argv);
-     159           0 :         return RUN_ALL_TESTS();
-     160             : }
-     161             : 
-     162             : } // namespace crpropa
-
-
-
- - - - -
Generated by: LCOV version 1.14
-
- - - diff --git a/doc/coverageReport/updown.png b/doc/coverageReport/updown.png deleted file mode 100644 index aa56a238b3e6c435265250f9266cd1b8caba0f20..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 117 zcmeAS@N?(olHy`uVBq!ia0vp^AT}Qd8;}%R+`Ae`*?77*hG?8mPH5^{)z4*}Q$iB}huR`+ diff --git a/doc/index.rst b/doc/index.rst index a123374e6..f398dca5b 100644 --- a/doc/index.rst +++ b/doc/index.rst @@ -43,10 +43,8 @@ Contents .. toctree:: :caption: DEVEL - :maxdepth: 1 + :maxdepth: 2 pages/Debugging.md pages/Code-Coverage.md pages/Data-files.md - - diff --git a/doc/pages/Code-Coverage.md b/doc/pages/Code-Coverage.md index a70872b04..8621353a5 100644 --- a/doc/pages/Code-Coverage.md +++ b/doc/pages/Code-Coverage.md @@ -17,9 +17,5 @@ make coverage ``` The final report is in ```~/build/coverageReport/index.html``` - -### Code Coverage for the current master version -The report for the current master branch version can be found here. - -.. toctree:: - conerageReport/index.html \ No newline at end of file +### coverage report of the current master branch +The coverage report of the current master branch can be accesed `by clicking here `_ now. \ No newline at end of file From bf9ed4c433105cd6be7b85576697abac57868150 Mon Sep 17 00:00:00 2001 From: Julien Date: Wed, 17 Apr 2024 11:38:19 +0200 Subject: [PATCH 11/45] add individual workfolows for documentation and coverage report --- .github/workflows/create_coverage_report.yml | 59 ++++++++++++++++++++ .github/workflows/create_documentation.yml | 4 +- 2 files changed, 60 insertions(+), 3 deletions(-) create mode 100644 .github/workflows/create_coverage_report.yml diff --git a/.github/workflows/create_coverage_report.yml b/.github/workflows/create_coverage_report.yml new file mode 100644 index 000000000..0a24a5080 --- /dev/null +++ b/.github/workflows/create_coverage_report.yml @@ -0,0 +1,59 @@ +name: create-coverage-report +on: [workflow_dispatch] + +jobs: + create-coverage-report: + runs-on: ubuntu-latest + + strategy: + fail-fast: false + matrix: + config: + - name: "ubuntu-22" + os: ubuntu-22.04 + cxx: "g++-11" + cc: "gcc-11" + fc: "gfortran-11" + swig_builtin: "On" #uses swig 4.0.2 + py: "/usr/bin/python3" #python 3.10 + # define steps to take + steps: + - name: Checkout repository + uses: actions/checkout@v4 + - name: Prerequirements + run: | + sudo apt-get update + sudo apt-get install libmuparser-dev libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov doxygen graphviz + sudo apt-get install pandoc # do not only use pip to install pandoc, see https://stackoverflow.com/questions/62398231/building-docs-fails-due-to-missing-pandoc + pip install -r doc/pages/example_notebooks/requirements.txt # load requirements for notebooks + pip install sphinx sphinx_rtd_theme m2r2 nbsphinx lxml_html_clean breathe pandoc exhale # load requirements for documentation + - name: Set up the build + env: + CXX: ${{ matrix.config.cxx }} + CC: ${{ matrix.config.cc }} + FC: ${{ matrix.config.fc }} + run: | + mkdir build + cd build + cmake .. -DCMAKE_INSTALL_PREFIX=$HOME/.local -DENABLE_PYTHON=True -DPython_EXECUTABLE=${{ matrix.config.py }} -DENABLE_TESTING=On -DENABLE_SWIG_BUILTIN=${{ matrix.config.swig_builtin }} -DSIMD_EXTENSIONS=native -DPython_INSTALL_PACKAGE_DIR=/home/runner/.local/ -DBUILD_DOC=OFF -DENABLE_COVERAGE=On + - name: Build CRPropa + run: | + cd build + make -j + - name: run test + run: | + cd build + make test + continue-on-error: true + - name: coverage report + run: | + cd build + make coverage + tar -zcvf coverage.tar.gz coverageReport + - name: archive documentation + uses: actions/upload-artifact@v4 + with: + name: "coverage" + path: | + build/coverage.tar.gz + \ No newline at end of file diff --git a/.github/workflows/create_documentation.yml b/.github/workflows/create_documentation.yml index 9d8dbc1b7..69f96b279 100644 --- a/.github/workflows/create_documentation.yml +++ b/.github/workflows/create_documentation.yml @@ -50,17 +50,15 @@ jobs: run: | cd build make coverage - tar -zcvf coverage.tar.gz coverageReport - name: build documentation run: | cd build make doc cp -r coverageReport doc/pages/coverageReport - tar -zcvf documentation.tar.gz doc + tar -zcvf documentation.tar.gz doc - name: archive documentation uses: actions/upload-artifact@v4 with: name: "documentation" path: | build/documentation.tar.gz - build/coverage.tar.gz From e6c747a111c037701e58f5848c61f11df7e165f8 Mon Sep 17 00:00:00 2001 From: Julien Date: Wed, 17 Apr 2024 12:22:33 +0200 Subject: [PATCH 12/45] fix sphinx version 7.2.6 --- .github/workflows/create_documentation.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/create_documentation.yml b/.github/workflows/create_documentation.yml index 69f96b279..0556e6d9a 100644 --- a/.github/workflows/create_documentation.yml +++ b/.github/workflows/create_documentation.yml @@ -27,7 +27,7 @@ jobs: sudo apt-get install libmuparser-dev libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov doxygen graphviz sudo apt-get install pandoc # do not only use pip to install pandoc, see https://stackoverflow.com/questions/62398231/building-docs-fails-due-to-missing-pandoc pip install -r doc/pages/example_notebooks/requirements.txt # load requirements for notebooks - pip install sphinx sphinx_rtd_theme m2r2 nbsphinx lxml_html_clean breathe pandoc exhale # load requirements for documentation + pip install sphinx==7.2.6 sphinx_rtd_theme m2r2 nbsphinx lxml_html_clean breathe pandoc exhale # load requirements for documentation - name: Set up the build env: CXX: ${{ matrix.config.cxx }} From baa586b3c7516ce2a9f86af0047e35016fb876bf Mon Sep 17 00:00:00 2001 From: Julien Date: Wed, 17 Apr 2024 12:33:54 +0200 Subject: [PATCH 13/45] add workflow for deployment of documentation --- .github/workflows/create_coverage_report.yml | 2 +- .../workflows/deploy_new_documentation.yml | 65 +++++++++++++++++++ .gitignore | 2 + 3 files changed, 68 insertions(+), 1 deletion(-) create mode 100644 .github/workflows/deploy_new_documentation.yml diff --git a/.github/workflows/create_coverage_report.yml b/.github/workflows/create_coverage_report.yml index 0a24a5080..37653ff29 100644 --- a/.github/workflows/create_coverage_report.yml +++ b/.github/workflows/create_coverage_report.yml @@ -26,7 +26,7 @@ jobs: sudo apt-get install libmuparser-dev libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov doxygen graphviz sudo apt-get install pandoc # do not only use pip to install pandoc, see https://stackoverflow.com/questions/62398231/building-docs-fails-due-to-missing-pandoc pip install -r doc/pages/example_notebooks/requirements.txt # load requirements for notebooks - pip install sphinx sphinx_rtd_theme m2r2 nbsphinx lxml_html_clean breathe pandoc exhale # load requirements for documentation + pip install sphinx==7.2.6 sphinx_rtd_theme m2r2 nbsphinx lxml_html_clean breathe pandoc exhale # load requirements for documentation - name: Set up the build env: CXX: ${{ matrix.config.cxx }} diff --git a/.github/workflows/deploy_new_documentation.yml b/.github/workflows/deploy_new_documentation.yml new file mode 100644 index 000000000..7fc313e0c --- /dev/null +++ b/.github/workflows/deploy_new_documentation.yml @@ -0,0 +1,65 @@ +name: deploy-documentation +on: [workflow_dispatch] + +jobs: + build-and-deploy: + runs-on: ubuntu-latest + + strategy: + fail-fast: false + matrix: + config: + - name: "ubuntu-22" + os: ubuntu-22.04 + cxx: "g++-11" + cc: "gcc-11" + fc: "gfortran-11" + swig_builtin: "On" #uses swig 4.0.2 + py: "/usr/bin/python3" #python 3.10 + + # define steps to take + steps: + - name: Checkout repository + uses: actions/checkout@v4 + - name: Prerequirements + run: | + sudo apt-get update + sudo apt-get install libmuparser-dev libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov doxygen graphviz + sudo apt-get install pandoc # do not only use pip to install pandoc, see https://stackoverflow.com/questions/62398231/building-docs-fails-due-to-missing-pandoc + pip install -r doc/pages/example_notebooks/requirements.txt # load requirements for notebooks + pip install sphinx==7.2.6 sphinx_rtd_theme m2r2 nbsphinx lxml_html_clean breathe pandoc exhale # load requirements for documentation + - name: Set up the build + env: + CXX: ${{ matrix.config.cxx }} + CC: ${{ matrix.config.cc }} + FC: ${{ matrix.config.fc }} + run: | + mkdir build + cd build + cmake .. -DCMAKE_INSTALL_PREFIX=$HOME/.local -DENABLE_PYTHON=True -DPython_EXECUTABLE=${{ matrix.config.py }} -DENABLE_TESTING=On -DENABLE_SWIG_BUILTIN=${{ matrix.config.swig_builtin }} -DSIMD_EXTENSIONS=native -DPython_INSTALL_PACKAGE_DIR=/home/runner/.local/ -DBUILD_DOC=On -DENABLE_COVERAGE=On + - name: Build CRPropa + run: | + cd build + make -j + - name: run test + run: | + cd build + make test + continue-on-error: true + - name: coverage report + run: | + cd build + make coverage + - name: build documentation + run: | + cd build + make doc + - name: move final documentation # to avoid conflict with .gitignore + run: | + mv build/doc ~/final_doc + cp -r build/coverageReport ~/final_doc/pages/coverageReport + - name: deploy documentation #deploys the documentation to the gh-pages branch + uses: JamesIves/github-pages-deploy-action@v4 + with: + folder: ~/final_doc + diff --git a/.gitignore b/.gitignore index edc79bc75..75599931a 100644 --- a/.gitignore +++ b/.gitignore @@ -13,6 +13,8 @@ lib/ share/ doc/api/ +!final_doc/ # needed for deployment of the documentation + cmake/CMakeCache.txt cmake/CMakeFiles/ From 5306f96829c7852190dca8dfee1e6f2ca5835fec Mon Sep 17 00:00:00 2001 From: Julien Date: Wed, 17 Apr 2024 14:17:36 +0200 Subject: [PATCH 14/45] perform documentation deploy on push to master --- .github/workflows/deploy_new_documentation.yml | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/.github/workflows/deploy_new_documentation.yml b/.github/workflows/deploy_new_documentation.yml index 7fc313e0c..70783f060 100644 --- a/.github/workflows/deploy_new_documentation.yml +++ b/.github/workflows/deploy_new_documentation.yml @@ -1,5 +1,9 @@ name: deploy-documentation -on: [workflow_dispatch] +on: + push: + branches: + - main + - 'releases/**' jobs: build-and-deploy: From 25aac942e22663d11e50bf1e5b4c8287349895cb Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Sun, 21 Apr 2024 19:42:05 +0200 Subject: [PATCH 15/45] bugfix to prevent photons getting pmass unequal to zero and commented lines for non-nuclei --- src/ParticleState.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/ParticleState.cpp b/src/ParticleState.cpp index 9f867c384..ad7aa4fa9 100644 --- a/src/ParticleState.cpp +++ b/src/ParticleState.cpp @@ -55,8 +55,10 @@ void ParticleState::setId(int newId) { if (id < 0) charge *= -1; // anti-nucleus } else { - if (abs(id) == 11) + if (abs(id) == 11) //electron or positron pmass = mass_electron; + if (abs(id) == 22) //photon + pmass = 0.0; charge = HepPID::charge(id) * eplus; } } From a22b225623485aaf5a26e2c7d2fa0153364cb4d9 Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Mon, 22 Apr 2024 18:35:51 +0200 Subject: [PATCH 16/45] introduction of new general function particleMass for non-nuclei and nuclei as suggested by Lukas and Julien --- include/crpropa/ParticleMass.h | 10 +++++++++- src/ParticleMass.cpp | 11 +++++++++++ src/ParticleState.cpp | 6 +----- 3 files changed, 21 insertions(+), 6 deletions(-) diff --git a/include/crpropa/ParticleMass.h b/include/crpropa/ParticleMass.h index f4e5a6d6c..fdfd8579d 100644 --- a/include/crpropa/ParticleMass.h +++ b/include/crpropa/ParticleMass.h @@ -6,7 +6,15 @@ namespace crpropa { * \addtogroup PhysicsDefinitions * @{ */ - + + /** Get the particle mass by lookup from a table. + For nuclei, the function nuclearMass is called, for the case of + electrons or positrons the mass_electron is returned and for all + other cases like photons and also neutrinos, zero mass is returned. + @param id id of the particle following the PDG numbering scheme + @returns The mass of a the particle + */ + double particleMass(int id); /** Get the nucleus mass by lookup from a table. The masses are the atomic masses from the NIST database: http://www.nist.gov/pml/data/comp.cfm diff --git a/src/ParticleMass.cpp b/src/ParticleMass.cpp index a2a5c5090..cc474eb2a 100644 --- a/src/ParticleMass.cpp +++ b/src/ParticleMass.cpp @@ -53,6 +53,17 @@ struct NuclearMassTable { static NuclearMassTable nuclearMassTable; +double particleMass(int id) { + double m; + if (isNucleus(id)) + return nuclearMass(id); + if (abs(id) == 11) + m = mass_electron; + else + m = 0.0; + return m; +} + double nuclearMass(int id) { int A = massNumber(id); int Z = chargeNumber(id); diff --git a/src/ParticleState.cpp b/src/ParticleState.cpp index ad7aa4fa9..85736a856 100644 --- a/src/ParticleState.cpp +++ b/src/ParticleState.cpp @@ -49,16 +49,12 @@ double ParticleState::getRigidity() const { void ParticleState::setId(int newId) { id = newId; + pmass = particleMass(id); if (isNucleus(id)) { - pmass = nuclearMass(id); charge = chargeNumber(id) * eplus; if (id < 0) charge *= -1; // anti-nucleus } else { - if (abs(id) == 11) //electron or positron - pmass = mass_electron; - if (abs(id) == 22) //photon - pmass = 0.0; charge = HepPID::charge(id) * eplus; } } From e900b39f746b706c8098c43f1cfc7d599f08cdd7 Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Mon, 22 Apr 2024 18:45:09 +0200 Subject: [PATCH 17/45] updated CHANGELOG.md --- CHANGELOG.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4332cf998..cf17ffbb7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -3,10 +3,12 @@ ### Bug fixes: * Fixed sign for exponential decay of magn. field strength with Galactic height in LogarithmicSpiralField * Fixed r term in source distribution for SNR and Pulsar + * Fixed wrong mass inheritance for secondaries other than nuclei or electron/positron ### New features: ### Interface changes: + * Added new backwards-compatible function particleMass that returns particle mass also for non-nuclei ### Features that are deprecated and will be removed after this release * EBL model from Finke et al. 2022 From 5649102f041b5d86014c61780a4f5ea50d5fd9c9 Mon Sep 17 00:00:00 2001 From: Julien Date: Tue, 23 Apr 2024 09:57:14 +0200 Subject: [PATCH 18/45] add clip volume to reading function; update test for reading grid properties --- src/GridTools.cpp | 12 ++++++++++++ test/testCore.cpp | 6 ++++++ 2 files changed, 18 insertions(+) diff --git a/src/GridTools.cpp b/src/GridTools.cpp index d7da0961c..27f38ab2d 100644 --- a/src/GridTools.cpp +++ b/src/GridTools.cpp @@ -299,6 +299,11 @@ ref_ptr loadGrid3fFromTxt(std::string filename, double c) { // reflective ss >> name >> gp.reflective; + + // clip volume + bool clip; + ss >> name >> clip; + gp.setClipVolume(clip); // interpolation type ss >> name >> type; @@ -389,6 +394,11 @@ ref_ptr loadGrid1fFromTxt(std::string filename, double c) { // reflective ss >> name >> gp.reflective; + // clip volume + bool clip; + ss >> name >> clip; + gp.setClipVolume(clip); + // interpolation type ss >> name >> type; if (type == "TRICUBIC") @@ -426,6 +436,7 @@ void dumpGridToTxt(ref_ptr grid, std::string filename, double c, bool sa << "\t" << "gridsize: " << grid -> getNx() << " " << grid -> getNy() << " " << grid -> getNz() << "\t" << "spacing: " << grid -> getSpacing () << "\t" << "reflective: " << grid -> isReflective() + << "\t" << "clipVolume: " << grid -> getClipVolume() << "\t" << "interpolation: " << grid -> getInterpolationTypeName() << "\n"; } @@ -455,6 +466,7 @@ void dumpGridToTxt(ref_ptr grid, std::string filename, double c, bool sa << "\t" << "gridsize: " << grid -> getNx() << " " << grid -> getNy() << " " << grid -> getNz() << "\t" << "spacing: " << grid -> getSpacing () << "\t" << "reflective: " << grid -> isReflective() + << "\t" << "clipVolume: " << grid -> getClipVolume() << "\t" << "interpolation: " << grid -> getInterpolationTypeName() << "\n"; } diff --git a/test/testCore.cpp b/test/testCore.cpp index 24f6f9113..98ed78294 100644 --- a/test/testCore.cpp +++ b/test/testCore.cpp @@ -903,6 +903,7 @@ TEST(Grid1f, DumpLoadTxtGridProperties) { ref_ptr grid = new Grid1f(Vector3d(0.5, 1.5, 2.5), 3, 2, 4, Vector3d(0.2, 1.2, 2.2)); grid -> setInterpolationType(TRICUBIC); grid -> setReflective(true); + grid -> setClipVolume(true); // set some values for the grid for (int ix = 0; ix < grid -> getNx(); ix++) { @@ -923,6 +924,8 @@ TEST(Grid1f, DumpLoadTxtGridProperties) { EXPECT_EQ(grid -> getNy(), loadedGrid -> getNy()); EXPECT_EQ(grid -> getNz(), loadedGrid -> getNz()); + EXPECT_TRUE(loadedGrid -> getClipVolume()); + Vector3d orig = grid -> getOrigin(); Vector3d loadedOrigin = loadedGrid -> getOrigin(); EXPECT_EQ(orig.x, loadedOrigin.x); @@ -953,6 +956,7 @@ TEST(Grid3f, DumpLoadTxtGridProperties) { ref_ptr grid = new Grid3f(Vector3d(0.5, 1.5, 2.5), 3, 2, 4, Vector3d(0.2, 1.2, 2.2)); grid -> setInterpolationType(NEAREST_NEIGHBOUR); grid -> setReflective(true); + grid -> setClipVolume(true); // set some values for the grid for (int ix = 0; ix < grid -> getNx(); ix++) { @@ -972,6 +976,8 @@ TEST(Grid3f, DumpLoadTxtGridProperties) { EXPECT_EQ(grid -> getNx(), loadedGrid -> getNx()); EXPECT_EQ(grid -> getNy(), loadedGrid -> getNy()); EXPECT_EQ(grid -> getNz(), loadedGrid -> getNz()); + + EXPECT_TRUE(loadedGrid -> getClipVolume()); Vector3d orig = grid -> getOrigin(); Vector3d loadedOrigin = loadedGrid -> getOrigin(); From e27102be6afe24c7f52629e761965795aee2422d Mon Sep 17 00:00:00 2001 From: Julien Date: Tue, 23 Apr 2024 10:00:31 +0200 Subject: [PATCH 19/45] update example with grid property loading --- .../density/density_grid_sampling.ipynb | 113 ++++++++---------- 1 file changed, 47 insertions(+), 66 deletions(-) diff --git a/doc/pages/example_notebooks/density/density_grid_sampling.ipynb b/doc/pages/example_notebooks/density/density_grid_sampling.ipynb index 2dde74268..1fd5ae2e4 100644 --- a/doc/pages/example_notebooks/density/density_grid_sampling.ipynb +++ b/doc/pages/example_notebooks/density/density_grid_sampling.ipynb @@ -10,7 +10,7 @@ }, { "cell_type": "code", - "execution_count": 9, + "execution_count": 1, "metadata": {}, "outputs": [], "source": [ @@ -41,27 +41,20 @@ }, { "cell_type": "code", - "execution_count": 10, + "execution_count": 2, "metadata": {}, "outputs": [], "source": [ - "data_path = \"/home/home1/jdo/H2-Data/Mertsch2020/H2_dens_mean_BEG03.txt\" # has to be adjusted after download" + "data_path = \"H2_dens_mean_BEG03.txt\" # path to the data file " ] }, { "cell_type": "code", - "execution_count": 11, + "execution_count": 3, "metadata": {}, "outputs": [], "source": [ - "origin = Vector3d(-15.96875, -15.96875, -0.46875) * kpc\n", - "nX, nY, nZ = 512, 512, 16\n", - "spacing = 0.0625 * kpc\n", - "grid = Grid1f(origin, nX, nY, nZ, spacing)\n", - "grid.setClipVolume(True) # return 0 outside of the volume\n", - "\n", - "# load data \n", - "loadGridFromTxt(grid, data_path)" + "grid = loadGrid1fFromTxt(data_path)" ] }, { @@ -74,7 +67,7 @@ }, { "cell_type": "code", - "execution_count": 12, + "execution_count": 4, "metadata": {}, "outputs": [ { @@ -103,27 +96,25 @@ }, { "cell_type": "code", - "execution_count": 13, + "execution_count": 5, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ - "/tmp/ipykernel_188985/463811823.py:16: RuntimeWarning: divide by zero encountered in log10\n", + "/tmp/ipykernel_9824/463811823.py:16: RuntimeWarning: divide by zero encountered in log10\n", " p = ax.pcolormesh(xRange, yRange, np.log10(dens_data).T)\n" ] }, { "data": { - "image/png": "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", + "image/png": "iVBORw0KGgoAAAANSUhEUgAAAtcAAAM5CAYAAADMtx0bAAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjguNCwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy8fJSN1AAAACXBIWXMAABcSAAAXEgFnn9JSAAEAAElEQVR4nOz9abBs2Vkdin4r18p293uftupUqRqVhFRSqQGBEMaWZEkg9GR0hXwj8FXELQF+YWxuSBYOQ/ghHiHJYe61jBEhfIOHMTgcgY0pG3FlTCMhgzFVKlBHQakrVd+cZvd7Z59rZb4f8xtzfnOtPKU6OKXinBojoir3zpxr9mud3PMb3xjJbDabCUEQBEEQBEEQ/9OoPdsdIAiCIAiCIIhrBfxyTRAEQRAEQRALAr9cEwRBEARBEMSCwC/XBEEQBEEQBLEg8Ms1QRAEQRAEQSwI/HJNEARBEARBEAsCv1wTBEEQBEEQxILAL9cEQRAEQRAEsSDwyzVBEARBEARBLAj8ck0QBEEQBEEQCwK/XBMEQRAEQRDEgsAv1wRBEARBEASxIPDLNUEQBEEQBEEsCPxyTRAEQRAEQRALwlXx5brf78tHP/pR+cEf/EF54QtfKK1WS5aWluRlL3uZvP/975dut3vZa3/lV35FvvVbv1WWl5dlc3NTvud7vkfuvvvub2DvCYIgCIIgiOcKktlsNnu2O/G18K//9b+Wv/t3/66IiLzoRS+Sl7zkJXJ0dCR33323HB8fyzd90zfJH/7hH8qpU6ei697znvfIhz/8YWm32/KmN71JhsOh/P7v/77MZjO566675G1ve9uzMBqCIAiCIAjiWsVV8eX63/7bfyt33323vOc975EXvehF/v3z58/LW97yFvnc5z4n3//93y+/+qu/6j/7xCc+IW984xtla2tL7rnnHrnttttEROSee+6R1772tdLpdOThhx+W9fX1b/RwCIIgCIIgiGsUV8WX66fDPffcI695zWuk2WzK0dGRNBoNERH5nu/5Hvnt3/5t+Zf/8l/Ke97znuiad7/73fJzP/dz8qEPfUh+9Ed/9FnoNUEQBEEQBHEt4qrgXD8dXvayl4mIyGg0kt3dXRERGQwG8slPflJERN7xjndUrsF7H/vYx75BvSQIgiAIgiCeC8ie7Q78z+Khhx4SEZF6vS6bm5siIvLlL39ZRqORnDx5Us6dO1e55pWvfKWIiNx3333/0+2fOXNGer2e3Hjjjf/TdREEQRAEQTxbeOyxx2RpaUkuXLjwbHflqsZV/+X6wx/+sIiIfPd3f7c0m00RcZtDROZ+sRYRWVpakvX1ddnf35fj42NZWVn5mu3cfvvtc9/f3t6Wer3+l+k6QRAEQRDEXxlMJhPp9XrPdjeuelzVX67/63/9r/JLv/RLUq/X5QMf+IB/H9J8nU7nstcuLS3JwcHBM/5yfTnU63W59dZb5f777/9L10EQBEEQBPFs43IHicSV4ar9cv2lL31J3vnOd8psNpN//s//uedef71wuS/P3IgEQRAEQRAEcFUmND755JPy3d/93bK/vy/vfe975d3vfnf0+fLysog485nLAWGP/5lTa4IgCIIgCIKwuOq+XO/t7cmb3vQmefTRR+Vd73qXfOhDH6qUQXLhE088MbeOXq8nBwcHsrGxwS/XBEEQBEEQxMJwVX257na78uY3v1m+8IUvyNvf/nb5xV/8RUmSpFLuhS98oTSbTdne3pYnn3yy8vlnP/tZERG54447vu59JgiCIAiCIJ47uGq+XI9GI/ne7/1e+ZM/+RP5ru/6Lvn3//7fS5qmc8u22215/etfLyIiv/7rv175/K677hIRkbe+9a1fvw4TBEEQBEEQzzlcFV+ui6KQ7//+75dPfvKT8p3f+Z3yn//zf/ZOjJfDe9/7XhER+eAHPygPPPCAf/+ee+6RX/iFX5D19XX5wR/8wa9rvwmCIAiCIIjnFq4KtZCPfOQj8hu/8RsiInLixAn5+3//788t96EPfUhOnDghIiJveMMb5N3vfrd8+MMflpe//OXyxje+UcbjsXz84x+X2Wwmv/zLvyzr6+vfqCEQBEEQBEEQzwFcFV+u9/f3/c/4kj0PP/VTP+W/XIuI/OzP/qy8/OUvl4985CPy8Y9/XBqNhrzhDW+Q973vffKa17zm69pngiAIgiAI4rmHZDabzZ7tTlzNgM41TWQIgiAIgriawe80i8FVwbkmCIIgCIIgiKsB/HJNEARBEARBEAsCv1wTBEEQBEEQxILAL9cEQRAEQRAEsSDwyzVBEARBEARBLAj8ck0QBEEQBEEQCwK/XBMEQRAEQRDEgsAv1wRBEARBEASxIPDLNUEQBEEQBEEsCPxyTRAEQRAEQRALAr9cEwRBEARBEMSCwC/XBEEQBEEQBLEg8Ms1QRAEQRAEQSwI/HJNEARBEARBEAsCv1wTBEEQBEEQxILAL9cEQRAEQRAEsSDwyzVBEARBEARBLAj8ck0QBEEQBEEQCwK/XBMEQRAEQRDEgsAv1wRBEARBEASxIPDLNUEQBEEQBEEsCPxyTRAEQRAEQRALAr9cEwRBEARBEMSCwC/XBEEQBEEQBLEg8Ms1QRAEQRAEQSwI/HJNEARBEARBEAsCv1wTBEEQBEEQxILAL9cEQRAEQRAEsSDwyzVBEARBEARBLAj8ck0QBEEQBEEQCwK/XBMEQRAEQRDEgsAv1wRBEARBEASxIPDLNUEQBEEQBEEsCPxyTRAEQRAEQRALAr9cEwRBEARBEMSCwC/XBEEQBEEQBLEg8Ms1QRAEQRAEQSwI/HJNEARBEARBEAsCv1wTBEEQBEEQxILAL9cEQRAEQRAEsSDwyzVBEARBEARBLAj8ck0QBEEQBEEQCwK/XBMEQRAEQRDEgsAv1wRBEARBEASxIPDLNUEQBEEQBEEsCPxyTRAEQRAEQRALQvZsd4C4uvC67/o/o98nS2mlzDRLRESkcZSLiEg6nvrPxqtuy2V999607srKLFyf9d11RduVLZpJpe507C6Y6Z+HtXGooJbPorIzfU1MG/4zrTobuP7knfD3JtpA2Xo312tCfwD0I++kOoYifFavaR9dG3bO0Nek0PGk1b7WRu66ouXqSYfVvgKTZVd3e3virmmGMmjD90vbKhphPNnIlZm03XXNw9yMUfs2nUW/z1sfjKvec/PQP93wZZqH7r1cr0ObGKcdK+Yc1ydhWn3dGGNz34152jBj1r5OdaypaQNrVT92182y6nxirVFP+CD8Pkt1fSeuP5M1Hau5BnOfaPOYJ1tv0Xb9wT6Zlfao+0znXu8brIGIyKSj8znQOvWjJAzZ97s2iceD9RIRGa9oP3SuC22rPjD38UotaisduMJTs98wRsz9zPxrk+i2ynQvYw3tfPh+z+L7MDP9yHWfYg+mY73ELOXlxjpZtvcGXmfR2CvrLiK57k1737QO3AWDzVT7gfs6XDetu1fM3crjk0rdWPNC93DD3H+hr67u8Vr8z3dS7arfO/YeBdJR6ZljxurXrh7vQewx11f32rnk1sM/d80/CWgX+wRjr5l5KfR2QRmslx0P5nOsa2bn1fdH20Wfo+ed3seFrkFNpzVvh/G0d1ylmAfsP8yPHdsf3/WPqh0gCAOeXBMEQRAEQRDEgsCTa+KKgBMND/MrTlTr3fhEJG+bk1qchrVw2ufKZr1wipN33LbECUJtXO0HTo1wcpcNqic86Js/CTEnGbOaa3+45fqGE5bmfqgHp+w4QZnqyaY9ScRJ6GQli/qD02qRcEIrTT3VHtkj9PiUpJa7H4ab4dbEmS/GMe+0HmOtd/UEEetkl2sWl/V9XwptFdqPyTJOAu0psL7i1EdPzu0JU71XOlXXa1q79gTcvZZPqrAnon5r3ViX4Ym6L1I7xLrqiZN23u6X2lg/w3ok9uTN/dy9oeX63HK/d3bCsViqp6TpKJ7X6KR3qRb1P8NJeGpOcevxSSD2oj1lx77CfTTarOs1YTwNPR1HZKQw+6xRIJJQi8ZT74eTXpz4Yew5Tv3NCWm0P2X+6S3W2UeAENUw85Li5K+p9fbCZ2gX8+FPVm3ERrvkT1b19ygao23403rU37In6Nrnvisz1NPlmnlk2EiTbdP2Z1rH6Tr6ET7DiTXawB6fmtPt8ZLur2095T7hOta5GJ59aLe14zYxTqftcxefIVIzXncbBKfCtt/NI9dWTfuFKITtY20yjcdsxoioAe7x9m7YS9gn6NtgU/f/0D5nE+1bHHG0yAbutXySPjXDKfR6RDzn9XWwivblsmXSCX53bTUPQ38QyWjonGFv2j5nfRsGIojLgyfXBEEQBEEQBLEg8Ms1QRAEQRAEQSwIpIUQVwQkEPmwuGUmINRdCX0HWgjCrwiHoz6REPtGCL5QGoVNQsPfg6CXzGpxwprtG8KC41UkB4XQL0KZy09Moj6D3iFiKBYa2p1o+N8mkQkS5TSUP15FVo1JVGu59xrHrr4oQU3nyCfXaZuWngKKCfqRILRp5h5jRR/bO+76wUYYD6gZk0489yhr56F5OK2MNZnF9A20aUOlWDu85jr2oh3+jvcJZlr1HNaB1A91kNo+5gmJmiImVK7X9886ekdrz1CMGm5flZMERUTqSLgdxgmndsyD0+765UdRZxKNXaSaEJmvuGuSSZgXJGaC8gT6T/3I9HXZXQfaA5LZbJIg9olPgDVhfiQiIuEPFAWb0FdOMsxG1TFLEVMBsHaJOYrBfZzp4oH6ZekLlcQyu85Y+xLNzNI7hqAZ6HuFJp81uubeUjoJqDmtfe3XsFoGyWygH9jESJ+8BjoHqChmXpB41zieahvhuYY6QbEAZcsmHS8fz6LPcB/WbOJdaZ/ifu5cCvsEid4AEoEb5r2QMIuLNPHUlMGaV8pKeIaCfofxWYoE5mqkz9eQBCkV1LvxPouSJxvxHkAC/Gg19LZMQ7IUGOxzJLOCygK6iUigSGHfITES10Zt1OMzx+FG+D3rVxNDCWIeeHJNEARBEARBEAvCVfPl+jOf+Yz89E//tLz97W+Xc+fOSZIkksyRRAN+6qd+ypeZ99+P//iPfwN7TxAEQRAEQTwXcNXQQj7wgQ/Ib/7mb17xdd/xHd8hz3/+8yvvf/M3f/MiuvWcA6gNoBRYygZCftBxBsUh6xk6RhPUConKWNpA3qlH16XDQFsoWo3oeq9TbULwI82eh4Yu6CDj9RBmxHtlagGuEQnhSugpe31q+zfdNA55e+1oo1YAXWcoKVjNWVA+0AbUAax6AZQPMOZWX6kshpoA1YiaRo+hdFKbE8ZF+BehZqtYAQoBXnOzLlk3VuVA38eGSpOmMRUA82DraaqyC/ZOvhTrO7sKkui90VYjmgv3s6ovXHL1LT3u4sCFUT9BmD7rupixDamDxpFqf7wGtQkLLz0xjMacDVU/fCkE4ad10Jd0L2/ovhmF4XhdbF0y7NHWrlUicP0YryqtBJrU5h6DAIlXozGMAtAcQkgfdJewl6DYUSi9BLq9VhcaVJyp3y+xoo1IULNpHsR721aD/mC/g+IgYmgGGNscalDzEPfmLLrG6ktD/QSKKFCwKAw1IR3F4xC9xu5JjL/RjdUg7LyAdoC9DVUJkaA0UcuhJnN5VQnQd0DHOrglyI6090CfcL8vPeUatXQ1zDWoI6Ck2QVKihLlo6S+44rruiYxZUJEpIC2fz+e88Tou2N/pPqsAF2mdyY8Z9s7U70ubj41VCV8VtbPtwpD+HcD+vtWJzv4GsT1WZQVb5peaciW0T5qBUE9hAohxJXjqvly/e3f/u1yxx13yKte9Sp51ateJTfddJOMRqOved0P/dAPyZ133vn17yBBEARBEATxnMdV8+X6x37sx57tLhAEQRAEQRDE0+Kq+XJN/NVAyPZ2v/dPGbMTDQvCJtmH8parSh7A8DoXv02NcUXnAjyM3Xu9c+1wvYYTEQpFRLN/KsSBvSqGWoEnUw1xmpAvMtKnJbvxWJckid7EmBuHwaUExjK5ttXamURjFxFJleIB+kP92NBkNHQ/WnfzaJUuyn0FQAGJ2sB8aPjWUwLMfAczHaUvtGJTDJFAkZg2YYFts/pBM3C/gyZjQ7yT5SzqD+gtgy1DyQEVBxQWzfxvHoV+5KA9lGg31hClc8FVMNpwaz/bgEW6CTnrBtl7yYqIiKw+EqJd6Gv9WGkqx+o+YSgfaB+KN8WqC+HnxsK+uQfDD9cPUJ2iMLuqhJSNYqxyzAzzC0pNA2oZYb8k/Vidw1ItQFPAmnu6gLnlQAeBkkmSVPcAKACgo+QraaVMmTaEPtvxlC23LZ3Dm+qAfqDPjLGxJIfJS/mZEfUDajt6Lww39B7rWQUbpRatqZqKKolYRRE8a0A78oorXWMqpesL6lf3ekMx0qF1xrENfKyko7SdUXw/gwri+qhqNAnMedxe7FwMzxysvafUaNt2nkDrQL9mXhGkqhyDZ7p9zmA9RjqfWLu6UWqpgUal81HTW2Lpotmv3hxL90erShHy1IyScszUmDCBBgIqWDTWJuh72uf1Ks3MU4PwOAGF0di5B6t2pRMexTQrkbBvCeJr4Zr/cv3JT35SPv/5z8twOJRz587Jm9/8ZvKtCYIgCIIgiK8Lrvkv1//u3/276Pf3ve998n3f933yK7/yK7K8vPws9YogCIIgCIK4FnHNfrl+/vOfLx/60IfkzW9+szzvec+T/f19+e///b/LP/7H/1j+03/6T1IUhfzGb/zGM67v9ttvn/v+gw8+KLfeeuuiuv1XHt5ARKNjy08ZcwMNhfqwp2asp4M4rCsSwuqtvaLyWTlrvH0xhPJhyOLpKRoWRla9LQPDA589bo1dlHbgw6X6UToM/RmqGUj/hPZVDSpgBCISMv+bavjhFUFaYTxQAGkeqNmIkZAEDSNDNr5eP1mt3ppeGaVf4qmICV16c44SNUBi4xMRs06mP35+oWJyaGgqOucIS3uKjgm/ZpUQvvt9+UlrgqFUmgTmOkoJMMYQDVWhgEnKtGTWYwGllaHSQzp2vyi9pXXgrrOqC6gLiiJTVamBMogr78LyWc/1P+vGryKBLmPpKCJhLUXCOtd0XkHLsKY2MNzx66HzPTgRaCpQs8F+tTSZxG+L+P6ZrAQKi6cGlRQihltZpUxZqdWG0Ot90TaUNiMxzUMkUAtAKbBmRYGyFatRWMObQB3QfQJal6W56Nyjrcwrg0gFTaXNTNNqaL93xo1/5UldpzH6HuYA+3PpvHvWdC5WaS6gJuC50DgKY8Yzz1OCoFByGMrUJu5NPEut0Q3g7wG9HvejVdIBVaus2BIhiekghaGZjdbxmavHm60YU51c6/TUsVn1Oe9VRvye1PcNvSKF6csQVCPshVDPcF1NgnAfm70IWgnWyj+n7XyUzJKgLGJNi2B+g2cp9qhtq71T/feKIObhmv1y/c53vjP6fWlpSf7O3/k78rrXvU5e+tKXykc/+lH51Kc+Ja9+9aufpR4SBEEQBEEQ1xqu2S/Xl8PZs2flXe96l3zoQx+S3/md33nGX67vv//+ue9f7kSbIAiCIAiCeO7hOfflWkTktttuExGR8+fPP8s9ufoA0wmf/W2ijQhXwkwDGdozG0pUhQaEdhGugymFiEgyU9WFIxcXnKwGJRCE2j2tZNs1kq+EMlkPYVY1ytAQpFW18IYqoI6UMt9FgqpHNtTQ5qQa/gQlAXQZmLZYlQDQDhC+tYCSCdpHGRte95n6PVAb0koboHxUxjrH8AaUD6wLzGFEAiUiUUOTomXoAmqMAfUKGzIHxuv16HdQT1Jj8lOhevgQdjWs7FVQdD4yQ9uZlSLdGUK/Zg0x9x01mLHIlxtR+ZmqEyTWAATCJrq/Gntuv02NGQ2oNAgjt3bdvq2NrHmS+wzKJsNN19baV4dmrFoelCdd79rYrME4ppNYihH6CsrTPDUYUFdgkITQuTVEAeUEn+Ga5lFVXaOsvmCVFUCjgBKQNSsK5izodInCJSJNVWsAhQDUBksX8FQcb1oEVxyjalHEZeeZjKw8Hqv0gCJhaUgwgwoqLuGzYTveA/XeHPoAKFtQUeoopcXcf1Bfah5c3rjE922C563eI5aShT2t84znkjW3KpRtBMUj+6zIYB6jc57q3Fnqln9+wLxI72N7/2HOfVncz4W5R7E+nrZXpRh5pZlZTO+wn+H6/kpMBSv3yV3vXidLluoU7w8/rnH1HiOIr4Wrxv58kdjf3xcRRxUhCIIgCIIgiEXhOXdyPZvNfCLjK1/5yme5N1cfcArmtZrNn2c4NYKNs09eaYYTW5zOJRM9ndBToPaOSRDTU4ahWl7b0zCc2rb2tTw0Wo1dOE4pcNKKkzOre4qTSG9Z3USipBkscnj01AdloY/sxqOnyXqaNNVknMZxSFLCKctsnkZqHv+KE0mbCDU4oXbuODEuLv83MU6BMtXntYmRXv9YT/ZxYmWT6mZpfNpvk8e8lTo0eKFFPSlMmVgfeN5pfWNfLZ2XYVNfVMsi3077PNaEO5vwhlMxrEdzdxTVKyLS3HEnw9OWvmdONLs3uqxT6GVjfa1dOMaKBMRiydXjT0glzFX7kms/O9JoylrIasXYcCq2rIlz1o4dSZM+qqNJkDOj94u1wtrhpFQkJKYlk/ho1mobY/68vbWemkIbWCQkGeOUcTpPIzmN94fX7zZtY79BC9ue9GZ6YI/kNatzD+QdnJxr3cM5J8+z+CQee8LqswftbJy0zip9xTgQEcv61ZNnnDT7U36zl6Ctj/nFs2fnpUGjf+0hTYbV/T7N3F6y2smrj7h7A0m/GOvIRIQwtklT7wmdZ3tyDWvy8mmyfZYmszgigORF1yeJ60Zkz/QV89A/hWeyPgut9vpxyU5+jiZ3OFXWPpaiiSIiK0/E94ZNwvZR1NJj0V6PE3dE+7zlurVRH8d7EGXtaf8049E18cxwTZ5cb29vy8///M/L8fFx9H6325Uf/uEflnvvvVfOnDkjb3/725+lHhIEQRAEQRDXIq6ak+vf+q3fkg984AP+9/HY/YVvExLf9773yVve8hbp9XryIz/yI/LjP/7j8qpXvUrOnj0r29vb8tnPflZ2d3dlfX1d7rrrLul0Ot/wcRAEQRAEQRDXLq6aL9fb29ty7733Vt63721vb4uIyNbWlvzYj/2YfOpTn5KvfOUrcvfdd0uapnLzzTfLnXfeKf/wH/5Duf76679hfb+mgPwjtVHOjgOdI4W8Nayz82pYbdyMk3hAERiebIY2NNwKXWifcCMijQNXPtiwa+jZUAHwnrcHhrVxp5qch4Qwn+xkwoQ+OUn7Oq0jaTHEGxFGBg1kXpIfkgTrmhBmtZbR7kATOtvbOmaTgNPQRKqxXoeQtU0Q8zbSpUSqKFlxBk3hWnS9TfZB2BZjTmxiGGgHJT1bS5EAHQRJgUiMsmFc0BywPlhfS/nwCaJaD8Lutq+gH2VK68D6WLvw0clW3C/TRntb6THQKD4ClSbsxfqx22/JUK+fap/N3CPBDjQO0EFqo0DtaZQoLAjtp71Qplhyn2FPFKq7bdsCrcpbzxsrba+NrDQd7Mm8E9YHdAPsC1xj7cIHJ1w/Wqo1Hu4No9udx0mK85IEfTIgEvnq1VA+ki9TJLzNoWNgv5btqUWCnjTq87rOpi2MDfeI13y2ydhKFfF0CN0nU6P9jPsQiYSJTdJNY33q4ZaraP3B8HwEpQd7IOxJkxipz0Hcf/5ZY/qBNQS83rRhVYFS04Kmdpwr6Krc072XlObFvIfngU/yM8+XwlvFxzQOJH7a63Fvelt301esC9bOP9vNcwa0pZD4bfqqjTQPdZ117WElb/vo6TG6LG07nlKi9ViTjtNgoRDdbwTxdLhqvlzfeeedcueddz6jsisrK/LTP/3TX98OEQRBEARBEEQJ1yTnmiAIgiAIgiCeDVw1J9fEXw2U9a2tkgGoIl6LVwtZe18Aob9CVRRsuNHrwGr41IacYQ8MFYyGUkfmhaVBVwBNxKodeL1f2FFPq4oiCKFCPQJ627aMt2+GcobRX/VjxWdeaSXMB9qHNTQUH3KrRtGIdV+DdbTpKvrRjP9etn2dlTLdMef2Gq+frG+lg+p8zGr6oYZtrWX8aFPtwjW8D51pSykALQYqErDwtuFxKB8gjOuVEMwTa7zh2oIeuterNhQU9AP626AhiVSVYqYN7F+zF7F2DReuB9XD2p8jhD7aUgqKUqVmmV1DhJhjLe6pUdLx9Isc+rpVVQqoi2DtI4pSu6Qg0tVxmjUEXQB0prKGuohIw0tD6D0BdpXZWug/rsdn3iZbwn2ce11moxChS4R9jz6PjN69p9uMYx1lUGLcZ5ArcS/Yy3a/QUFnWlLr8drJIjKrgd6l91+neu5U9+opOi6jxNPacfvK08SOQCMK16N9v7d13wxPBRpS47iIys6SWLNcJDyDPXVMX4YbYV6g31zv6XxM4ue2iFEiWdPniZ0zKL1AIeU4VtkQMZbiqjAEWkXd6NWDajJada9Ll/R+XA7jwf1/fL3+W6BKMnZPggaCOQMFxALPR+wJq4fuFVE8VSmJ+mzfw2bya2fuv7IiCUFcDtwqBEEQBEEQBLEg8Ms1QRAEQRAEQSwIpIUQVwRk7oPa0D9jDDsOYAaiSg8IfZvwK8KnXlFkXA3vecvckhmMSKCToH3YSdtw5RRUFdA6NCTaPRu2++qjqgKBKGEeqzm4fms9c0wwfF+hkKJhWx96tsoKoEZoeHG8ZoxDNCQKagWoLNZwBuYGoAkEmovpR0nBw5uMmNA16AFQqhivw3wlUCWwHrCTt/OBdYFKB2gUNpwMmg7gTU/q4e94qHlgzr2luR2CN5GZ2l9lNg31DJVCUBul0TVWHQPGMtgvloYROlmaTxMpntbLyjc6H4b+k/bV7nwS150YekkB06JhrMARAfb0un+nzdhoybUfh/kju/D9PCoDC2xLt0FYHPSFdI4tti8DExe93Cp5zHDfNEoheNMf2Kd7KoyZs0RihQrcW5a6gXsDpiR5u3oWlJYMRxDmr1nREU+Zmq+AISKSKY0D+xVzECnypKU+WypbI77/05H2x/S5bEKDNWjthnume4OjOrV34ZyD+qrPnnrJ5GdiqBbLTxXRWKfYN/Y5CYWhflyP/TkblJ4rZn3wM8yGJjrWefQhGMxM9RaJDGtSUD3wDAa9w4wVhi6gy9hvLjBdwnNSDYlyQ3eDSdGsZH5kVYx6Z1355aemcX3WuCqfc98SxBzw5JogCIIgCIIgFgR+uSYIgiAIgiCIBYG0EOKK4OkYCMkbFgBCqj6MlsIYwpotoAwoDu79wqomaJh+qmHk4aahnqjyyGw6P/tbRKQO845SBG/Z/OwVCPR1rEogUVhaw77TksqGNXhByL2mWf3oT2T04JVVoKxQDb9KUvo714aslUrgFRqUOjK1ie4argQFBaHZmgkng1YC2kFdlQmgQCEiUsvdgmZqbgI1F9dXDfvqa9ZzZfOlurleaRz6Ok0uT/+BeoqnfpiQK8xa0FcY8cxqxgTmUqwS4k1uTDgYphx5y5WBcYzt//iMU/kIphhVNZjxmhtjc0/pRIWhSGRQvNHPdG9LLfQDbYFWAiUNq97QONTx6GVQp5katokPa4PyYftaxIo3/j40WwvvIeSN/WdpKp7aAKoG1HuMSgfUJHDfeVqS3ZPezAm0jGo/vJERmFymH34P63SiDaylBfZ5oTQeS00AnQR0DFAjIvoCDGZgWNPAHjfrnEKBQxUvVu19E1MIvKHPHFMcT2+BoYp5vngjFDCdtK+WVhVoO0rtUZpV+1LY22NVAGl0dc7q8T0iEvY76CpWncPTR0ArAV3GPE9ANZFGXNY+3/CM8eZjuMaqjoxBCXKfdS7GijoiVSqPfbSHvsUP/FphnydxWVBZcmOc07kE46uYpmaNhMpqTARxOXCnEARBEARBEMSCwC/XBEEQBEEQBLEgkBZCXBGsEoOISL0bwp4Iw3lDllE1JApTkcmqiyWCYmFDeKLRTYQLkyNTAcJ7MOUYwXTBGKEgVK3UAoRs690QNgUVAXQQhDuzoU2n13HkGr5F5r4xo4F5TFrK3Pd0FQOE/UGvcH3ULHYNpSaC0H64rndWFQSU0gDzi4huo1UWJbMSS2GBAkhjz0kZQO1DDLUnX9JHApg9QzNnoMBMYuWMwUmjwvKQ6zjWozauhni9ORD2S6GfmadRbQDaAOLBSoWxFB0dMygXA6V3QJFGJNCNsn6JviCBztLadvORDtTQZDXwF7wyC0w1lqqPTFBoPDWpZCojElRC0H8YfqRmv00zt84NpV7hmpmh5pRVIyyNqV4yxcH+t8o1M79flSLhqT6G6gSTE9AysJescgYMUaZxKN4q2HhaFagfNswPxgroJVAIMuMpSuYzhVenMEo849jsBGUt/WG8ij1QMkIp0b3seHy/0moZPIPsPe7NjsCOmcTUDdenmIqD+bF9xe4CBQf3iG0Lz8qZV5cp0fFEpLWnzwqY6kAxpVF99jS6cwxZSuNGWbvfvOrQcmw0Y2lMSYkqCHpHYag9MI3B3qkoepj2oRxjKSz1AhQPGO5UlU7Kz9nBpt5/Zs5AccQYvTKWoV7Ne64TxDzw5JogCIIgCIIgFgSeXBNXhP5pPQXCqYA9SMTJGay7kVxkTohmWXyiisSb1q5JNFPd4OEp2Ekb+3SceOG0B0lTxoIbpxO1kiapPbWp6/V1PXWcLMFW2pyKIUlKr8NJjT3VQbIhTmqhAW0TLHM9eUQb0Hl25fQFR3n6Emk1H8VJiogWRP3ox3Pv9arXQrIhTsomeoLtLbSNjnjZrtwmGdamqs+7ohlMellrz+g5IznSzyNOp0M9OOnFiXNI9Azrky839DokO+qYl8KpstcWR4KlnkyOzZj93sGy5NWTJ59U26lrv8LJN/pUx8lfC6fC5jTYrwOS8xC9MPPSwkmZawzJmOmcRE9fn36EJEoRkbyjCZElK22RYCsfTvxijW4Rsw540aW0VuBZXiqDZD+rcVyKnpRPoEXMvGpZe0qIurxOddnmXkSQuwq9bCSh2UTE8Qr2QJzUNjXW89Dfx3U+idQmcfoTXvc7kjltpANzh3s9Sn5G+XIkyiwv2sX9GyIE1QRnf0JaOhEXMVG7UsJpvmSjd9qvPtqKE2FtWz7q1bTPE40wLpciRqYfzcNCx64n2CtVnWskVI5X9I2kGtkrn1jDOt5qr+O6cnRUJDwHccKMvWVP0Gv6oEUyrLdTN2UaOF1HIr720Vq1J9VgLEHMBU+uCYIgCIIgCGJB4JdrgiAIgiAIglgQSAshrgirj7hwNsKFFqAEVJKcbKhXqSOpht46F2MNZxGRvBPTFiLtWy03WVE6yU6cNOV+iROH5sHrakOq9WgSvy/BOhyJSKAoZCZRExQLhMUxBzYUX6aOzCKb4dJ7pblzlcbvYVwR7QVRX20LGsmRrm0zpreAAjI80fBlWsYKXURk2jLrPIX1NvgkGsY9GPkiPpkUOtdeQ7uaXARrcbQRWa1rca+3XatqhCMs3j/txrry6MCVMQmjoNcghN84DBQj1AUaEjZD0Q60knTgPkuwB5CothLKgKqBNU+VGgSNbttWqkm1Sb16ruGpI7qG6Lu9n7yO+KxKo5C+zqvuYX9PmCX1ezBBfUqrOjLzomuY6z2Otahbu+9JrOPs9X/t3tZX0CCsZnoG+oa+hVGkhgHmKUXTuKylWiBM3+zG8XpLo0D2JNYDlIThVthvjUPQqlT7eRn0N0NfqM2iMjVj4e3pXO1YZ9tqL3srcty/+n7N2NPjnvIJtKDf2DIlagKSY+3zINF5xBjbO+6NmqEqQac7w74xVJpgf67UiJU4aVEk6I8jHxkUH2ttjn1f72MtY6qd67d7DzrkPkHTjCfQZUBHNImvSvWA/bv/98KUmeoeQiJkU5Pk+yfCmItGKYEd96xZQyY0Es8UPLkmCIIgCIIgiAWBX64JgiAIgiAIYkEgLYS4IvhwaQ+hXmvxrGE9hJwLZLOH0JvXg/VayRoKt6oJEB6Arq3NcPeqHLAZ17pt1LQTKzNAixrKICKGjlEDzSSE+YEEVtGjOFw5S4zuMLS4YX88rtJcfKa7qm2M10NbyIzPa65OUAEyE370qhP61hg21Cb8iox5KJykUAmYQzNBGHo6x+IZtB3okEf23EqdQZgda2Ht01OlWBSqIe2pF+Mgpu3Dz3oZKCRWhxzAZ6BeJEV1PB1V3sA8W2oPwripaukWrSqdKTlQGke7EY3LvRlTnYLusKFI6F6arMaPU6tnXivpZPt5NaFrTyWCFvAcq2WvWIGwulmfOqgdmKJyWdNGUEhJo7IigVJRK801lH1EQnjd3+tz9MyDhTboN0Y9BWPTz4JyxeVD8N6q3XSrXqKDgLJhqQm+fVXp8RrSpnooboAG4ekhRoEDVJYkr+5Br4E/jK+XWbUf2OdQtZnOU/Cox/XZtSi0vLep91QJ05SnQcQUuWnD7NEknnP7zMEYoRGOeqCyIWKoIt1YMcZSt2ZJfN94upfZC9if/lmFlzkUsNkcqh+e76CsYC2KICwkY13HNu5bXZf2rumH11GP93b0PJine04Qc8CTa4IgCIIgCIJYEPjlmiAIgiAIgiAWBNJCiCuCt9XWLPbmfgj3J6WQs8+KN5nuyNj3Zic5QnA2pqltDaufwaIa9cyjPSB0iMx9hCRzo1bgFTNA+YBdt1ECgeqEDzPOoZeAgpBO9DqoZdiQOro/J6ToqSZpPFc29DxeQVZ/EdWddavKF2E+MdCqmU3W12tK4XKRQOGpH0MVJjwiYBWPOfeGOVY0QSkfmEeEfCOqRsmm29NuTJgebUHFIZhPhP2G9SnvO5jTiMSKHSKxegrCwLMU1KKY2jOvr/NoKV5x5nBy2bKgTyG87VUhrBlNSSkC6z019BC/l5V2YGkRua4V9gUURQoT1sb40Udv+GHuMdChYCcN6pIlTk3UbrxYd/W0t1WNwuzbCq3FtIHrYfCSwPjDhP1BrYC5CegP1rxlqhQPmIHg+rwV+tHcLxkswSK9MEo62AtatbdBt+Yt2MK67yLjHdA3RqCSVe9jPDNBF/KUD6Ms5O9omMDoswa0KJFwv4423IoMN0HPCG01QIfS/QZ1JXuvehv1rDr3MxjVwLIdBi/WKr10KwTbcPO81vkYraXR75bCgrVrHJdVYUID/dNu/DDUsn0FHQSUHlB5akYlB3u3vN8jc6tBPKAa/h0zG//pFKgIwoIn1wRBEARBEASxIPDLNUEQBEEQBEEsCKSFEFeEmoY7EcK2mdQwA0GY0SuKNKvZ1l5dAPWYUKKlMoiIJCbjfrTlUsCbe7HZSaRSgEx5qFvM6SsUA+rHUhqPMZFZiY0kGodj7Wsog75504ielmmGWCKoET7sb5VNQEfR+UA42So84D2Eg725jqXEzOKQJsLIdl6hsIL1QZu1QaCXDM+2RSQoT2DMIoaeoy+5KoKklkoDkQSdo7Tr1mB4pu3L1PY0dA6zFQ2T1wahrQbGk8Theqvq4mlDnuKgagyHwdQmGbk6i5UGBhH6qmZFUDaZ+rWwVAsdo4bnA33IUHJSVUZJ4nm1+3aaxwoPWak+23+Y+oCOkRnqB9a8caxmTEa1JBjmxGYaXrlCRBKNueM97AlLtUBYve4VgapmNs1917fjG1xfoSKUTmaVetCGNWSpS7wXg+lK1aQjncTPg4gWUse48Orab+2ZOUPoX19x70dqJHqfjJXm4k1YNsLcrT3s9hJoHLlRnvFUNP9cKaKyImY/aB+hyDM06kFLF2Kqlac1mecbVEY8/ULLwoTFXQcVpDI1zuwFVdBJB1B5MuZLLdDM4meWVfAABQgUH/TDKrVAXaS168bVO6vUpXCL+s+whwq9VbOh2W+H8b6YmX9SQBvCWSGeebWJKaN1QjUINJdZM4wHlBWMa7RaorJITHsiiKcDT64JgiAIgiAIYkHgl2uCIAiCIAiCWBBICyGuDFBtgAKIidZlMCdBNr2Gnq3wf/3YhQC9UsQQ4e2qagKy4cWofIAOMi0peeSd8Hciwtk+vLfp6qmZkDVCfWUDAxvKbxy4uCJC9+N1F1u0ZiezKcLasfJEbugLwVSnRFcRCaoRCF1r+zakOdU6J6qggevnqZ8IlCZAFxiEerAOZcObwigRNHdGOg6EnMN89G7oiIihKyitw9IoEMZOey7+mq+1dDxWdgEuJe4FJjQYn0hQyGjuuvX262P2W9ncB3tivB7cIzyVBhQJM2eNXRObFkPFMaHv7Ni1PzqptBbUo9QNEZHmnluPWu7aGpxy7YMOIRLmvrEP2pCGwOt237r5bEHRA7QD63ujxTH3ds7QN2/80cW9ZVQxWjHlA3vB0qGah65ua4IjEtNTQPUCBQD7b7xsroHqz6hKPele59Z86bzuIa3a0hYQ7seaYw9Nzb9auI/RD4wnMn8ZxCYn+N1SajAv7Yt6z2d4zpnJR/f9XjTGO/Axwn3ojYDC9VCaAFUDfc47YV76p9zgOtoPPI+mdg/MYoMY0CqsAgfGk+gQvbmUoTiAPoHnm6XN+XnVOYeaSpl+JhLm1RvFmHs00TX05mOjuH4RkfFKiXak9BRLqQkKINU2emdgAOR+bx6AwxLaqHfda3lPJWEL+P5D2cRTlYZ2nau0JYKYB55cEwRBEARBEMSCwJNr4oow2nB/1TcO9A1zWuKTtPRPNtglLz8ajk+9jrImyvlTE3NKhpPI9gV3+mlPk31CjZav68miJOEkEckqCXSp9aQ30hQuncp5LWtrFQ0tbCSoTaonIuXT0/GmO7W0J7WYonwZYw+nH15nG6f9eoprT9VgOz4r/SkcJX+hEZ9gidMfezSjls6qmz0rJY6KiEzxnnZ/eCrM6/JjPR1r3JGiZezPh9Ah19M5JEva5EvfBhIQh9V+tOraV/eKk9rEJoh5u2StR63X7Smsj5rovGTH1agBkhNrIzcuWJS7cWjdpWgBEtZcR+K+t7fHUVkRkVwTPLG+WPfUWnAjsVM107M+TmGrltVDjcbYJMHxZhaNNVEBYWth7yMSWg+0uaPIggJ721uum5Nn2HPX+9DknkZl3XgQsqnuM5xYox+jNTd2fworIZHRn0YvQxs/1IPTV1hx4zS3eRAK4SQfJ8WIZtj9D01xb58+RBKzDSHFSbbWhh0nonh+ILozz5Icmtg4PT3x+V7oq0bHcP8jMbk2rq4PkhyHJ1QDeq+qe+8TjGtxxEIkaNLjVHy0ZrWjdcg+UVQqY/ZRD40a4qkwi07Z3Usd9uWjuH8i4eTbW7RPY21tkXB6PFmGvnvY9619nORroik05U1gCv2GTrffm2Y8uM7buPuIoxnOnL1MEPPAk2uCIAiCIAiCWBD45ZogCIIgCIIgFgTSQogrgg/HIapmkhWh/ww6BZKDbMJcoEHEIfkkN/qrSIzUhK7+qZb/zGu5Qmu5g2TFOYkmoEgoPaQwYUb0sWxnbfWyYcftE/ZKlAv3YZyQOC/k7PWXNVQ8tVbgJa1nhCltv7xFei1+jXSU67DX1oTRFhIsw9zDghshcNRr65EiHjN0wN319WgeED4FFUQk7IGQ3ASKQqgnyRGCVy1u1aC2iZGop3Ew0mtg6272GxL+8J7SQsTQQsYbmoSK8L69XkP4o+s06VL73NoJettoF2uG8HhhEu9qxzElIgqLK5D0iDZ9cmrXchyQdKnzgnvEWmgjdA678DyMp73t2hitgR6iYzD9mCKJVK+HZrJNepzqHBWrmjQMJonNSQVdpldctkzQC9Z9ZxLDfDKf5p7a5E8ASWygO4AGZZMe8TxqHOjcQ2/aJDhnI9y32kev+Wz06rGuSAScxn0QCcl9uH9qRt/d25wv6XVKYfH0EAn7q39Gn1lgTGXh+VbzOvfxJkrN881rNPs1mEa/2z5C+zzoxYcyeM6C2mOvx/ogQdUnIJr19UmKg/jfhCSiGIH2B31316/edSERF3ONtYQNeUSD0ypbamWfN+1YY9vzoMltLof7e4JE3Oqc4TokzKZ4DNjnY2rvJoK4PHhyTRAEQRAEQRALAr9cEwRBEARBEMSCQFoIcUVA2Bch3yKy5XXbqaXaxIOTLiQPq2SRoDQxK9EprH4oKBL9My5c2rkwrHzmQ/DQ0u0baoLSBY5vctrE7UsuXB6pa8xiSsO0iax80w+t21Mu1NpcrLRwI74O1IbBdcHuG6Hz3hlVAjDO7VAFwHxA23Vq6DaYc1AKQIGxIV6EqEG1QLizfzrc4stPqGazKk20tjWd3lBYYOmcIQpsFRV0/KBKFErJSUw/siNX51T7gXWabATt6RQUGGg294wig8LrQEM9BUogzTAe7Jna2H02OeHm3KoMQKt8tAkVhrC+XskkyaLP7Jj9ODwVRq83AieeHoDQ+xybe68UcwyNcGgcm0cw2oA6h1IDjs8FisDGA0PtR7z/RYKtN4B9NzgR2gA1I/FKOFVdaFAjxsuqKHJcpWyA0gCKhlUt8fVAOeM4Dtvb9kFvCZrPhs7Rj9cD90HzwCpe6PW4t2Ppcldnye58vKprarsMukwT96G+GqWIoSoldaDcYSlkoGgozQf3kb1H85LaCZ6LUFkSERnDCh11z6GwTMtjTmItaddGaZ11HFbxxWuV67ykZg2xB6CuAXpIzdDVoHoyKalsJOb+wZpjLUcb+nyyKlOjmEKGPTBv34HqYdcFaidhzCgcymCflyl23kJejGY7GGRznoFTWylBPA14ck0QBEEQBEEQCwK/XBMEQRAEQRDEgkBaCHFlQDi3ZKUtItJQ5Q9EzhD2tFnbey92VI961xXauN+Fua2pS22caxmlOrQNFWAah0m9yYNpI19yodXlxzSEPkYGvglLQ5lBqQ1QaphZO2pVqoApSbHcjNoWMfbtPVcWdt+eciGBvrAECowxQgFNJhi7uPdbl8L1sFL3oUwY8RwFfsl4raH9j8Oe7W1Dl9HPOueH+nvVwAcW3FNPvzGhYp2rtAtTHvf+ZDUYzaRapzeYaML0IVA/MObxSkwdsfbLGBvmanCds163SgTtJ52UCdbFU3Osikoz3icI17vK3HwsP9rTcSh1xYSsa16lRD+CwYUN00PZAZF8bTNS0imZVmB+bXi8pvOJ/YVw/dKlUAbXYS/b66EQAyWFaQMGPGa/Iayubw1OqjKJoTqBttDah6ICLg5lhuu6zjAJ6akahFEEgcFLMQMVzPS1ZJ8OKk9maDtlc56at/A2yhm6Z45vdHuwdQCqULUeqzJi+66dFJFARYCailWTWHpK1Y+gKGImPy0r8Og+GRpKDoo31IAINB4oDImEtYKBD2hDqSkDWgv2AKhPtbF5hpZMgUCNmRlaiN/Luk6WMuUVakp27pau5il5MNnC5WbdQNkA1QNlUmOKgzVH3Z6OZ1lOSbwZ8raht/hnnvsdazhPCcQ/95sxHUkkzBley4ZC7heqhRDPDDy5JgiCIAiCIIgFgV+uCYIgCIIgCGJBIC2EuCLAzABh/8gsBWE9KF9AAcRE0ja/6CgJZfMWC5i0NPdc2cHZjv+suefoAt5IQf88nHZCXBshYRiItC8M4v5IoGrkK0r56FRDtMj0r030PX2FcoWISL7s2hieXRYRkfoxVC1MTFNpA9nxOKrXVR4b1EC5Y3QiqGsgfJ1rmBKUk8j0AQYbSmGBicRwyyhFQH2hrsoZWsaqDGA+QXeJQudeJQRqCxpGNWYaIXwbU2CsGsxUQ7oYB+qzewk0FwAmMJa2c/yCdREJBi3+qMBGcWHSg/2SVR952G9BOcaY0KjJCgyAJmtqJmPoUFDJ8QoGBZRorKSBGhlBRQKeQWYN82aJtjCKzWlEwlp5QxQzVoTVYQrizVv6ocxI6RwoAzoIjDtsPQi9I0xfM343uL5WUh2x1JHRqrtw6SLMQcJnqLtxGNMp5s1HcxDTyyLlDNBLoPBQIOxvKBLe4Ck2oZkYZRLQA7z5Squ6T0ATwPX147C+UODx94SnGITroRSDewoUp3zJtAXaQqselZ1aCorSFHpn3HWF3s+tffNcUhqIp8fo5d3rQ1vt7ViNw+6l0XoajQPrZJ8Vfq4boHzEyiQiVYpGrtSlRtfsaVBGivgaq2yC60A7slSnBCpK2p/BVhqVtXXBcMe/n1bbaKpRjaeDGJpZbRRfTxCXA0+uCYIgCIIgCGJB4Mk18ZeC1342p5ZTPQHEKbBPQLL22LCmTpDwFusyi4gMT7pT27bqW+Pk2VWuJxel/kBfWURkqtrT+NMRJ8U4WXE/x4lDSFyzp9JIVENSERIcoxPjHpL79BRJT7xqNmlRT2SHZ9wJfP0wJCLiNB39GK+7seOUy1XuR6ltlGy/JWhFI6nJJ08d2FNlieBP6/vmtF7H5u25TT/KVtmZngpbe27Y2fvT+Xl/vls7YRGp71eTWiOLeQnRA0QKRESWnuhrv9x7XpfW5iziFyRv1e3pOPSt42Qru3ZIJJuWEkVnJgHQ2yajXZ90WNUqx6n6eCW2hRYJp3HQ/QWixCz9CKd99gQPp884MQ6JfEYPfYK+VrW4geGmnhLqiTe0jgtjOY3rcQLpAzBm2ZpHcXQruv8QjenYrLX4eiS6+cQynORbO/gGogToY2xvLWJOiJHQmECTOux7XDdegU+21msSAyfLsR27BZKER1tuL3rrdnP/IWkZluiZRjYKEylB4h9swpG0mJsTYySKLz+p0RzsSfM88BE9vR4a3fVeGA9uDeyPJPIL1+szJFHHCagiJhE5Q324R6pRSZyA10sJ8SIiddiX69hRj9Wgxr610a0yMOc4nbb7vqmJrj6ao6faM/MPCdrAfvNeDmZ97J4hiKcDT64JgiAIgiAIYkHgl2uCIAiCIAiCWBBICyGuCEiQSeaE93zyWMna3CaIIaSLEDF0lGuGmtBG2BchwJkN8SqNA3q9SjmB1rGtE4lPXv/YUD4QGq6ppffMaxMbLWylbGSHcxIRFVPV4Ib+MOgdVlMbIdby3IlYnWtoEut4WnG4XCQkyKEthC9FRNJBEpXxFuc7gYLiw8e6ZoOTrkzjOLSBUGxTk6Os9nRzP7YpxzigKy4SHiigh+QdpWwYqkXNJ8XGNuoWsJH3NvegMRjd7d71sLd3dJ3+GacxbpMwc7/PYj1lEZE6bJ9HSKBSasBqeCz6RD2f1Od+hx20SAgx+/C6bmWbJIiQtQ+dQyPYJF2BtpC39XelGDUPDU0FexlUB5OUh4QshPsTZS9YOgfa9VQTyBmvmHnp6vU6dyFc74uEhMzSK/ogEuzTk05SGQfmFc8PUEAsBcZrcntr9Oo9gT5ib3sah2UmlG5bn6BpKB+zzP3cPe3mfPkp2Jibe0zXCvvDJhDOSjQb1G3vddyLeDb4Z4ZJfPUJg0msPV0Lt7G/7z1lRPdd+2Loj6cP6b7rXKgmBGNdO9t4rtgEafQnTm5FIquISX7WsU5xr5m597SSVnxvjM1+g9W8Z6WANmaet3VYs3ufA/N8xb00wrNCKn31tJhBnHCamzEXHdwT8VgtxQjzSRBfC9wpBEEQBEEQBLEg8Ms1QRAEQRAEQSwIpIUQV4TRhgvhty+67PhiJdAx0r57L+vFurRWXxpW2cjMniitor5v7MIRFpynhQ291BVXz3RD7dSPTYhWQ8T1o4m2qfbhJuQMbWb8dQm6ybQZKApj1ZoGbSBTConVUQb9IYVusKqfZKqAYRsZbzm1kMJo6GKsXh+7Uf17F3SSfFnr1vm1Si0ArvchaENz8Vnwk1grtrFvYs4z6OxqH01IHeF02NFDQcOGvhEGTjTUC/WVWWYUEZZVdWQAjWNwC2yYHuWLqD92LzUPdZ8hvD6uUgsQVvfzsmtD5wgxq9Z5SZXCjh+UBHxmVRO8HrRXbdB6DaUAczVcV43vA7XH3rLW87H6AlQ6rDU56EKFiqZM5yiJYH3LIX03HxLDh9TDW9Ms/nCeZTU0r/EZ6ERWjQV1Y39Mlkw/xknUVjIt0TokqHyMNmLdYrvfQDOrKa0DVth1oyjiw/ozKKyojXk73IfYJ51Lbr9l3SpVAoB9+XAjLAwUQPDMma27zyx1y6tgKE0HdJeksDcZaC6iZWMlGxGjmqKKR/WjWClFJGhPg6aTKJUl0q3Xnwebbn7bO0EFpeb3g/sMe9BakoP2hL7NQHcxih7e2lzHjrVoTYzyjK4Z9pSnfFh6F6hNiVKUzGMS8zFeTaP+jM1+a+3Het+Yh9Q8+sqW8bU5Xg6NY6qFEM8MPLkmCIIgCIIgiAWBX64JgiAIgiAIYkEgLYS4IiBMilB+czt4K0/WHEUDNt8Ipk3WA3WkfqRxOA3tJhqaTQpjZFJTlY8+lDyqahKpUiMyVZyYbIQ2sq4LzY41NAuVi5mNWKvqBCgFaNOqY/jQ4RAW2hqiNbFVlPdqH0p1KNptX6ahcwQTGvsnrQ+Z6xzNUxAAFaKx664HzQWmFCIijcPY2AI0iMLQTLyCAQwyvPGGUXPBZ2o5jdCzSDC4Qca8nx8TgsccQQEElBYbXocKS5kCM14PBjEIyWZKl0Fb1hY9LdmDe6WGSI0FIfhqm57CoC/o48TYUVvjE5FAIUmN0ct4CRbcJUWSsAU8FQBh6ElJWUQk7E9cP1IKSTlc7cqCYhDe81bZWfyZteCerMT1ZD1UaN7UKULYH21Z6gjaskok5fGAPpV64xrTREktBAYtyZFRRtEfQY/xduVWRQKGIVBK0RB+a988T2AihT6DWmP6XlfLbViawz4cZi4isdKGrU8k7D3snfqhPnNS+zzBfIK+oJQWo6QD9ZfGUayWUxjLd09fGsR0ENsf3Bu1dtyWRR1W4rquVoED98ZoTZ/zR1VL8kkNxjRFNAd2PFgz9Ceo/lSfodgTMJWZR3kCtcjupWRai95T5oi096yRF8rqWL3VeXhu+jXX9mEoZFVy0uHlTWwIwoIn1wRBEARBEASxIFw1X64/85nPyE//9E/L29/+djl37pwkSSLJHN3hMn7lV35FvvVbv1WWl5dlc3NTvud7vkfuvvvub0CPCYIgCIIgiOcarhpayAc+8AH5zd/8zSu65j3veY98+MMflna7LW9605tkOBzKxz/+cfm93/s9ueuuu+Rtb3vb16ez1zAQOhxtufB8/aj691nRUaqHhiKbF7vh+vV2VBZh+mwSwq8JaBhQrDBhRrwHIxSvZDAI4T20j3Clz/Y2f4tB1QNGJuhr1jWmKwgDQ4VhpIoerUBTqSl9o9aObyVQU1x591nRVurIcYivz+qx0Y2H7WsdVBFVJFCqBAxn7BhzzP2cvzs9fULD0/jj1IaM04EqKXhaRzU0i1Bq0amGnGu6jqDboD82VAzqCwwzWjtuPtpPBorR6KSjGMGAyBt/mHAy6oSCDcLKqVEUgZoEKDQzs0yoc7QeUz3seBAGn5W2+WjVqEBonTM18il0i0+WQnlPl/DmMe41G4QyeSc2mCnTVVxf3WtZrUNEZAojF20ftBCrNoI1zHSqEfIuWqFM4yimg2A+IuMP3d4w5YDqh10f0A1w/2SGSjPcgMKLew80jkjNAgZCul9AAbGqGFAUGet6tNUQxRoBgeqBZ0beipVfRERy3YuJp065972piwSqksyjNmifvKKOtjFeq/4Ti/sHewo0LztG3OvjjYaUUTY2mukezQ1lA/sCFAfUO21UDYUCncq24tpo7+qcazcavWm5iJ+XaT2mZ4mI1LtQBIrVZEBJEwkKHN5oaRLTeNybs2gc9h7Nm6Bl6XhgGGX2PQyAytQpa0wU6GX6b8Gwut/6p66ar0zEs4yrZqd8+7d/u9xxxx3yqle9Sl71qlfJTTfdJKPR6LLlP/GJT8iHP/xh2draknvuuUduu+02ERG555575LWvfa28613vkte+9rWyvr7+DRoBQRAEQRAEca3jqvly/WM/9mNXVP5nfuZnRETkJ37iJ/wXaxH3Jf3v/b2/Jz/3cz8nv/RLvyQ/+qM/utB+EgRBEARBEM9dXDVfrq8Eg8FAPvnJT4qIyDve8Y7K5+94xzvk537u5+RjH/sYv1xfIda/eCQiIvmqizlbgX0w+KHkMTzdrpSBcUPWU2rDoZqddEL4c1bT8GBJmUQk0BagoFHT3ydrQTYBBjFSi7kR2WHZQUNkfKIT/W7NbDy1A1n+DVALQn+CIYqqayB0PLMxTQeEG0FJEQmmOhhr1nX1WFULXDdR45y6qrFYhYcZzCpKod6I8jECTcb9XsNHZppgzgODl0g9ZQqVER1rgXiylWHBmsV0ityoHfj+DBHi1TGYtmp5af6gWNGvmgUhTA5Kgm2rTLcpbOi81ARC1kW9+h7G4c09TLQe9QxP6Gdz6Bj5sob7B2pms335etA+qB9ijTuUzpEvVa/He/mKrnND53cU5rWxB0UEiZAYsZmJ0lMaXdBDtO2hMW/RWwyfgd6RGwUOr8ahL629cD3oJIlfM6V+9A19qBHfv7i3spmh/eieXH1YlYVg5GPWuWwEA6UIayASKtRrdM6tgkbroIj6YSlGMsUzQpUvdFyWeoK++TFDWeQoTH6SK2VqDfe6Pg/MvTHxqhaqbKK0BXvPYN/6/TuHygI6BtRHytQnW77eR/9mlc88ZcubF1WpFphHtJEauhmeY42DmL5jzaA8z21WUuSRMNeJPrqLKpPGGJphXVBvKFMbz+ZegzUQEWlfookM8cxw1SQ0Xgm+/OUvy2g0kpMnT8q5c+cqn7/yla8UEZH77rvvG901giAIgiAI4hrGNXly/dhjj4mIzP1iLSKytLQk6+vrsr+/L8fHx7KysjK3nMXtt98+9/0HH3xQbr311r98Z68yINENSWk4gRaxmtF6CqVar1Ojo9zccRlcOMGeNTShbxjqKdTmG9fZ00fYYnudaj1NtrrQE72+9ZQT8S1glW70snFKWj90RxhT7QdObm0bkzXVy951R11pLxx5pZr8leR6wrTkji2TkdXHjU9trVaz13PW5ERoQFub72SsdSEpCHM2CicqKU4C89JpcFo9wfPzCgv4iT3xqkXX2RN0zDESRn3/bJKh9ilvq3U8rNuNdjRO+TCe0WYj6p+ISHNvHPU1JIqFenx5fcGJmR0PEhmRcDfvdG5aegri5NaNQ5tAIhSWzh6IIzFtWV/X9IRzxSS1jlQT+Ci2s7Yauug13kOC4rR66O/7NTphEoFXXXupWoFP1YK+dmiS+zS32Cex6Va2p+yZBnhwco6TdDsvzcNZ1NeRJqM1D409vWojI1FtHnwbeko9Wg2DRZ+gt12Dtv6+TV7W/aFNQJvY2lQXbSQET7Vfuo/r8Ym2iEiCE14kYQ6mlTI+imEPVvUVp8mF3kfRyfeu6/fgVKzbn7fD74gI4ATf31s2OU9Pw5GMN8+SO+kh0VOTqTWKkJil8DrOeqJet5repZNuJPVFp8nlyE8j1ugWCafQdY0CQkvanhIjQoF1QgKqfR74ZFQtY+/xkJipCfT6TC5M5KOshZ/mc9YVp/3lD0x2eN65Jr8yEV8HXJMn192u+xek0+lctszSkouhHh8ff0P6RBAEQRAEQVz74J9hzxD333//3Pcvd6JNEARBEARBPPdwTX65Xl528dl+v3/ZMr2eoww8E0oIEQDqBxJlhqeCQO7Swy7ZsdDkRCTQQfNVRCRRrejxWRdVQIJMMw+hxEypGp5OYUKR3qpb6SGwP7f0hbomBR6+eFVERFYedXFua+Vd06RLJBdCr9omX6L/6XnVdV5CbNboXPfirKhkAtviaqg21fatru3Eh6w11F1DiNTMGagaGRL4MGYbQgftIKa5FCZ5Em2ADgJqzLgT5i4bxv2O9MNbsKov2Tab5E2UQdjWJxeaxMrudW786w/EFCGsm2sEFt5Ko9B9kneqwTaEj5FUZ3VpETL29tjWgjuPP0MiVGGk2Ms60N4u3IbXV1FYX1tK7clMMumT9fj6kpa1SKAEgJLgaQemLVBP8hVNkNwKCbhpplSpqY71khtI/ahKf4BONZLyUK9ICJ0PNzTJVrW4671QxttQQ4peg4SFuQ87O9OojLVP9zSOZd3TBa43luTQfFZ97ONzbjFG66GNpYtxkmE5SdYCzyzQVOr9Ocl5oEMgedfcDsMN0DAwLkNbKNlrIwmuc8Ho5iMBdxJTFCwdo3cWzwZkzmLyQlvjFTwzlP7TKOmji0jRiCkjGWy7DYXLewUgSXBOEmjzEJmrOgdb4XnS2kNis1LbdBz2Hh2ccP1o78Y0k5mdO+jNr8WJmeNl81waxAmilq4z3Myi90D3SQ31BM/ZRPdHNo6pNSKBquKfsxOMK9C75hoIEMQcXJO0kBtvvFFERJ544om5n/d6PTk4OJCNjQ1+uSYIgiAIgiAWhmvyy/ULX/hCaTabsr29LU8++WTl889+9rMiInLHHXd8o7tGEARBEARBXMO4Jmkh7XZbXv/618tv//Zvy6//+q/Le97znujzu+66S0RE3vrWtz4Lvbu60T/jYufQJG1dCtrRxZL7rAYtYv3TrfV4KDM57eLPzV0XIz66xcWTG4dG43istJBWdXtCRQNhW1g013eCjzToJGtfgVpJbD8uEmzOoUYBlQCrTDJed4oXddXizg6qOtnejl1vpWSsahnG5h0h68FZxy1o7YRQcQOqIAgZG9UUAGoang4CqoUJUXoN6wxqFErdMKojoI6ANuE1eK3OtdadKW1GjMa4t02fxpQPa3kdtKencT2GbrN8QSlFJ5vaHygKVEOuUDSAxnJmbJMR4gYVYbAV2yCLBIULhIjHRvEClAjQFiYaxLLKGbNU53EMmoqWMVq6oFh4+sMeaC5VFQivOlJdQr8MoKt4tRCrl92JtYWnB0HfvWiq+suhu6Cxn0T1uXGgLAboXhomrxt9hWoI9KA9/UVExmvude1BtclWDWvYmouE9Wgcg0ZkaDK4BZTSkBmKRrkM6AqgmVhNblAHoK6BNqwSCMrgMzsfQKa67thLXqfd0DFaO9CgB3UkXO/1taEkAsqVoXeBNgGqBq6JKW1KV4DKiO7/zoXAqZnV3Pr6PaB9jDS109K9inGZDQfajVfQMWPF/TL1qkHQPg9tQJ0nLelDW/Wg1n5MHYMaUW0cqDC5jrG1F1PS7DrhGYE9MTK28qANlZVdLD3MewUsz1E9UeCexrpC/7uWh7a89wFBfA1ckyfXIiLvfe97RUTkgx/8oDzwwAP+/XvuuUd+4Rd+QdbX1+UHf/AHn63uEQRBEARBENcgrpqT69/6rd+SD3zgA/738dj9CfvqV7/av/e+971P3vKWt4iIyBve8AZ597vfLR/+8Ifl5S9/ubzxjW+U8XgsH//4x2U2m8kv//Ivy/r6+jd0DARBEARBEMS1javmy/X29rbce++9lffte9vb29FnP/uzPysvf/nL5SMf+Yh8/OMfl0ajIW94wxvkfe97n7zmNa/5uvf5WkTnfGwzbG15UzVCgWmLD/3VTNhzx0kO9G5xcWWE8qwxizdigRqFUfmYLiF2B+cADUGaGAxMbMohyJpRtfCGNwkUEVzfbbgQxi7eEllpJVC3EBFp6HhgZlM2cXHtu3oQFs72g4oNriv3K+2GMHBrDDtrpXVoqNlm5SeFjkdNfjAOSwsJtuU6P40SBURC+NT338y9VznRuuvHSrsxewAGMylMfpRWMjWW8aCM1LVv6Rix9DAPUI1AKB/UiGJqDV405F5RO6hSDEAPsWoh3ohlQ8t7G2cTHh9iHiXqR2oYQqjTm68ohSStsoiC5Xq1i55WgiGirdwoeaBvM9BMhqavAxgs6e9GncP3VdsAtQL9SUxE3t9Sekt6G2ijFgIFEczreGUOVaJkfjPpVMP0COlj7qHE4dqNFSY8tcYyg1TZATQQ0Cm8yoWps6zCYmkqMFsJ5jqqPNG0wd040Guvh+JMMN6pGrNAgcPbdYPaZuYeqhjZKLaT758J9B9roOKumUbjsuPwpivoq7m0rDJi64X5E+gXUHOxbYCK401cvIqQVWHRdVFVDm+As2Qt0qPheCMha1q0pLbjWJeaURvxJkVJbCKVmLF6SpC2hbqtYgzmpjaCGow+Z40RUNEM60AQT4er5sv1nXfeKXfeeec37DqCIAiCIAiCuFJcs5xrgiAIgiAIgvhG46o5uSb+aqG+5+LCiaVaKF0gO9Ksek+jMPFhpVS0n9Lr1XRlsh7MaEBXqB+7uHRiFCJA8ZhpyA5UBWT7i4TwZNqP1UJqA0M9abrratp+vgy6Segq6A6NXUgsaLgxt6HrOPvcU1pMNjzKIBw87QSpCU8jUerItOW4CoMbgtpI86Kbq2BYoyY9/UDnyGFwgwjpLA63iwTKCUx9EHavH4e+gvKSwADIUGAQKvZjhbmNoYXAgAFmMp5qYVVY1uLHDkLv0zlPIxhLIHyL8LvrT1wGNI9aXjX3mGcQM1lWZYllDTUPYM4RyviffchYonGJBAOVxqF+BDaUUTuA4Ufejmkmth4oeFT6amgQoHqAzhQpXyA8D4GGLK7XtgszG4T0h5uhTP242n9X2PxYMriB2ocNxSe9uD/j1TBYUGf8uFRxwiq9DNUsptGFQUxMERIR6Z12ZdYfcp2tK8XJhvLLVCcwyubRKKDiMtXroVIhYugxXb03DGWkeRRTJEABmRj6g7//QT3T38drJf6MGLrcuPrMQT1Qs8BYrakN5qi16/oKRRJ7H3qVH4zdKKx4uhxUWAqobYS+DrbUIOZSHvVntB7qaavCCubMGk5VoJeB0hMp2JRMbCLlmVFpffUjqxjjx6VLBtUTa3qUaZ3DE6r206s6EY3mrBVBzANPrgmCIAiCIAhiQeCXa4IgCIIgCIJYEEgLIa4IUJ8oVpX+YAwDElWISAYa28VnDRPKh8GMqlCMT7mYem1ksvt3VU1D6RRJYTLuUxfvBO2iuQ0zmBArrmn7UBZBuHS6Fqgnno6BLPIJDCJM2E/vjlzHmqqiSDI08XJPtVAzGaVI2HBj43CiY8+jti0mm24eRluqtBJl3LuxguoxWXZtNY1xTurVT/R3mMoY8xZP21EKTYK1NGY96LdXWjHr4g1Q0JYa8NhQcYBeP4nNI1zflCLRif+2t5SCvBmHdEGnsMoC45VSiyVFD5FAiZioAUq+bCg9y7qOfdf/xgFC4aZdpXw097WP1aXzVA1cl06qoW/0H2UL3YqWCoO+elMPbSstqSmIVBUWRIw6h07daK1KDaofwxQk7nvz0PZVmy8ZzaSBVeXb8lSccayEIVJVfImMYrxih9bThNqHNUaKFUVAK7Fr0LkU38egNiRz2AdlusB0jpEIxoVnxsxsURi8zLLqdSiP/jf3lJ6yVL03oEYBGoU1P8F9AjpGUVb7MH1KlS6XYlwto8hzFNM5BAZU5rk08yosOs+GMuLVfXSoMHOammd58wDUMVVo2Xc3YL1n+jGJbxj/XLSUHDwjQA/TKbP3ERRBQBmxlA/MDfaAN6yyywSxFKhcaRvjZUv7wXq4wnWlN+bL4SZdumBuAoJ4GvDkmiAIgiAIgiAWBJ5cE1eE8YaerI7i5DYRkXSIE9GSFbc5qcXJ8LTp6mle6Loyxva7WNPT7DG0p8PpD/SwrY2viEjaDycK5c9qc05ocaKDk2achNdGVW9k36aebOQb4QQ82x9qX3U+NHkKCZ8iwRYedupZr6qTjZPmg1vdWK/7A5PNU9Kchr500TH22jiJL5/YRf7aeqo3KZ3AmSJYQ5ukCFR0h3Wszf2wvtAL9k1qmcJqxeL0qqJPHeATyZAghsREk5CI5LeJ6kDj5Nom8I3Xtf3r3BHtrLAZnnpSfYw9qfUemDbG8atPiDo2kQVvBx+fiEZJV8PSKfJszuknTpMHcZu5HfMc7Wp/fRKXT/SNetcUKulao+xszjGLT56sVftRrs/bwdtExRmuq2qM13X+BidKfTT7N/VW7bEmsU1qxXtICvS62aYenAzjZBdT3zCJvFhDrB3KWkvx8j61J6s4Sa3BNrwRt+XaiOvx95EphARrby0+hOayOWHF9Xnc1jwMNzRxu0D0IIzHJ3pqPfZZPtGTauxhJE1a+3OMp7nvFiqHxv3AJFrjvUms/18bV++fMbTCdV6hdy0SNLVhZT83MpFBX15P7U1yLOYca4Y2kSwrEtYa89A/6zZ1eztUlJRO4gnicuDJNUEQBEEQBEEsCPxyTRAEQRAEQRALAmkhxBXBW/hqyLh+FOgYCJmBFiKw9jbUhNGm0kF2NEyPxJnM6MGONAynVIfZaqBhFEorqSG5UKkFRT1cD0pDejSKykTJitonJAdC9zdKJASdpANNbMR1Q5mpfoZkzpomwwzPLIUxr7t2OxfcuEAFETH259rH6/6oq++bvoJFoVk46ZHjDeQbncp4EA8voO1tEhJBA5mqdrXX6bXRbmhfH8Y29/Z6H0aek9gFe2HMUe+Mzp2Z1wx6xUgCg76zSWL0SXV4QiWlVwk6zl5bWFkyE2MXPrvRzVVW02TQXqDSpDvu58aR9l23naVeeCvlp4kGI+TsEyqz6jWBWhFbTtuExkypEd5qWreAtR2HBjZoHUXLfFZyZsY4bIInKCcoi4RN2wbewyvasvV4a3QkNmo/6naeSqH7xDCuvOY1qCOduH+2vaBBDQpJqBga50ius/vV16P7HElxoBTkhguD60ANsImZgKcypPF9ICKSlqhSuB9nc5ImQeMALaTeNTQK9QQAlQV7qzCJhPgMzxVQYXpnLI3CtdHeBVUPdBnz7AJ1RfdCZqzak9L4fdKlud6XL2lXT9bCRgFdJj2Mx2OpLBV7e59AG+qFTnaiz0BLDUJiNJIdRxv6TO9Xb1qvY660H6tlXabHNPe1vvUwntb20/CyCMKAJ9cEQRAEQRAEsSDwyzVBEARBEARBLAikhRBXBITFoK5hNahBcRidcXH5xp5T0hgbdY3WtqprqLoH9J3rw26lnumKvs4LIU5jL2OrFlIsuzgndK59aNaEL0EHgfIG7MNzQ3Vo7LmxTuuxXbi1HQcFJaKciEhzL4QPG/ug0kyi8dk+JVAlUJrM8FTLXO/GBuv3yQk3v/X9qiKJtySHssfUZvdDAzgO0VpFBNBI8hWdj04YF/S6J6oI4pUMTOjbR9oxVxratVbaU2+fDi3hWHvZfab1ZbhGtM1QBpQErxKiVJLJhtFMz1Rl4KL7MDMavOkw1s5GPZbOgRC1VyfwWt+mDMpDY1zrGa1ZjXGJge1r2/KF3QuoMVZ321NPGuWLqoomXkvaqCbgOAXzi8/Ga+HeyJeg7KDh8Z1apa9+rqCmAgqKnRfMlbZlaSsoB3qJn2er3+0t3lXZYQDKU1WRBBSnsN8M/UHnvnEc0wRqRu3DU55KqhaJeWZ4FaI5lJHBaTfI1q7b6GNVugBdxdWp97rOHZ5LRTNsDjzfPC1lFtPXXGPxeHBN51KVggKAGmOfgaC5FB3Ylocb0M+VlrfKKsB4TfX2D+J1aRyFm314g1v0Wc3NT3tHlUVs3/Q50DxQXWntT81Os98f0OQOH4HagT3UOFItbOuvoGMdbijtZog+h+fBZEP7ofQS9Kt+HHo7bZZvZIKYD55cEwRBEARBEMSCwC/XBEEQBEEQBLEgkBZCXBHGqy68l/VV6aET6As+fLvTj65pXgiGKOPTjtKQIVP+EiQSQvlk6GJ+WddxAEbXrfnPkOWdqroBQquzzNqfq9KFms8knoYQGqkfqUV6A2YRGvY0yeBQAMnUsh3h22IptIU66weqfoI2rA20UiwQerYmC+MtpSt0Y3pKczfEPWsw2AEFpmfj/HGZfFlpNvs6EEPZgIlOptcXbRcGhh26SDCxqI3VEtxYImM+0gHCsLF6ggUMIBDeLgzlAzSQWYmiYA03vA016CCwGDfrMy1RRjxNZBTWOX/cqbakOuWggkQAfQJW3EaBI1VTFB9GRqh5TjUYh1fVMGFtr2ACEw1ty5q3INSNcdWPS/WZz/ycmSh12QgGlIvJknmv5JE0Xncdalwf5ELyC7qHDkEl0P7Ze6NEl/FrGa2ze/VW72YcnmKCrQ1qz5zrMS+Tjt7HhrrV2XH7dbwS24Tjd9t/rCEMsKwpTA71CPQPFuXmmWHtxUVi2/L2tlIa1GwFKiaNw3BvgZpRtumemY0CsyG0BeoKLLlFwtylShODwohVOIGaRjEDpUfpFKYePI8wZ6390Fc8H8eqlIE5z3phAzXxzNRxeMqFUenAnIMqki9lUX0iYZ3xPMEzHbQzEWNC5fdb1dt80o7VYDJzPZ4tLaXpoH1LaYMhEegyFUqYGDUYgvga4Mk1QRAEQRAEQSwI/HJNEARBEARBEAsCaSHEFSEbxqHAxlGgKIzVPGB8woWVoRYy2QwyAY1LLvw8bZsYcQnJSEOIp1ZFRCQdhlDk8c2uboQnQVWwYULvN6JhxhxtmYhevhRnfddgWGMMb2pqbJN3lE7RhVpG6DvCp2grAT3DGN/UD908QNHDAvQN0EkyVSKBGoury81fdqyqIQO9plWtrwYaB+gyZjxZP+YENHdV+cWGk5diCss0s2HxetQGaDI2xAuzh7qGhn142ig8TL1Kgvt9vIa+m85pl2BuAnUKq3yBn6GqgRnLjk3IGEIxutyWduCv71Tr9t3IcJ2G0LWR8YopUzqiSKrCCp4OAmpEDpqIjTKDIYV+KZ3DqoVAEcXTMOw2TuLPMFarrDBZVtrBqu4zNbwZXQyGRM3dNBoHxmzbwpALUHFA47FCOLX41c6Lp4rAKEfH3jwIZaDwMC3RF+qW2gAPqpJhyHgpLEp7T9UjvDpNTLmwdWOdvaKH2dueJgBqgFUSKSngtHeVQmWUeIrSWRaUSSzy5fi5NGnGVAeRQHGY6DOsrkoetq/pWMc4hvoJpFtCPTW9Vws1lZqYZ2KiVBNQM4LBihmD/jhai6keUEqJ+pZCMWkaX2zG0z/tNmx7G5MfmhK0D1aWUYMBhQbUE5jI5OaZ46k0oNmoAY79d8CbFXnqFxSXrGKMEMQzAk+uCYIgCIIgCGJB4JdrgiAIgiAIglgQSAshrghQx4DZyMwaiOjPEw3TZV3NYjeKEzBQSVSVYtaCm0StUiY9dPHwWTPQMNa+7CQUZqArgNJg6A+gZMB0BdSIWmGy2FUxAwYxoIXYUG8IR7vPeje4mHz7UoizT1vuelBFGqoaYusZb7rroCgybYbbDlSaxoGrM8kRi5eAUoa6N6GZ2TR2GLEgHKzUi05oa3DStQXTBYyvuRf4EDBVQIjUUknSUWx64efHKqNoxj4+80YZxtBhuKlj31AFAyh4WLUQKEUEoZkKQHsAjaJ+iD6EMl6lQzFtGArMGTX1KVzDo00Nsx8ZVRmlpXg1iw7qNfukqePoY+61X9Y4R/uat2MlgtrI0GVKTKlg8BLeA50C4Wm0LWLmTOfTX78R9v20hTC/rnM/Noqx13kjFd2Sll6Ctjw9ROfcUkfQV6iM2PnIduM2ApcrlAlmQ1qf7iFLyWntxeYxeQNGIMYYSakAoD+NV3SdDZUEdCZ//2BPG+pIohQJr1Bknn1edQgmNqNppQwoIoGuVjUkwZihRJKok4pVNhmvq5KPKpH0rlcDKVNd56LSfvTZAdoc1IBERCbL+uxRaptVQ/EGQJiPGWgu5np95oFGgbHj+WLbL6tsxMpA7pfOeX0GzjBmsyfH0+g9+yz3ikTa/9aeG7s1iPGUHqWTTJvVc0XQhjBm0FMs7W14kl+ZiGcGnlwTBEEQBEEQxILAP8OIKwKS+nCCkOThBKF1yfny+qQX6ONaa3JN6quN9ERFT6DzlZBphhPeYs0dEybmlAKnpjgJyTWZxp6e4vTHXzfnT0icWPt69QS6Zk5mcBqMk5XWjp50muRJnASlyHFKY71dEZHaOM6UsychsEnvX6en4hdje3kRc8quJ94T1c3OjN61twVWDW3YsRfGOr6hGq84QcMpVGQvXzpJnCxl5rM4kQvJQdAfFgmnnj6pTk8d7Qny8LS7busFOyIisv2oO8puboc1ybyOuXuF7blNHszK7+E01yRtQSt6dEJPrE6Evbi06ip4/pbrx/1PnXH19UNyH/bSDMmXqgudnQnW8zM9BZ6N9ah2ohrwS9XTbRzZwTZ83mm9T1jTE1p7ol00kViGz6xGskaOzrjK22uaSDsOazjbdQOpH6omsQ4jSiYtwSd12lNlaHqjaqzBHIt0nFinA/NZKekT7Ue639DCP0QZnDxXE1Zxsot5ydsmkddbs8enwvY+RjIfPsPzwOrVj9c1cQ/50eb6ziW9R3HyrInfiEyJhHsUp6c+idKcomb9Iq4bEQ4zX9DCHm7Cfhx619YsIG7Ta8ubhMRyH+uH4XkyQXL6siu/9JSehOc2+ufea+y798Yb1QRrAM8hn0RqltDrjjfiB7U9Jccpv0/sNPsM8+efq62SnriIT8Avt1mzuvlN3Mfud78G5tqlp+ZkPRPEHPDkmiAIgiAIgiAWBH65JgiCIAiCIIgFgbQQ4oowXnOhPyTB5MYKvLGrCYjQkR0ojcIkG/oEG6VlIMxY3x+GMtCc7qjmchroAtCDzjVsizBy41L1+vGmJjaqnqzVla3NkASTRf3KTQIgtKJ9eFGvaRyaGDqSaVRXF3SZ2ZxkHIQXrWYtNGZBB0FodNY0Y0bioNaTDqFra5JAvS02wq9I0AxtYTw+/Ar9YTMv0BT3CVAmJIq6x6vxnNnxILkJdJC8g4TGUCY57daqWQdfINawFQl0BdBBPF3FjgeUgJINem4SGnGdT/Dsh/XtqcD1fcfXu7JKmcjGVTFbUDxqJ9063XH9U/6zz/z5LSIiUtfr8hUkjFbFiT29BRFnE97GXp44eXcpWkpl6RhOQFvXfqT3j7F6l3Nu0m46se/GN3aTvv1U4OQgWTMt0TCi5MuStbqn+Bgb9aITr1m9CzpEKINESKyBpXzMSjbwSPiMNL2RxAcNeVxjpgNrjqp9fYb1NVqN7cHTEbL1TLKi/ghqBShPM5NIiPfqXdVw74QB4Z4A5Qo0CJvIZzWvXeU65kEYkLVbdxfBplsqaO3mURlrx57qswJ0CrQRPYt1PkBFsfr9gUKjVJx1bIpw/0DDGmUjGkapnpEmYbZ38mqZBvTHlda0BG3v0BYoeVhDa1uONWscgeZWvX/93gP1Cs/OyNpcX0vX1sy61fLSGhLEZcCTa4IgCIIgCIJYEPjlmiAIgiAIgiAWBNJCiCtC2UK7YegcHshMB+XC2JdD3zpfVtUQaFCPQxmE7GoDaLWacGfXxfGaXbUAb7t6rJ6sJDGNAnG+wihfpAMoZ5QUM0w93jrYW/9q2HI1cByy41g9BdraNmyZ1GI6RjooSSVIyNj3Fs9HgXoyXnd0hclKfLtCG9u1r3bFUAvB74byMZ3VojKgpKQmnJt3oMYi0Zhd/2PdYegXx6HVeK4Qpoe9tYjI6ElH1zn/hFPnqOeuLDSlbfsArNKtRXnZXhv0kMzUA7oB6Bi1S4ZuU8NY61E99nqv3wxVDpXM+Nynb/VlUq8pXqKDGJ5L1lO6Tw0UB91LK2agm249Z4Xupcztk+tPHvoiu8eOmzGcuYGtnAoT2+u5SXr0C2d1zK6NxsRKksRdA8XCqrlg7kHlyVeV6rAc9m2tH2uCl1ViRMQrOqANw0jwtBS/zvq7p2xIoBTh/oWddb1vyrSh3zyLXotVQ8uCKkc9pjpYRRFQEhpKdQDdy1q2J6DJgAZhlg7PqMObVcHjUJ9TB4UpE9Mm5ulcey1s3Ed6b4hRGJrqPEDXGUopoE6ImOcZGDBZ9RytULrdQLWb7bx6O/lZrDZi9aELfVakSuUBzaRmlI5ANcF6e9qNWWfM5wy0O10Dq6KC9osytU3C+mLvYV2seoqnEpW/8VRvDal3oZNd8kAwYySIrwWeXBMEQRAEQRDEgsAv1wRBEARBEASxIJAWQlwREK5EWG54IhhutJ+CiQxkHDR8aqgFMJHxMWIYZqy1fBmECRs7Gm801ugIUxYbajCjNJOaNapZcbH8xkXnIFKstbVfJqQJUwKYLCRQtTCh4kRD+RqeBp3DmkeM1914YMiAcVkr4VqpjUg1QatqqIHDZDmr9BVmMaBxIH4JpRORoPKB99B+1qtSUKYa7vSUGKNQAFUBmGjMsmroHCHdYk5Wft6qvlfG0hMa2oXKB6gbxtABpiKw0IZ6SB62ib9upHbqSR6XFTEKExoxhzGLbaNsnGPt06HYkWh4PrnoqBeWLlC041BxOogt6EVMyFppJfkp16EX3hJURx7e3hIRkXHfhdJPbbn9e9Pqni+z3nSD++LIUWp6j6yGdnvxWYlXwDBmNqCloI8z2LobG3UY3kyX3CATpbkkQ7OnYbGuc+gpOXPMaILVe3gPVtll5J3qnHnVELxYOoauA6gRMDTKTFtlitF4RekUhpUBu/QEJiegH5j9n6r9eeGpDaFi3CdrD7tN2DuTVa7H/Q8lH68SMkeAAuPBfdw4MJSPPI0+w/zC5EZEpLmv5fV5DVMYq8jTOHR99QY4c6gj/nnmFTkCfQ+KKOgHFEqiy7VvzQNYrFepMKDWQWEJZaZFlTqCNZgsG8oV3luKVWGskZd/ZrVKJl+2DZ1z0HUwnmhe+I2JeIbgyTVBEARBEARBLAj8ck0QBEEQBEEQCwKDHMQVAdSEybKaExjaweiEi9lDVQImA9acAAYoCI3WRmpaYkJv2e4wes8a1WSHLt4LoxiELe31taGLTReraiKjlJFiqRnKeEpETJHIl0LY0pujQDkAv5usf6gT+Pe0PzaMC8AYBlQSkRDmnGrXEBq1Kh0wcIBqCdocrxlDB4idYH5hxGMlGmDGUVI/sUCGvKeezKF+FE0YW1QNYryiiHYNaiHWaEZ0y8x0zKBzWLoMqBkIY3sKiXliDU7qDxBUGMfXiARayWR5FpUVEall8dimjVn0KiJSg9JGDYoTOncNoyAAykcXxkixUort91jpIPUl19kvPXhdaKunc6/tX9pzHJaL24H6MR1mURti6Bwz5T94FZWmUh1MX6Ufh9ynraqyyWzN9fHsaadSctBzizHsBgoY/D1g2OMVGkIRqR+jsL4YRgDoQ970BetqlsSr0mDptA1LCUiHSnPRtc+GlzcyQX1Q8sA+tgBtwNN4THXDLVXX0Xt2tBE2IxQuoFCxdNENLDXGLnjmgYaVzGKKnUhQ7oDKiDdWMc9Q3P/oG1Q2UuttpXXiOV3vllSRRCRfxl6KTbJEREab2o89Nw48yy28Sge8fvRZkxjaHOrGsyLr5VH/RMIzr0xLsbQOKDfhmTed883FG/9oNYOtsOEwNw01AJI5BlgF9glUWEZznuW16p4hiHngyTVBEARBEARBLAj8ck0QBEEQBEEQCwJpIcQVAWohzb1q9jdMTWDWUlMlj8TE+xGGG55o6DWaBW7NaTx9wYXwQNkQMcY0E4Q5tS2T9V0bub5BCaRYBufCDiQO702WqrcCwp1WFaAMhHYxD4kPYZvGoFih46jZrPpSlLFsAmMBdQGElevHxpzHK15oaBbzYaoZbbrQcuM4Do1m/TC/PlNfM+ctxcIbSWiId7gBSk4oM1nSqhGC30e9oQyUO/CeV4UwqhuNQ+wL7fu6e82N2QkoDVCuwPraMumLjkRE5NaNAxERefjSVuhr1/BZRORbvukRERF55HDDv7e36yqb5a6T587tiohIZiQoHnn8pFggBO2pKCJSrKkhkipuTJVqIR2jOKF0kMauqh5ccGXyjqF+nHGVv+5lXxYRkbrpx1Q30+FY1XJS1+aFfpBIeegp19ek7+6JtKv9sWohI9f+zqFbzHwfki1mT28MtU3FJVcmObZmTtpnr5QSPsJ7oJHA5Gd4IpTpXHCvMBDC9UmVoeDLQClmbExkQB3BVA3XS4oRIjJbjukgsznHTt5YqVM1QumdzqL3alCXqYf5GCkdrLUfq3NYekprF/c/lHmU6mMoXKMN3R96H3lVC3OvJ6qwlGl/YP4yWQoDqytFAjVbFSTMGWhyoKJYGuB4zX3mqTAX9PnfDB3xz9AxjHtgzGIVbGAMo1QhPG/T6r8b/lllFggUE08j0r63Dgx1Cz/O4r1g4ZVQwDjU5+Ph88PDa+mpvHwZQcwFT64JgiAIgiAIYkHgyTVxRcDpK05YJQmnfzhpzo7dCUZtoCc0nVBm2nAnF61LLjEx7amNeSNsRfw8WVVNYZNok3b1VFrt0lN9nTVDwk9R11O0AgmV7iRvvBpOVDrnh1rG9blxpGWXTT9g4+5fdQ7MqYu3F9bTk+auG89oKyRP1o8m0XW1QRDhnaU48dYTcE0YtWPOuvGJNWyBfTKlu8D1fyVOurIncO1tXQ89BUtKfRcxVsR4y5zwF5qEBhtq6EyPQ76dDM/BB1v7rprN1rYcp4w4aRqfc/slbYZTsWnfrdl0Bf1CH8wJK/SXkeyIE8AXBkvw06suq+545PbEC89c8p/d/8j1IiLS6Lj2P/vwDSIiUm+ZiIBm0yFpbPvInWSPemFP1w51jHqCPrzODbatp7siIpOJW+cbb3Ka1asNtwduWtr1ZX7r498qIsF+3Z+UmhPF6b5r67/9xYtcmbqxJNf5yBqu/2fX3Kn9+UOzQHuu3/Uj6AZrG8PQRtbTpLFLmdanp44nwyIuL7sLez1NYtaEz1phdZ1L47DBmFn04iMTNjm2p7me9aO4Ppsoij1Z7820ntiOXSQkNOKeiu7fUn9wT/mTYnuLTXF99XIkUuI5Ml6JE4NFQnQNp7f5HL1szBVOwHOckhtdcNi3T7P4+WSjZZiriWp6+9N7O3d6Uuy17ev2VNu9d/Q8jTB2q0e96Cs+w0k8+iwSTrr9fOKU2n7zQLQPiZqI9NlIBxKb9Vnl7dklnHiPNXkTY7Wn7DiBR1RptA6fg9BGOo7nM9Nk1PaOiZyWkqAJ4nLgyTVBEARBEARBLAj8ck0QBEEQBEEQCwJpIcQVwWtPL7tw4Wg90DFaeRw6LDrus7QfYrT4OdGkwym0p60NrVJHEObMDkJ4faaJfsPrHF+gueMymCbrgYbhtWERJtSQamLayA5VS1spKKMTjobg6S4GsA5Goo21NIbdOJILEf6EnbntT5Jr3TWbqKMhXh3X4JQbR2vPzJlam09WXD98YqPRhUWf8Bn0ZUF7ceNQq/auqw/haW/dbjBrxUlCIiKTtoZflWUAK/HJemgj6+gYn3R0AVABCvOkmZYoHq0VR5EYPxoyEb39ebN0zXLo620vcNbhX3norGvrUK3jh6GxR550GXK33+TKHk/CPklS1c7tKxdBeTJTQ21AyPrkCcdNKJQvMzoO9UxVT3r1+U4X+p23/ImIiPSLUKavHJq6xqF/9f5XiYjIXzxxiy9T1+RNbwOv09rqh+60djXxLqlqwHst7TXX6Uc0aXg2MknHmsA42tJktgKUgtBGqhQRWKJ73e9x2G/Hj6y5smqj3lQqi9e2lhCCL9vL2/cmuuST1VJZUx4a8Hi1lA/MVVkH3dIOkOToaRRhWUJTuO2VBoVEy3pgGPnxlHWmRQJNAXSQpadcYaubj2cDKFfzLOB9cmMSUxRy02fQWjBXeK5ZChjaAoUEZTKju+0TiRvVM7ba2O3T1ceU4qdJk8OtsN/Qt7LGt30+hgTraVTP1CRogi4DjXG/XeYkPfqxW2aeftY8cleC0mKTQD0VaBrPQ82swaxCH4JXgPFQKKprRhDzwJNrgiAIgiAIglgQ+OWaIAiCIAiCIBYE0kKIK8JQtZJBW2hfCsoXtZ4LIU6VDpLtu5jq1NiOezpIy4Ws82W19raUjX2lgSxpWNtoPo+3WlH5actdb22+oaax9JiLVUN1pLFvssfX21E9jQM3DqiZuOtc3XXVP0Wmug17IqyIECTCy1brFZjVGtqmiX0jM/3Itd/acXMIm3cRM58DaLxq2NLof4My4m2GEX61etk+fKwKC6q8EpWBioOWKYxOL+ggY5WBzl7saBCjo6ADmz3q5jXTJfQaxTbcr21Ayzr/iuOXLF8MRbxeOKRnUc9WoAg1ICeAiO+6WjU3jOrI1LXx2IHr9E0be/6zrZueEBGRR1XXempFvRW3bey4vtVdu32Nz3/ZlO323HuDkVuD3734YhERORi0fZntS45GUT/v9kAKBY05VAnMGeZ7ZvSlm/tJVAbKIiIiudJ0atc7HslPvPx3RERkPQ2F/u3573BldIK7E9cfq/9dTFWVZqz7Qm3dJQ+dTftKB1Edc9AzrJIGKEFe6cVSjIL0tvtM9b4be9XzHl+PfmSpGpi/vB2rexSW+lFaVihEjNfCe+kg7j+oJ2PTz9okbsNSE8Yrcb/rfWj9h0KR9r0EmhWeVyJBJaRs4z419+FQda4bvZhiYdVYUI9XBBnGVuWuPzquOZQPUOpQxitvmOdspopEmXoUzDKzwKV+zzLVzwf1wjzvp14PXZ8HUDgxlI0yrcMqknhllKX4+Vw3iiJeaUbf6l7v1mf1kcAxwryuPIZ/C1SZZGD+3WhXn+sEMQ88uSYIgiAIgiCIBYFfrgmCIAiCIAhiQSAthLgiIDO8nPkuIiL6XtqNjWGgqCEikivVA0YzaU+VMNaM0cxJl6rfAD1kGsJ7oG+U0bwYYsWgkUybquRxMIjeFxGpwWQlg+2xe02M4kmmfatN3Hu5GszUjOnDTI0XZqq6MG3C3jeUydVSPNP3rIkFQsK5Uldqqtwx2QyUAoSTYU3uLdINhaW57eZqdLIVjSM1/ajl8d/SsxQ20KavOkcIFSfT6t/f43XXx+tW3Jw/8lRQ+QBNAPsCKhAIu4sE45JUI7Jt+LpEVuvuta5h+oHaqk/Od3yZLz75PFePxpWnm25PTQYmPN1z4zlWiYhHTSx/ONZy+tarbnhMRESOxoHmMlSZk62m60hfXD2vOPWEL/PJP3eGLrMDV/bhBxyXwNIX4GAO9ZVclzcNLBdvHT9Rs5ZXv+ghERE51QwSHL/9+98sIiJZVxVxjD9MvqymF2os8++e+DZXthbWd73hGgTN5UDNdc5sHvkyh2rgU9P6DqdufbOL4R6FcgaoCKB5ZEbZxFMzvFlR+Ax0A7yXqIHHZMUYRsHYBiF9vfVjqobWgyXHJYaeMtzUsvqepwgYkZzxevwZFEYiExi9frThCrX2woet/WnUbv+EmmUZC+7JUhK1UR9c3pQG1AbQXSYdQwsBg2dbqTkHVYt03NN4dozUQMs+rxvHWkZVOlJDYRmpfXx7R5/PShOx6kHYA97GvV41s/HKRuhbGhthiQQTnVTL1kauLGzeRYJBzPIF15+IVqL0DaxnrsZCnsYj4ZkLNZb2tj7T26EfUBuBWRfGMc9kiyC+FnhyTRAEQRAEQRALAr9cEwRBEARBEMSCQFoIcUVAuBLhWCv0DzWKQtVBaqoMAoqBiAkDTxGCc1sQZjAiwXwGmKWGztF3sUjQOKCkMW2Ga1A3jBDgSlAbhvhrUPdwHxaqDGJNZLzhgYYJG3tVSgpMPEAdwSuuERFpHLg+D0+7EHxzN9STqakOMuURdrTqABgrQqxZ19XXvyHQMerHaqSg9JCk0HCsmRdkuqdjmCNUQ5wwSRhsVh8NCJVnPdefRx4/KSIinafC+kAlBLQHUCMsXQCUgOY+ZBdE+xX2Uq7hW6gdQI2ifmCMc3RotVtdI7mqWyQXAq0Da1+0Xd29B9b9R0VbP+y4ufoff3GbiIgsbYXOpjV33Y7yUnaP3Ov4YqCntFThItOxgu5iKQWgSKR5/Ptk1YS3W7EJ071/9nx3Tc+G0GP6xLRpnUyUAqC0mJ3U7Y9GPezpSeHm6EzL0UBamfvsXPPQl/l8/3oRETncddeD8pSfHfsy+VCpBKokkqiSCAxsRIJKCObBmr/AQMjTOLSNWmjCU2ZAOSk24/mx16cDvX6E+ycUmdUhgRP3Jx1X93/RgEGL7jvTH7+Gnp4Srsc+H29qP/DoqVtqQtz+cEOfK8eGJtaIFUmCeklVMQb3y2S5agR0eJOb/EY3NpixZcCQmurtm41CG/VePNegA47Ww72OZz/GCGMWS+fwVBU/nqqhF8aM5xwUmJoHgbfjzXBgnGP6VtN2cx1kovvOUmC8aooqiCSzqiEY5mFwSv8tGFXNeerHVcMtgpiHa/7k+rWvfa0kSXLZ/37nd37n2e4iQRAEQRAEcY3gOXNy/X3f932yvLxcef/6669/FnpDEARBEARBXIt4zny5/tCHPiQ33XTTs92Nqx6gFCCsV7TDFppCzQLmJC0YxNgQo2aLd2D+4t6FaoeISHY41M+QVm/CjFAgQbtJNUN9msXbOkGZgaF11NXQRWkmGQxWjLIJQpqgl2AcUNkQMQYKJfWUKKtcs9bb55VuYKcjjfsPpZXxRpCBgIlNOnDzmq+4+HTncSNHkcBIAq+qbDIIsXgvqDCFUkpVQWCq8wslgYnJpkcbrW1tY8/NYf3YFAEFR6cxUxGKxERTkZWP9+pdpbA0qoE0hLzTkimNiMhkS9VcRq6x7DFHBwEFxPantaMhZ0NNGG5pe0pxmCpNpL8fKB+InXeP3XrUlErQGBhKgI4RtJlp1UvDx7GHJ9UEYx3uOKaePTcOfy+A0rIVaB233HxeRES2e+6gYP9ikM4AtaLouw4cDRAfD23s6HiGuSvzrpvuFhGRTx3d4ssU2qcbzzkDnZW625PXdwJ15AsHp0VE5HjoFuTowM3ZbGoD9ooBDFXMfaNUl+RpouzjdX3GrGgh0GZ6VvUn3jOjMzpXRhUG84K5hgEOVG/cm/raUJrYmpY9Dm019ksmMuY+hqoHKCPYp4OtKu0gV1WYht43ll6COvNWPAxLqwJdwZdtg/JgVDr0fvHzi3oM9QPbwtOxzDO0VsTriGdEaq4HVWXarMVljAEO1DkaXVDR3PswfBEJdBIod4xPudfOtqGF9N3PRbv6zEL/8V7vjPth+UlDR9R7cnASJmjuM0vzwFzDoMYrrayFxqwCEEE8Ha55WghBEARBEARBfKPwnDm5JhaDiWo9IynPajbXxqqJuhFblOftIHCbeS1TPYnQk2JrFw795tpINU2NzfdAk/gah+4IMtEEwmQSyiCRctYywroiMrhp3f/ceqKrZVz7SPzDGEREZno6nuhpJ06sIz1ZPdWu6bgK1fFGv0RE8o7qbUNXtghtTBuufG2ofdZTy+ZOOGVHXTOdFyQ0Wk1unPIXK3rkhZMqM55UT+mnGDP0YUeXPz6MTmFLluQNnNiakyokIkID2Ns5D6pWxvUuhIf1xSS+FnU9YdKkx+G6JtUtm3oGmhB23o0ZyYGJOZ1u7cw/gXP9d58NT6g+9GlnEz44DgmR6Y7rR7Gsp+uCU61Qz0RPHnHyhaS8PEiVS/86RAt0Xo5xqhzKwAI82XRr32i5+flr5x71Ze59wml7D8+748/ULt0MyXwIH+jY7Snkkt5T2tm/6J0TEZE7lp/0RT6bufcGqgNe1+y8x/vrvswrNl35P98/6+Ygd3tz0AuhhVkfvufuxepcQ7N6qgmEWU/3bytMCD5D0uRMT6yzvjkNhlS5Jp6mWma6ETIRb755W0REdrru2XF8QemB5iQ9XXdHvTj1B+zJetGOxzE1UZRUT5aRAIlExMK4ZWewiMfewUmpzb9Fki728DR+X0QkRUTDj13rMVrYVufb9QuJhOG9ybK7sLVb1Y4O2vr6zPP63zYjEm3pc34Z62NPg2MN7KIV27GL2ORP99q5pNHAmllnfVb1Tqt++H7V2hz9X7qoyYqNcH2qvgZ4HuHU3dqoox/tbdf+WLXB7Qk6QTxTPGe+XP/SL/2S7O7uSq1Wkxe84AXytre9TW688cZnu1sEQRAEQRDENYTnzJfrD37wg9Hv/+gf/SN53/veJ+973/uepR4RBEEQBEEQ1xqu+S/Xf/2v/3X5oR/6IXnNa14jZ8+elccff1zuuusu+eAHPyg/+ZM/Kaurq/Lud7/7a9Zz++23z33/wQcflFtvvXXR3f4rC69JiqQ+kzgkGhKFjW2ilInsyFAclMowWVfqCBL5euNKGdieW/pD51HHRQB9AqFAa20+bbt4raeKaNn2IwehzLLGYgsk5ej1tZhGICIyOOvKZj1Xn7VgR1IgAN1rG2JNVV97sqLW7z3r8z2LxpivubagSS0i0tx2MeeZWpHD1n1m9MCzHUdpAGWl0DBqOjS3uFJEwvzC3jceg4hIruHgwVYIm+bI80MYVhOyrAavsh6kjuSqGWgh1oZdf0aRGkLGph9IfOrElIvWRRPq1eRC2EFjXpu7pho0C4aEoSbk6kmOcHDxRZe0aMlE4zWtQCkE132T82q/feOCL/OJP3pZ1B+fiGjC/c1ddz2oK7ANn3YMnWnFcQFWV11m5GDk1veex28K/bnkuAleo3glXP+KFzj6yFtO3iciIh/+0utFROT4YlBJSttuD3Tq7n570dJTIiLyNztf9mW+52V/ISIinx85JaUvD5X6MQvrs6te7Tevusne7saa2CLikwOR2jM1mbzTVaXJYK429IORFSfGvnCFMqWHRJbk+thIlBtQgGLQDfv+oUdc8mV6pPSsQbynRERyXazaLL7/rY44hp8qLcXSOXBZrlMN2ovNagJVw699I75WJOxXJEairKUzIYHRa0dj/xrqSKuLvT2L2rA0PtiOg3Jhk8JB9fCW6Okc/X1N2h6tpVHdeSfsE7QhJb3rOAEdDxT3AjqG7WuhHzYPoU8dxjrT/oNWknjaTOgrnoeg64xX8LvZBNC1tkncIjI02t7WIp4gng7XfELj+9//fnnnO98pt9xyi7TbbXnBC14g/+Sf/BP56Ec/KiIiP/VTPyWDweDpKyEIgiAIgiCIZ4Br/uT6cnjTm94k3/It3yKf/vSn5d5775XXvva1T1v+/vvvn/v+5U60CYIgCIIgiOcenrNfrkVEbrvtNvn0pz8t58+ff7a7ctWgtQdLc41FGgvtiVIaGqAoQJPa0BegDpKpFnbQXK7qKScaUrSUDwDv5Suq6GGidaCY+OsQkrTqIaBjFFAvgXKGkZrQOGNzT6tReke+FOqpHwy0H46KAvv04ckgJVDTjPT2BVc2omHoWMsKHqm1jFe1Fa8DDSWQ40BPmZxy8WhYttf3BvEcmD5mPTfGVDW6i6WwPgjRjlbd6+BM6CqUHNoXYvtlqwSSzGIlkGkK/d8wnqBEEIf5p3aZ8R5CvdDE7oUiEw3BQ6EBWsA2hI6QORQrUrNP2uexdxPzf0N/MZWNTqvWuEo9/N7nXuKLLClVBSFn7EW7J70GMCgFS6CHhEI3n3G60t958kEREfmPX32FiIj0La2jDzqWDmstzOu3rDtayFh9x1t1t85HNaPm0nUT+uCRo3r8nw+7Bf6/Jm8JnVU6BygkjaarZ2slTH5Tfdx3+44eMuhXOQ5J5upZ3nALMzWf6TaRyUT3vWpQF4n5J2mo9ACl2wRd9FAEqhqY3wb2zZ69x9zPsFEHlSRWwoHajlKnVHElMYs4zVX5oh1bvouIFJM5+t4SU8A8XQE26howtfukXMb/bpVWdB4w5hqUSsyjC3UGOgjGGcqAQmYpbACeNaBWZCPYhleKerWR3hm3dkuHQaoE2tVQ5QCdwyouXQ5jq4U9hNW69s/4CIDagfkAlaxudL9BZ7RUHldv+Bn0NPSxrJ8tItI4pHII8cxwzdNCng77+/siIrK0tPQs94QgCIIgCIK4FvCc/XK9vb0tf/RHfyQiIq985Suf5d4QBEEQBEEQ1wKuaVrI3XffLZcuXZK3vvWtkqYhTPjII4/IO9/5Tun1evK3/tbfknPnzj2Lvby64IX9ExhwhHhlc9/FJScbTtHAZ2Ib6khdlTbSY6VIKFXD0hdq3WF0HeglIsGe2yqIiIhMDa0kxXX1Uhb81BoguPbGW44D0LzUq/QDbWDI/bNuXM2DEH+FxTvUU1I1ZGkchdAoTFpGW7G5jisfm+CA1mEVBPKl+DZNh64saB52jLBPxzisAU8COorOw+SEG7sNsSIcDGOU0Wljn74HG2v3O+gglvIBswb0JxvDOKcaT8ZYx+tVhRWoJNS7UCBw/ZmYIBNspLOSJXHNRG7rxwjtzglD4y1t1ofrrR08bNwPXIfO/+l1IiLSMW2CluJNQdRsJLUhZ5hwYIi+P2FtH3zilIiIPLG/LiIio223PtlR9QwE9c3G4bNf+cKrRUTk7KazKb9l3fGZLj254cs0tvX+0SWbaz8OGoWqQAwTNzHnx8Fqvax2kq65STh5KlikLzXcexPl+xz0g6tOoco3+VgNYvQ1UgtBd2A5r6ZFtSAs5Od+WjJUsXsAlIqGdg0qHZb+Uyy7+3XrjGvkhtUDV9bciPj5fNepyhx1A8dg0oV5lD5zlCZSGOoIOBWpqpUoe0dqZp8UJdpC/Sgen4jZk7Ba1/GkgSUmE1UUwTyADlGfk7tfA6VlVr1Hcd95O3SrsKJtYC819F4tmmENoS4Cc6lA87JcmFKbUEOxRk1LWo9uITtP6QjUM7TpXmE8ZZvA3hnpLdHaM2X0/q/3XN8mSmWpG9pb3n7OnkcSV4hr+sv1V77yFXnXu94lZ86ckVe+8pWyvr4ujz76qHzmM5+R4XAot99+u/ziL/7is91NgiAIgiAI4hrBNf3l+tu+7dvkh3/4h+Xee++VP/3TP5X9/X1ZWlqSl7/85fK3//bflh/+4R+Wdrv9tSsiCIIgCIIgiGeAa/rL9Yte9CL5V//qXz3b3bimAAoBsr1tuH3vxe4PlY0vDbWse79+EOKeXhWjo7FMhKcNZaNYd/Fa0DKScaBYlI1hsi5cJIwSAX6GEgcy3nuGIqH1NPZhpIJwuekHVDS0nvZFHVezql6SFEq1WFGaiAl1ghrRmIwr16cDx7EAvQShWcyTSAizwqyl0OuhuCIikiqVxtNBQDOx6icQG/FjhWJKKDLYdIXAAEh7oa9ZP1bF8AYVWSmuG9VdDTVj73jzCi0z3AhtIbyPkDOURGLKR1zW0jB8n1VlABQlhJfdhRK9hzC9DX2jzlqO/a7vm/B6mVrh1SxMU7gXoFhRqDnJtGNUVJQ2kE/cYNfPOR5DKwv7f6XpOvTQhZPujX7YJ5M9Fyt/bNe9PnXoKCxZFgY0ud7FzmuqhjFVk6Gka+YeCiZKlXjFrY+LiEgnC3yMJeVjnB84ikSuE7M/CFwLGMvkhftsNjXKQiM1QppA4gHyJ0YFAioheh1oHGY4np6CNcA850FgxdMEQAsBEkM7AOVpb7TuxrHqOEeNTrh/NpedLEdWg5KIqQuPHB0HVF2ivZHE90lZGcQCfR677sjMip/odpjqdaA65OacqKF7cJbHyhl5K/QB9wbu1alR8MC9AIqEp06Z670iiS6hV+TYDNQJfx8X8TWgm7iG9RXPJ2wFQ9tBPV5tJKl+Nl7VNnR+ina1TKaCN80D7Yehl+C+Pb5B/71QFRarOpKNaCJDPDOQQEQQBEEQBEEQCwK/XBMEQRAEQRDEgnBN00KIxQPUBNAXGsYwIOu72B8oEjBUyVdD3BM0kmK9GdXnFT1EZLjlYqIrXzlwZVdC7K42UnOSpoaz1cwGyiDuMzWYUZOSbFg1vMHPtV3lFqhqyfhUiCeHPsWqJzNTT++ciz0ibOsVNIYh5jxZdeOBqgb6JRJUTqAy4qkwZj5AC0H4uAkjH0P5KJZb0Xu1I+Ut1MK8JGqCM0tBHVG1js2wPiPNsO+8xhma9M+vheu341A31s6qhUxW1SRI9wL2wMxIcIzXlBJQgwIAwv5VygaoAMMtvfak2W/7rp7ORf19AAqIqaYGagH2WfhstBYbS0BFwppGeJUGqFBoCN6G6UXbg3KFr88oPCBkP95QKs2Wo2fcfN2OL/O6Uw+IiMiXe6dFRGRv5Aa/bOgYw8KN+f/zyv8qIiIPj076zz72mDO2OXjMrVmxpNSPduAmLK85WkmWuvde/yLX5loWeC5fPD6r7btOf3X3hIiInFgOEimPPOXemyktJV11+25pKXBztpaN44+I1Azfpjd2k93IXD/qyve5dBzuv9HITWB+pIpCR27Si6ahNvTjV1BxrIJMrUQZ8TSGtjGIaevGaOrzZA6VZftAjZrUlGd8FJSSan3Xt3QYU6dgvCQiUj92n41XdQ/Uq0ZCs6be/3hPeRSzPGzKmlK1poNaNHZLi8L90trVN2AmYz2yQM+CIkge+pGOYsUMKHFYmktQAtFrSipCIsGEBu3D+MkaRhUldR20Ye8xTxVpzRmHrquny+iyWFUZP34YPelyz+YcL65/1X042KpF17i2vrb5DUGI8OSaIAiCIAiCIBYGnlwTV4Ssj+MBtbnuhROvadOdNBVtPZnEqewg/Onv7c8HSLjTk2hjCb7yVSfuitNYa5U73nLHHPXDkZapV9qAfnJjFGeaTdvhKBFJdMXZdXe92pjDGjwaB04/9VS56NjkL/cKHVdY9mZGrxdtNQ+KynhqAxzTwBJcEz5NmXpXda1VY9Unk0bW5m5srQM9xproOOrW41lPrH1bOOEPbfXP6glvPidpUw+koGfrNbrNKXvj0LWLpMuJrs/UaN+Ol3UcyGVbivVyRUSGJ/T1pCZbbbpjqEbbaIwfuqQzRBLQPyRquQ91XKfUftkMC6doOFWGJfm0Ea4Pp566hjtpdK0bq3stn+5ZLd7BDW5/Ntf15FhPbJEcJyLyH77qzKzywrUxOnQVJ4PqWvzFmktWPGN0paHNPDzt5nw0gOBvuL73lOs4Tk1/Y//l7veRSbLVZLzsWF/1Fr9UrPsyyL8dnnL9f/H150VE5Js3HvNlXtC64MpEPuMOv37hm0VE5FTLHTGvqg/16snwPMFp9q894OZloCLn9cNq4ivWwyfQ2S2Aw1Od6ryj67wUng+NTU1W1oTKqZ5cT83JNQJW0OZOzIkzMEWiarP62fB0rM0viCgYe/o01WgD7j9YwJvnSUj01PGVkjpFQsItpn60qkl6kWZz/J7VcC4nIuOU2p704vQYJ7vQ1o6WG/LYuA6BT7OlEWVAEiVOoqdzEj2xrvbewntJ6VTanm6X7d/xHLDPnBQJ45qY2TqYVvo6L0GbIOaBJ9cEQRAEQRAEsSDwyzVBEARBEARBLAikhRBXBE9JUI1iq9kMm+/6nlqbt2NrcPeZoy3MNNEO1IbaxOhLqwY2NKcTk5gy1fKzTK8bxtQPEZt0ook6Y4glm3GAsqKJf9B+npjkSyQSgv4wBX1iWqUdTJbdZz0XrfeJTSIinQtxGLfeDx3xlBOfxKMJn22rLx3TSSytBGied4mZXue6rXHTwgxaxwy6S9FCoqRJENNwcvfBdRERaR0begrspyfVMDLgqSvQrC0lLUZloWM7J1Q8Wi8ldKnN9/g4iNc2dY4bmpOKcK5NQMqbcbuRpjBCxMhLw3AMp8DruCu3YHSDizVbXehUE8sQ1gbtwCbMJZoo1265zXy453gMDzwV+CWoB/bYPg/RLCFC7hPt9PnZuv9ssOk+nKhO9qzrfgeNQEQkUd3j2jG0fDUh0STDeU1isBbmJH8h5L70qHvzK3u3iIjIFzo3+zLFsrtw63n7IiLy3dd/0X+2Wnccmi/suuTNG9cORETkBrVsFxGpawdOr7oFfkot0+V06MdEKRrTQ13EAve8GTNuf6X7zPS1uRUoKJnSMYYTTZ7UejrL4eGDREZQRY72jRAzmstBtVCKhNnT3uZc91dyUKX7YE8iD3mmdCRvUS7zk/BEYm1vT9kAramJa009oLTJHMpHXqKezKHbTEvd97byRl/aW5KDhqHvWzoG3oP7urcqN7QOXxZ70vQV4yjr3Nvr0Z6njCDhdA59CPVhvTKTnJ5MStQegrgMeHJNEARBEARBEAsCv1wTBEEQBEEQxIJAWghxRciVrpAq1SI16hqSguKgSiCD+H2RYGU+XYM+tGonm3BbbRaH3rzluYikKF9AuUMVShrh78TJsusjVDZ8vVZGWfvUv21DRESWHnWhZ1BaRETyG1XXVuuB8oUF9GB9OFenY3gucBPSsSqkgMZgNHhBPYHiBvoF1Q2RoIXt6SE+tmrD/TpnE23Xx1hNGFgpI1AkGa2rKsV66M/oeS4MXtuHCosZq9d4dnV2r4emtbHXhpW4hlYLaM6apUDYGKHmwS061tzQU9SOOjvQMPsxLOBDPc19HSJs2HWBJ0YvG8oDiDVbRYWZ9gNUGITHZRr20vSEDlqpAKALpKdCDDpXC/Hpnu7FVbcGSd3QS1SNA3QQ0BfSYWgL9vKwaEZ3rDICdJNrJ128/SXnngrXK3/jsdq6iIhsQwFkHPZtvQvahGj72pTVLy6tmbeOnmP5rgIefi0sHQqqGrvan//YfWXoq6qltJtuQTcaji52f/c6X+bmjtMAf+OZL4mIyKcajnLy6MGGLzNSnsJIde9F9aYtLUSFSPz+wN4c5UuhHrWD9zQMpfEUZi+M1ap91Fe6zV7QucZ8QMu6TFGw7eKeLKvM2Pc8VUrvCatgU6Yv4BpLh0qgelKPr8E6WQQb9PAe1IrwXELdMXVL28jicdSNvDnu1/K4jOS5n7vU9F8k0KxsmafTp66VrrcUsOy42n/bP5GgiJKOoRqCesNeSs3PBPF04Mk1QRAEQRAEQSwI/HJNEARBEARBEAsCaSHEFcFn3itVQQxVAmohCHtC7aNoh/hcMlC1BaV6JHrNrGW24ji2As/XQ/o56CMwnYFZiVWu6DzlYrKwRJ+nsgHVkc5TLhwNAxxrKd44iNPVp6pG0TgypjhK66j3VEngAG2E8UAVwys9mL6iLtBc6sc6PmPn7sPyPbgkVEOTUD9JkNkOak07cAqm6vwxPKHKKEtQ8jAVqQpGdgzVkvARwqz9dnwdbMRFgr23H9++0m/OGWMWpSSs3u6UIV535hEREfkfT94SujFQ2/Wb1dzniy6E3wpu4T5sPF4rzcc8BYCSQYVICN17kxGYYayGMtPjLCqUdJQuYExXMjW2mZ2Flbfu24ExLYLxx0DVOfpVmgt+BlthsqZ7ITMDUuOTpbabRNihi4h0ElfBassN7NJk3dVrjFAQ6saYR5uublBSRMI9jvWuQ43FsKLqqhgDVYyyGoP9OV9yc3X6liP/2atPPioiIh9//AUiIvIHDz3f1VsP/JSdLTcRr9l6yI0vc+M72gmyGM0nXKc6SlmBcszMbAkoXExwH4JGYRRsQIVJdK5B/+kdGk4O9sCRm/PE0BAaR0n0HtYymSMugfdgW27nFb402KdQnImMWaBaokY1tWGs0OOuV5Ov4/jemM1hNcBEyiqBgO6WKdUjn0c90Z8bOvfjFVxryhQwnMKNqO/PmxcYxMxRHSkb1kRt4N8kvSW9solpA89g3POgfsybj5r2GUpD1pTqckotBFEGtwpBEARBEARBLAj8ck0QBEEQBEEQCwJpIcQVoTaOFTisQcxk1cXz8iUXw8z6LoZX6xkXGJicKOUD5i2FMaNJGsj4d21l+33/WbGiYVqlRtSPJ9qWUSlY0fZ7cfo4+uU+m0T9wJ0AeogbW2zw0tx313hKjIikSsPoaJi83oPxjKF1aNcQyqzlIcwI1RWET312/iyUybpj7ZuqUmhWe94JfW10lQqjFBxPyVkLsdXBKffZYEsNWTSMa9UooDLg/+w2y318s5pvPM/F3vu7LtaamLHKkq75oSpnaPO1kVmfM24iCqUrPHB0UkREji6shPFc79Y8V/pFpgorcehb5sKaW8BYI29jfQz9YYbP9HcYTBjDjqwHsyQNxafgTISOrK24uDjoIJd2wzg82rrfEcJXJRHD6pDJmoaqm7ondF5r49BWokYzvYEb5JcvGOeQhir4dCbR9daEJt9w61PfcGuQ6DhObh36MjvHjo4xeUjVcmA8Y1QgQCXwtJanU4HQe/OJLwf3l//0Rf0ZAi0t18nmydDIDUtO2uK/PPkSERG58GW3T1o7YT6aB3q93greHCQIefj7z1Mc8LvZCxNQyJrgt+i1EzP3RcwhsPvE02LKnlbmkrru4TJ9wtIXJqVx4L6x1CCvHKLrLYMqLaRxGCt5eOqEoZe0VDkE19nnAPoKw6iaPgux7iIizSN9ZsHYZRz33baH9cgGVVMcKVEzJrqlrVIRFF9QX2qoGjANw/Brg5ia5uosPdcUdaN0hLGBEuNfx8YMqqjWTRDzwJNrgiAIgiAIglgQ+OWaIAiCIAiCIBYE0kKIK0LRUsoGaAzG/KV+DLMVKCxoCM2odMwSVbVQVQ6vcmEVHkDHAGWjZkOzUMNwL9MGQuehH6m2i3BhqookzW5IMQf9I1AtlM7RN+Yvg9icBJQNGxqcaRsz/cyLqDwZ+oN+IDSbjoxhzjgejzfMMdQTwTzAdALGPZYioXSQouPGA+pJ7/oQ691/gbsA4d/RGaUPGNoB6Aq1XfdeIwg8yOiMqmFkcez7RS99zP/8pT+70V23B0MGqSDvuj52tP2vPHRWRESWDCVgrMY76aOOs+HNMAzlw6st6HgmGm4fnTD9U5pKuu3i0uP1sHaFKm9kB67SGULOg7BfEZb3qgI9xNlDEztPOWWTRI1IUg3Xr20Ft6CNtotxP3Xgyo53tdP1apg521EDnW7VkCSoi7g+W2WT0QlVeElBMdK+W7URfW/Sc4PdPOUoPv+v6//cF/m1h79ZRETUt8fTZiyloG72hUgIr1sDkaaWaR7CNCXsM9SJ16LlPusmHV/md45udz8oBSZT+oPd91CBwF4AxcGqsAy33GtrV98As8wqmyhXJFHzpKmuYWLnTqkM2BP2ek89Ke33xrGlFLhXUFnwnBsbCkuq4xivu1c/56l9QOprDhUkpS/0jfmRXod5wR6yZk4og3E0DmeVz8b1mP5jaRRhYHoN6BmG9jZP3UMkprCgPK736jTGBAZUGsydhb++DipMbBbk3nOvWI+5ZjS4p72iiZY147GKUwTxdODJNUEQBEEQBEEsCDy5Jq4I/tQVCT9Gj3kK/dVG1dI8FNJEu1V3ZIWT6LQfjpqGZ9xxVG2omsKrTSnDJ/5pG1afWnBKgtMJTaJE8qSIORVPcTIzrYwHSZM43ZhCU7sVjkTq3VgLe6b2z6PNcBzVOHLjgN6vTbTEiTnmYTZFAl3oaw261noin680omtsvxE1KPQUZ+cOk3z5YneUONrXuddTufTA6G7rKSMSmlq75qT3q2qbfsHZTydbblw4rRYR6TwJO3dtE6eu5sAr77gy2392ypVdd/X0j6uawqk/2a2eGA1dfpuMzrj5xAmelQFPYWN9So8Uu2Fe02O3HkhyREJWZJGuU5PCTvsQ+uqhzHjDfXbmnMsQG0xcG92eGY8Cp/5jJKPVzCnfARJxXX1NzTGMErtGOOXTa6xlvCZfIrHYW2jbk94lvb6tp/aahPmbj7/MlznYdRllsG9PZc5JoDltdZ+pBrw5qQ226dDEDuVxwg2repxgp6NwPI5TaawrEvmGy2HfI8mwoXsYp572tB928rkuB6IpNoEPUYKig2NL/cAm3iHxT5NjY3vu2G7cJ1Y2w/XQwvdRN+TY2dPkklYzIklIqBURSZbcM6emkRJZ0Tk02uvY53kH86OazWYNcNruNbkzE7EpnQbD5h5JfiIi9QFswkta2ma/lS3asU/q3eoJOObTR0FCHrvX5McazKJoaNzWPE1urHnZsr1tdPODh4POFe41M755+twEMQ88uSYIgiAIgiCIBYFfrgmCIAiCIAhiQSAthLgigD4B+gF0UEVCqK65F2f1wPJcRGS65GJ2qdGuFhGZtUM4uP04MlrUGj0LSU6gjxRLLi5dG7i2RidDmdZT7vrBDS7bq3VRLc7rYbtP1tz1qVJP0uEca3FYiNdAdVA76tVQDxIGG4euHiR6Zv0Q68WcFdp+YWklqtMNikcyJ1EUdJBC7cu9nXsW6hlrn/qnXF9H6h7efOmBL7OmHtHDJ1zYf9opUSZEJL3o1qehGraN49APaJEnO0oX0ESzzkVDHSkxeMaacNe72cwHtHthOw7tZ6Mj3Djp+lrU3Jj7N2IvGP3vFddvb++tH9Uy0+dLjm9Q07qttjHoHw2lX8CGGnQMkardMegQVtobYf1Ley7r6taz267MOOzpl5y8ICIijxxtiojIJNeExIF5BKOPemtk8S3i2sqf5nf0CRbg+vtoyybg6v5K4/j2MA/9WFpzc3/yescNQhLm8DAsLhIA67vuOiQLgo4kItLoxdrtSAwWqSaWIfRuEyVBV8B1sIWfLhmKxIbe/w23MEUDyY+hHlBFUB/oIDbpMdAW9A1Mj0k4Bf0g0STZaS/M2VTvBb9f9LLMai5DV71V0qA2tJDh2bhssaU6/u3Q2VT3d65Jv/WG9sfcP36dB9DE17ZsEqe2Cw3qOFk4TuSdZ2/vbdO1HiSlD7dCP0DPwX2D3z3NQ0Samkg50yFO05hiE9WDJEzL3stxnf6u73sajgR6ToZphPeA+afKJzDqZeNl10h7J6+UIYivBZ5cEwRBEARBEMSCwC/XBEEQBEEQBLEgkBZCXBHGqy4uF3SprU23i7nBlrtx5GKz05UQTq71XRxu1nJbD0oeka2s0kEQmq3vBPHc0fWOZ9B8wsXuZ6pX3XrSxJP1OtBBQKuojUJ4L1Md6RTa10oHAd1EJISja6qTDVpEayfEEnPVlS7aaimuiiA2fAiVkHrX1TM1er+iKgVQB0EfrWpJkbnPBqfcWBGubB5ayoarp39Gx3eHm58b1/d9mZou2rYqK+TjEJoF2kr5QN2wfBcRyQbuvdG6G8/qo1W1ANAUPB3kVvcGqB8iIkVH6153sd433PJlERH57T9+hS+TqorF+otdOn89dXN3YS8IO3/LjY+LiMi9X73JXXNJVVTMuGpQW2i51/ENYe2aj7h9iXBya08q8Pq4qm4w1j3hNZNFJFN94cmho6A8cHS9u+ZE4CZ85skbXH90XO2m60c+DrH4cujdK08Y+gIUL2ZQsjGhfGgJowxspG0Zb++tOtcXR+vu2rYJfetSPdp1AtEzWL1Pw7x6a3bYdGNa58gAI2w/MxQLH4LXOqGxbJUZoB6BceH3ohcGdPYmtz++8/YHRUTkjy7eKiIiT335lOmAKonoIwLUjcRQajyNxNPClApmqDmw7AYdy9qheytzWIGDgmJoMjNoe0PiXB9rEZVKp2iyFnMtpkW4f6AolOhemip3I2sEfslEdcMLvT6sl+VTuBfscauwgr3TMmoarq9hPN6K3I9d75E1o2CjdeN+wV7MTFto37+iXkPZAN3OeyDM0etGndDEnqxUFUWwzlb1xI9N9x7URnDPx/rsPI8knhm4UwiCIAiCIAhiQeCXa4IgCIIgCIJYEEgLIa4IoD94lZCZCRNqpj6UN0DZsAoc+bqqN6gaBq6pXzoO9XRceH+Waga+sQLPjpVWonSSqRrD1AYmTojyRRz6S2aBRpEdDKJ60Mf0KPj0FjBrmcH2XPucVWPfg001mIEphjGogBlCXU0+Wib73CtweEUQtWNvVpVAkJ0P1YTByTAvaAMmIS2lUewOlnwZUC0yNYiBakJ+2qiFjKGiEpsFiRhFh57OQx1jDYVASxlcr+sxgQqEoYUobSPZdH39xEMvFBGR2XJYw/Ultz4v3TwvIiKf2T7n2uoFCYE/fdiZ19R2dJ08ncIoPKjxSO2kixnXjGlL3sZY1ShjGXMQxgxVi2CEEhuBuPbc66gPVRm3dkNph3qUIjJVlZD+vholHYd1TlVFBTbuaMM6LkP1BAoP1owDYXCsq7eMt0wApQdAKeYtr7hPRETG0/BPwX978DaUdmNuOY7DZBIoU94uvKQUYaoJ9ActY40/Rqt6va4Z6AZWjQKUE9iXexrDUtgn3ZHr08O9EyIistp063zemL+AslIrUTasGgWALoa1CPM7PhlLtVi78dpEFW/SuI3EPoL08uaBe7N/OjZGcX3SC3R9OqtuPMutsCm7QzfmlqqEQHmm1zP0O530mqqM1NSIZ7JhFJP29b7xRkRGzQWKOWAElcYlYo2MtD5VALFW56C+gCYG1RCrhDPzRl762QDvhzJloxr7XAJdCIwXqI9YCgvuASiIFCUTJBGRsd4/nUtwH6tSR+rHReU9gpgHnlwTBEEQBEEQxILAL9cEQRAEQRAEsSCQFkJcEUAX8CHeJKmUmXkTgJKqvwS6Q5KrEYmqdUxOrfgyac+FQJOJhuBMOBkZ6aBz1MZV85diuanXa19BE7GhRIQi1USmNprEZUUkU4rIZKMdXT81ZXKvDuJ+n6hZQ/+cMTBYdn3sPOri0JkNJ2MeemoEoTSZyVKIiQ42XfnhSa1Po795J7QxuA5GHe714IKLwx4aQxUZu3pWNPza2HcDWnkkhJMbR64fmdJsRushdt69zvUJWfSjdXf9wAgzTFaUenIIipB731ItRmddG02lqYwfdH219IcLXTfY8y3lBKiqRGLi7IUasKSnXSOgjCydCuoyvQNdu103xqITwrrZjS42nY8cdSbVcLSlNmB9spFSYbBvDOUoF1CltF5tvv1EWMN833FOClUtkZbW1wrrk0M5Q9fFh9CNIQrC85hP0JDch+6lrrSfXIc+S41Kxwm3p5c7roJPPOwoOR1DO1jquDJDNcGBoklzLcT7x4jBH7nPYMDT6Ibu+FC+Nm8pEj5kD3UMZS/ly7aMvrZVMWNNKQ7NsIa9viv02YGjDU2GuniGYjSeKNVK57OpAjqWgpKN4vdQ1qpSZEd4dildxhrVKI2iBt8p3TfW5Af7qmjF11uKQl1NjmZKdxs23YeTSfWf6rzQ/kARxGyFQtdnqq+J7oGZofHhaC3FI9SM1c9DScnDUoy8igtYeM1qPRVTHaWDWGUS0D+SIv7dAv1BfZbSgyGB8YV7NOuHDQcqH/YgKEKWvrd0vojawhpatRCo/RDE1wJPrgmCIAiCIAhiQeDJNXFlwF/+Y/cXPOzDRUTytiYnHk/mXiNi9KxxCqxJZVbnerLhjhNwum0TS1L8nGhCo54qWF1obyEOfeueO2KZ1WwZtdPWpMnJpiaYjcN4oMWLBM3RhjuaqffCcRROwHFIhwRFq9c7HrljFiSajVdDPxpHeloC+/Np9ZQd1sVDtbGG3m77okkQ24TusY79UBOytkJfG9t60quHlI03OhHb/HdPhPFo8/mSnpxthr4e3+zq7px3dfdu1FPq60J20uzYzdFshNOjqh5zoifogydctKLZq2pHIzlqeAobReuf88RKDjSpVdvoXQjHnzM9uU+1zdtuf8J/ttN3x6WHmXvFoZS1TS7rFYcTPZOk247HiJO0qTmR9LrFelJd0z7Xj81CI5lOT/Vqc04U/UkobgN7OQ6DYeuuOcJj4xWdH7pOjXVeJgM9nX4sJL76e3PdDf7M2QMRETm9FJKOH2ltiIhI99i91o/ipFCRsJdsIqPvRysuM9IARb5mBtuMk8cS7fN0EjbTdB9JqaplPcKpf1hDJOeVT6x9UraEk8zxskYm9AQeJ8kiRq8be9BaievP2RCRjnh8IkYTXPcXTlijpEec8B6rFr0+NCbmJN5HIqA7jpPruu2Qvo40KXxSXYNUrdGR0Gv7EdYuHp+9j33z+hmeK3Y4OJ0f677w+9fMS7mteUAi8QTrY23L07hM+ZRbRCQbYc7jz5CwLCJSqDZ4bazP/Qnqs88D2p8Tzww8uSYIgiAIgiCIBYFfrgmCIAiCIAhiQSAthLgiZP048a5ohVgekuAQBkZiIpJzRIJtM5INkyn0rkOZFPV4m2LLK9EQfB2avpn2q0RFkZAQ6S3WJza0iuQkN576jsaBbb6KJi6CToKwcmE0qEFBqfc0MVJ/b+8YWsiKWhErVSQKRapueDpSO3i1104HRpO7HydNNpU+0doN9cCKvBrODX8/9zXxsLXvKjr/5LqIiHRCLqlP3kmPYPkextG65F6R3JR1te4vBS5A2oIeNGgdmhS0FdYnOdKxKkVieBYh39DX1q5qzj6VROOyVtFeS1u1n5u7CKWHeqanNVG15co+8Pkb/WegMjQ0dI1Qs010A70nJG+5vuYd0wZ0diFrjUQxo/ebQc9ak+Jg1VwPTItgf57H12fzrJp1/9dN0pbXG8cLEsRq9v5xL99yw2MiIvKpr96s4zTUqxND7YcbyIWnHPXjArgbIpLq2oP24+kgNhSviZ1IVrSUHoTnQZ3Jlfbwipc87Mu0Urd2X9l3ya3QsD7RCjSkPzt/nWvjPGhd2Ath3yLBExSfutIHoty+AvtWx4e9YCzOk5IFd808l0J5pRSM4vvR/ax7GZbgB+51bGy6QQkabeJ3tBWeOUiK9c9HT9m4/FlZ1sOzrPqZ36dzcvV8G8gtH1c/8/MKDWmrLw3KhrbhEyQNBQRJrO2L2haoh4aCgbZae/AcMM/QkgY2KGWNbvXeAHUkJNQaOqLSu5aO439/bP1Wn5sgng48uSYIgiAIgiCIBYFfrgmCIAiCIAhiQSAthLgi5CsqMKoZ1I39cbWQhj+hBFIbGHttDV1OlU6Sgk4xiZUBXGOqU103MURk2CutpD7SOKqVTdBQ37QFqoVqvRp9atBJEo1LZ4eunlnDekVDAkRDkaoakg2DAgcUSfI1l9WfQUnEZJi3L7l68o6qWuQh/grN7LKiAugiIiJ7d7jyS48pPUXVD5YuhH7Uu+5nUHGmTW3LqJ90LqhSxJpbw/qeUmqsXq+GRMerMRVFRKRQ1RLQFsZbruzSw4Ymo7H2XLWJ5XpXeSMNFc06Lo7cabtY8dGBq3g2DJyPwujPioTwcj1IWEv2VaT+uxeoqhSnwn777hd9QUREPvnwC1zRfqgYlAyoaqAeG6b3Vsp1aLfXorIiwY4eNAP01WrxegUQH0J3r4nRQU5LtJR0XLVa94oiE9g4G9rCtPSqdYO6IRKr6oiIvPr5jobxqQdv9u+98flfEhGR37nvpa7PqmwyM7by+Wau7+k+gzqMWR9YXvv+RapBpc9UeuKzX35eeFPfg834vk7wo5FgtpZROoinwlgKilJPZkpN8Eol5pkBCkGk3CGx5nlb98I0q0q1oFyjD31rfS60jEayPkeKDFQj93vTStHr3gMFDXsImvIiQWHGW7PPoPoR6gF9Cioo2JuZoSqVaVBWgcPTOOrxq9Xt9hbvWEuvZW31pfUH332oCIV6vDqNrhPGMW9vF7oHZ0Z7Gvcb7hfQXOwew5pP6zE1D0o/IiL1/lTbBVVP1ZAMRQ/XE8TXAk+uCYIgCIIgCGJB4JdrgiAIgiAIglgQSAshrgigPcBEJjEUB6hxFKux/fhks+3L1A9czC7pawwSUfYsbEUYvExbiBPOCcXhOqV81PrWVUDDpqBqqJIIFE7cBbH9MuqBdbobo/YDyhBab21kaCHaLt7ziiQm1DtTdZHmeRcLnbWCu0gyHEfvoY/TNJRpX3TtL71u25X9NWf6Yikbvv2BG2t2oPH5bojTN1YhC7IuIiKdC66tlceMioqGPWGmMQwCEZ5mgPBx+8mqvT1CslDimO06rsbwRAgVv+BVj4qIyF/belBERP7Dg9/srt0IseL+UCksam7S3ItVQywK3V7jNRjoBD7G797zcle3qpe09sJ1jSPtPgxARlXLatBBENKfZ3iB9yZKg0AI2iorlOcufFAdj7d4TueUKdEWrGoCQtblObJUh6zrytx7zzeJiEix4ta+tRm4QU/210VE5HUv+aKIiHz2orMWPz4O9/HzzzgDokvHbk8dP66DN1QJr2qhSiAzs1/rO26NMEde6WVgBqu0ECirhHEZOgboClqPp4CYOQBdyJcFhcVQJKDoA6oGLMk72+b5VsQ0jFkWJrZ5oKpHSrtJhkopGBlKAVRGlL4A05LIJAuUhhxqSFq/2begetR1LYs5Vu3Y2/gM90jzIJTBnsT+sBQY0EhA0fCPYLOXoOYB5Q2vEjWq7slyvRboa5keYhVFfJtKA7J0Kqj0eJWQY7xvVFh0XjGf3euVfnNgx6PXaZmGKuKAKkcQVwKeXBMEQRAEQRDEgsAv1wRBEARBEASxIJAWQlwRvFqCqmEktRC7S9UQBnQQoL4TQs6gjExOulhec8fFHdNjI1lRuOsRihej8oEQqjemmZXi5CIi2o90kEdlpsb8BbSNfMm951U1ZjakqSFe9APiIa1w20CVA2WSUTWECKrIdNnFGxOrNgK6gdJrpsuqXjIMc7j6sCpwXHBmGkmqpitLYV7qR9rXscY2RxonL0xY+qkLrqwqPJz8nA45C+HTic4HQsX1I/+RdJ/n3lx5RA1MtnVeDW3HK2XoFHVvcK/f+h1f8mU2Go7+8Yv//bWurVWl7QyMkZAqRHiVAGXrWLUQPy4N90Mxwh4ZwLwm6apyjV0eLefVDaCoYFQXwGUIphPuBcYoIiLd57v1/F+/7U9EROTXPv0q16+jMJ4GaDKYHyh62OMNTOM0fsNSHGCCgbI29O2vwvXafIWKIkFBBOYko1mgfDxYc1ygp5qO6jEYubl7w21fDtfrRE5nMAtyizDpG4kUmIE0tewo3H8wrQEFoDaZwxcATaCkvmLXsFBVGtAesHFzsz4A6CCeTmHmBdQEUAOyYdVoxt8nSVzWNCv1bhFdV7O0kI4biDeKGpb2lgQjFozVlzUUFk/f0PZB3bD0n2npX3aviGOBPuo82LGCrgPVk6DWYSg5qubhaVVz5syXLamOTAPrzasVeXMqKK7Mea6gbns91sHTqepxWZGgHoOxQtVmXl/T0v2CfyNEwvoSxNcCT64JgiAIgiAIYkHgl2uCIAiCIAiCWBBICyGuCAnChEicT8PfZ9NWbDCTdmHMErYZzFqSiYvrgQ4CtQ4RkUSpDDOlX0RKIECZMmKuhzkEjGmKjioT9AIdI+0hLR+GN65MbRjCfjC6QXg70Vj+rBlC3zWlgaDP+bqjfkyNGc00i2OPsywYmWR9vR5UGqWlYJ5FRLrXqYLHhvsdtIzhhqHkTJo6LqWeDNw8T41aCCgOya5zqMh0zOOtQAlAXzsX3Vw1D8M4OtuajY/QaIHQfhjf4ITr0/AE5tW1ec+Xbw31rGkcuK0h9AO3F5JGCKEjhJ93XBtZT8d8IgxnvKb0IVVWmLZ0fEshXl/bcfMCeos1r0AYG2FkGEtYGgbC0QiHwxjFqqgsnXZz/Ke7N7o2++6izChfeMMNHaJXtTBMJahapIP4GqteMlmO6SlWSQRh9VnpqW7NbPIljFlD70qlSQ9DRybrroLvuslReR7rb4qIyHEelHS+uHvavdd1+60YaaNDMyAwrbp6H1u2WAqJCl3nNS2cmzmDmsU0iX4vmkZdYwBVDVC/lLp0XZUHcXxx2dVXqHmS/bBkADRac5sgUguBMZS+wMjHNYx5hZmNzq9RcwGlYHDStdzcB/3NmFuBdqHPgdZB1SyovCdhZBUpyczwDNTu6R6wiiKeRqETYekQnlqRxvvNKhThOrznqTBmv850nROY/cAgxppEecqJXo/npbkPy23l4ZFVocX4bWofu2D0QMwJ94r1JxvHZaGY1N4Lg847PI8knhm4UwiCIAiCIAhiQeDJNXFF6F3njtyWLrg/823yIk5va91hdE3twJyeNvQUWX/1p8DG/rxYd9lItbFaLNtTbWSC4cQ6h952uN4fWIzc6fTslDvynZnEyAQJlBN3tJMuu2PD8dng2dx48lBERKadZtR23Wh755qAWD92Yy40adKeVuMUu3ud+8wmw6Xj+BZE4lLNnIpBi9WfzOipTXs3lEHiE3S6sx1te2yOo/TkulbXE2vVHz94vskOwqncSDVeB+aUUPVrseawB56akzecdI9X9eTsjJvnf/Sy3/dl/q8/+S4REXn3t7n3Pvw/3uj6vF99HMHqOSQtms80iXN8SpMW9YRz1jeJkaP4BK8Ih6/+NA361oMttaK3J2Yl3eR8WX83GsdZ6vbebg/7VvthTs681jI2fk0T7zqhnsYZd6yO3TXs6b1yKaxPOiwlRtbtcaX2DSfVSTXBzEecSscqxVY4bnzdzV8VEZEvHbnT6beevk9ERH5/90W+zP4Fp2+d6ql0NoxPl0WqduzzNMony65Dq9e50MJfu/4h/9nvfuXFIiKSb2tUZljNPqvUqeMbTYxufoJkY93TsJ63p7A6Z/kM0RlNGu4YreRSAK1omVN21a7GXkrVB2C8EvqBvmKOhluZljX3GDSwYe89m1XK4FQ8q8X3hh0PbNTxHPFa4WYKbf9dm+Fn3C8jjZZBZzvaS0XcrrdaN2viIzU+GRUW5dWTeN93fQSnJmEU7XqdeXtvteM+I0IS6WQjuTaPf7eJkXkrvm+xljZpuDau3m8EMQ88uSYIgiAIgiCIBeE58eV6MBjIT/7kT8oLXvACabVact1118kP/MAPyJNPPvlsd40gCIIgCIK4hnDN00KGw6G8/vWvl0996lNy9uxZ+d7v/V555JFH5Jd/+Zflv/yX/yKf+tSn5JZbbnm2u3nVoL3j4mpTpVg0DkOsNF/TGNuyiwFmXRenq6VG31aT6GDzne27UPj4zIov09juujJqCW7/ApwhMWwAwdKScLCIzJR6ksw0afJQs9hqJpaI6/CqtBJr5446a72Y5pKMQ+y7oXXP2q6txkWXSJWud3wZ6GKnm0oPOWd1bbWMhmRH59wAW4+ELLQbXveYiIg8pDrXrc+7OGhhQpqNQ7U939MKQaUxntO1pssiym9w9Wy/zFXQvSmUAdWircmLnZ1At2k/6eqGtjd0wGtG2xt0kiR3r+/4ps+LiMiTiC+LyK3nLomIyP/9G2929YKhE7aAFB2d+1Gs9VzcFNZiOtG28IbqKCP8LyLSOES/3GvzMIR1EcZGmL2u28TOK2r3SYEIJ5ukOuhAN+tuX4C+YMP0vraStbmlOkyecntmphrQSMxsPj+Ijb/irDsQ6GoC6xfOn/GfjY+ijkfzAFToICugWYXO7o9dP5Yzd4/d13X259uDwGdKhtCHd7/7cLvVFsbPWDvbvdJnWera/+LB6VCkhgRiTRZWqlXaszQxrUb3STpw/Sp6hnsFK+88DvvP1YUu0WashrtNKhQRae2b7EBNjAa1AGXTQXUTzJCIOHWN2IRTXNfouuuQWJkbLezmsdLTejovOomDE2FekKwLagMoE7AId++VKA6Ga+G1q/WemJXmx9YJLWxQaCyFBfQ4zHVZL962NdVnIDSobdIj7M5B47B7qZwk7Idjvt2AwgL9c58EaWlM2ickK0MPPTMWDO0BaSHEM8M1f3L9wQ9+UD71qU/Jt3/7t8tXvvIV+bVf+zW599575V/8i38h29vb8gM/8APPdhcJgiAIgiCIawTX9Jfr8XgsH/nIR0RE5Od//udleXnZf/be975X7rjjDvnDP/xD+cxnPvNsdZEgCIIgCIK4hnBN00L++I//WA4PD+XWW2+VV7ziFZXP3/GOd8h9990nH/vYx+Sbv/mbn4UeXn3wdt0I9S6FmGamFJEZbMNBsTCW4nivfqB0iroL40YWs4fxtoxUPqAqovrauF6MlnbSVe1sqHwMJ9rn0MZsyX1W21HeQOaurz90MZRZW9E+a5uHGp5vW5FW9GsS/Z5eCH7FtY6jcWz2XJmNL9l0eg0jQ2VElUWKVgg5HzzuPMS3dDrHSp/YfXmY152/7q5b+6yjfIAGsXT+el9mvKqhfA3jnrzPrVd7N6zhxhcdJQfUFz+/YtdKVSzUxt2uD0LwsHH+D3/8ahERufWbnvJFHj7vxKqxHF5Aw0zhuRedFxGRi0dusJ2W6+v+ftXX+hW3Pi4iIkPVL35w24hhQ9sYtuXLIfTtrcQlpgvY8D/oOlD7GOkivPbb/sKXeV7bSSk8MXTUl08cqHzBcZhXUBs8FUGVSqQZaAMf+Gv/WUREPrr9ShER+fnnfVRERLanYX5vr7uO3Pr77xIRkbX1INwN1Za/+XxnU/6JB14oIiLXnTzwZU533Pr+za0vunoabr9vpqGehgpU/0HfXb+vsfQ/GT0v9OOlj4qIyFd33FznE6VjWPtzVURJW26f3HBi33904dBJQuRKH7ph1fXx/3vj/xPmo/lWERH53MDphyfHbn2jcL/SUpJytN4wOGCtDvrAeF01pHfmaEfrVIM+Yfck9gBoC6Bs2LqhMgL1HquLjDJeH9vrUxs6Bp6vJV1m0DtEApWh0GcFFDgiTe4CqiNJ9GopG95aXecwb5nPkhK1CTrXhgnjVTp0L0NfGqo9IsbuvKRTbecVFA9QULwGtVXt0bmf6PmY1TqHcg80tf29locK0mP9N0n76vtj9k0ByiHs1GFzYOiEw/Vr+jySWCCu6Z3yZ3/2ZyIi8spXvnLu53j/vvvu+4b1iSAIgiAIgrh2cU2fXD/2mEsEO3fu3NzP8f6jjz76Neu6/fbb577/4IMPyq233jr3M4IgCIIgCOK5hWv6y3W360KgnU5n7udLSy7ceXxctcol5mOk1sjNQxebHJwMKdothM80HgK74FkaQsWgdRRrLqZYUxtyGJKIiEw2HO0CaiPJOHxWbLi1TI+R7q0hfUNfSGpxQAZKHlblI9l1FI/pyXX3+0jbGgY6R3LUjdoAdUSMYQ3oKf49hHrHIe6ZqEREokop6bYx1VFkMHtRgxevYiIiy7BdtmonIrL2UFDgOL7BjXH9Qdf/wQlVZTFmNpu/58xBil1HY5gVrs/rps50S1PlTzrL6/7pQMPonnN17r7CXdd5wrW59nBVEQFh9cauG8dXHwqqFq99qaMt/NG2+4M1OdSsfDMtT3zG0Vk2XrotIiI3rh24th8OY4bt+YN7rs+HFx2FJDNW3omGqhFOtm2A/uFNTiA8Y1QHRm4aZLyhyhUrbg/1jRV4TWPmZ5uOYnTj9bsiItLOwh7Y67t92264965fcmXPtIISyIMjp5Tx/z77ByIikuq+2yvC8+uf7N8hIiIvufEp7Ue4t972PBeB+41HXJk7X/opERE519jzZd6+HB8k7E3deG7KglTLVG1s/o8HHJXuyZ1194GhLzxvzVE8btpydbdSV8+fP3ZdqKer+33J1feyzSB9utZ09++LVi+IiMhI4/Q9M/n/x/WfEBGRf158t4iIPLrn1n7QDXOf7yq9C6or6KIJ93sKm1IJsj4oG6FMWR0DVtyRPTasu5UOURjuSfMgVsyo98GjqFJPZqBstJTWYdU1dE/WVS0EqiGz+NbX67WsUrCsokhtCvMZrVfbtjSIuvYDFIm6uTdgdFXXRyCeI5aS4xVWSrbnVskDY/YUEvTHsIfKNuxQCbFzP9pyzxyvpNMMz+DOiluYGSzflY5UGHOryboaeOmezJW6UuuHRqA4k5Ufz5GqzJyFIIg5uKa/XC8S999//9z3L3eiTRAEQRAEQTz3cE1zrqEO0u/3537e67k/UVdWVuZ+ThAEQRAEQRBXgmv65PrGG12W+RNPPDH3c7z/vOc9b+7nRBXBhEDVNXohPDetxyGzXM1k0n6gY8xSGI+49/JNF3+0GdmggwDFsgnBq/JHoWof6aFTBvEqIiIyXUXcVkOIMJgpDH2hpeHkI3UIGDk6xfS0oR1cVHUDqINAEcSY4vhxgUKiVAsx1BSMLBno9UeGhqRUE69MMlBaSm7mbFVjtAgxK/UkG4QxD5UG8uT1blxt59Mipz7drbSVNF2Z2cCFUxNr8qN/iNYgSWJNQbRY5wk1a9Hmz/+NEDdtPeU+G57FPOgaTMJ8DDXmvnSzo0YMxmvaplEZ0PDv8cDN/VcmTgVl7cZDX6b/58rZ+KRbs02durH5WxmmEeWQs0hQVIF6yrhTNbhoKqMiHaqKy3XuoppxiPnY4y8REZFR7hr5G9c/KCIin965wZfZ2XOduu7UgYiInO85tYyDcduXecGKW7SfffyNIiLy2L4b1y2bu6EeNXJ56nE39qQe+vHotnsvU0OYVPtYN04Z//tD3ysiIg/vu7KbHbfeUBEREfnfz/wPERHpjtw+Kca68P3wz8Xnc5evsrKmyjyzEi1DgnrDuO94An/w5PP9ZzCNwXi+5YTLj/mz4Y2+zPHULda3bLjPMh3P4/V1X+YAyhR7Sv3CLWHVQ8DQgAEQKAmGIwEzH6jDCKZ1jjoGaAM18xloF3gP9BDsLRGRmTekcXspVQWQwWa4N5Yu6nOx7d6r911HLB2hqMf7FEY32TDshfGKUtG8OkeVpoL3vNGLeTzi3gBlAwono3a4PoUxzXJ8jWFMeeoN7qOBegTVzWOprM6BNSjaZhFVEaS57p5Z68vB2eXW9R03Du3s3sgt1N4g8H66os88XZdioEZYmdkDA6ULlYxmLD2lXmX0EcRcXNMn1y972ctEROSzn/3s3M/x/h133PEN6xNBEARBEARx7eKa/nL9Hd/xHbK2tiYPPvigfP7zn698ftddd4mIyFvf+tZvcM8IgiAIgiCIaxHXNC2k0WjIj/zIj8g//af/VP7BP/gH8nu/93teIeRnfuZn5L777pO/8Tf+Bg1krgB5p5QtnZiYmUbY6gMNZWpsNT8R4oRZV9VCOm7rTZbda+MgUEHGm658duzeS0cm/gp1EA1lTldc2WkzbOVs34W6C6WH1LyJTNX8RTSkmuj1EQXlWOPAUPIAraQfQpLoT7KssUSlWkjTpMzXNQT5wMOu3qUQrvSzqWonMw1fjs8EbsPFb3Xvjdbd75tfjLP8RUQaypaoq4kFzFKGJ8OYkw0Xym9ddHSDVA19hteFtrwqgc7Lo/9rmPskcWN784tdcu/vPvAiERHZ+v0wHoSax1vu+uWbnRrG0ROrvsyf/ultrs/77m/7DGodZjwI0Q4vurpPvcCZnbz6xCO+zP/zmde4fun1eJ2asHTrlS4evdx0a7hzT1AtQcgbdBRPITFLBwrBLd/uVDb+/g1/ICIiH9t7uS/TH7sLek+6+PjHdl0kbP1kiH3fcp1TPZkof+DSsSs7HodBf/ERp7QxUxUUUD7u750N/VG1g9pYTZTG4XwkV9pG3nZr9h8fdmofzSys4f9y4+dFROQV68545y2rzgvggfFpX+Z3D14qIiLHPd07QzUfGpl7f+gmefiYK4O9mAUGiqgwiuQdtycOu2vhQ1VdWVUTnMf6jqayMw4uum3lHbx02dH3Oqq+0q6HZ8Vg2a3rqOs6UJvALCQ0leJ2HcdmQdbsREqPtZmuu+mOrwc0iGZgKAVqxQxUNPe+NSQCCwUGL95wqR+oCUVT6SDHbgCglcwszcyb0WgflQISTJEC5STcG+73ei8s0ESNu6YZaCqBF+INZkrUkdZ+aAPUl+YB+u5eoQgiItLROcL+aF+My7oxutf+Se1zgWd8aKt90u2TPFezIiOfsjN0N+6kcJ/tD9xzu9sNlKu8p5Q4NZZJlK5mqT3498v3HyomRtnE9psgng7X9JdrEZGf+ImfkE984hNy9913y2233Sbf+Z3fKY8++qjce++9cvLkSfk3/+bfPNtdJAiCIAiCIK4RXPNfrlutlvy3//bf5J/9s38mv/qrvyof/ehHZXNzU+688075wAc+cFmDGWI+TG6U+70Ipws+YQiJKe1q0iNOA/I2kuI0UWYjHA80jvPo+sGpcFzQueiyZnCyAq3XadNoG6/MOaEWkVnLbHc9YarBwluT+rLDYSgCfWwkASFZ0Vqdaz2zNXd6kmii5GwvWD3L0NXpT6yn4YRoeuxON2tr7mS30ATP8brtq77oSc7B81Xf1uRFrjzpPuuddp91b3JtFMYW/vhW1//r/tC11T/lFmNwKtQzusnNb2vJHd80vhBOtYvb3OnR733cRXo2HtA5nIQ9ANQPXd25as1mR9Uk0MkSTtf0lCxIjPuEzIZqVj8xdqe3v7616cs0cPKMhCjoGZvl32ibKIOI5Muhr40j1+5AD7OXb3en3C/c3PZljiZuPW9edkmFj49d+5+4/0Wh0pGe/PU16bHj5vm4GzpysOvWdXXDzSES+qQRbqh8z5VP1L55c8vtjf4wHKUPD9zPs7rO3VLYizPYPffcnB0O1rRs2G//v93vdM223XV/uO6SDIdGLxuYDN3eSXUN6sfWOh6N6ity7MwJMCIAiELghNQN1rV3NHD763P77t5omPGsdVwjf3LeJTl2j/WUfGTuDdUphsU5ohD29BR9xL6wp9pA2T59Wp0OP8ZwKh0+KjQwgz01T8/Zn1yrnX3j2FXUPDLRISwV5hNJkKZ/OG1FYmOmSY/Wah0L0bmkCeB6Ij5aDx3y+tZ6co4TcNs3JKnjmQ57d3u973te1YCulWzYJ4hwmNsSp8EN1bsPcxb6M3gKWZOuvt1+GMeu6OTrabQM9N8WE9VJJ+XTcH2GHto5iz4Kz11KWxN/CVzzX65FRNrttrz//e+X97///c92VwiCIAiCIIhrGNd0QiNBEARBEARBfCPxnDi5JhYHJJ3B+ne0ZkNv7hVJOAjXQ7NVRGSkNrT1ngs7lsOgIiLjVU0u1FBi4yCETUebLhabqsYzknAyk6gzy5DUNIt+t4Au9lQtySerrt7GbohXQpd62mlqX7XPRisWCYyJJgfCBj1ZCZlQs2Mj6ioiM6NhnUBDu6f60ppY2dwLt2bj2M0ZkknHt6rd7+OBdlAojaJ5qHqwn48TrEREsvtdPSPNKzu4XefVDKf5MERmVUfchss187CmU4QEqvOvN2FtnerlL6rN8Oe0MUPHAE0AyaDYJzZZ6OgO92at5eZqqpSH2k4ohPC+ymR77VwkTYmI7Pyus1EHRaFhtkL/OtenF3yLS1Z82+nPi4jIxAjb7uSOtvAHF10S5os7znY83Q1haYSa8w3X10TjyLMiTOyZ0y6z64aVAxERORi7tTsehTXsNx01Ium69vf6G1pf6LMoZeTs8xxNpZmGvfTIY8rvwRiT0qsEOshLzjjb8f/t9D2uP0Wwuf9c1+n+f+y8Jr7CFtrm8WLrgCIxh4lV0S1eCfvkxPUHIhKSE3eO3P0yMuH+HaWMgKLktbTTQHOBnjyS4PJVbaMZyiR1tc6eaIcmVQ5Leqz7KweFBc+wUCbfmEVlaiFfztumT5T5BVlqu3ag1HkaRxv737Sh73UuIglb72Ojl41nHhgj+H0yCc8MlMezFwmO9ePAl8k7MTUPtvAigUaSjmPqlx1Pa38alQWdo0wXsdfXp6Dzhc8wL8jZ9EmYEX1H22hpP/rmRkZCdBoVjTrrx1bSY7dUNPQD72Ec0RqarUcQTweeXBMEQRAEQRDEgsAv1wRBEARBEASxIJAWQlwRvM0vMvDTEEpE6B0hUtjg1mwWeSkLHtno6bgab0u8fXmIy9VGcbnaBKFJoxYCKgSUPJRqAct1kaBn7UOiqqk9Neoas46LcyLE6utthtB1rVGf+9lsjv359IJToUga4XpvPY7ys+qYVx9RisTEXbdzvWq93hji9LOvujjr0U2utaXz2qYR6RhtudfhLS7umWi806tMiMhk3V2/9XlQAUI/xheWdWzad/1o4/NhPIOT+plONRRNbOh7tKkh601XqHneXT86G5Qi/vqLvyIiIt+29pCIiPzcX7xORET+1us+58v81kMvFhGRM+uOcvHg40qLGJpBaxi6dUE1fY16w99+w90iInK67rS4P9d1qhS//9ALfRksa12pBR966k0iImK1T7xKwgz61EoPMZya/Z7jEFz8ygl3vdpt41VEpIWtDb1dnUNLl5msqBqM6kwfTq2fu7uwfdp5NEMTeNILgx5tO97CZ44c9ePTX7jZjc/QkNBuaxT/nloFjhKdC+tsFTRQBs+FZBT22XDs+tRSYeymimKvtINaz/a24/sMVT+8NoQykAn3d2vRewlUIcycNTuu7iRxAxiqHfvU7JNpE2oSEqEwWsvY0/my0jIsNaFEM8CWsHOG64cbqnACqodZwsaRqxvUOFA+QKcTEal3tX1oUINGYVR7skFM+fIUOfMoxjO3pj4CoKCIiMyyelznHMWMYK0ea3JPzb8JkxXcd3pvqFfAxFCmoAVe0z2Ee9RSR0AdE1Vjmc05FsTa1UDraBqNcUwHKCigMFoLhZIKjN/3YUvOpbwQxDzw5JogCIIgCIIgFgR+uSYIgiAIgiCIBYFBDuIvhXkZ3eVQXTasmos0NKQJO92aqmzAEEEkZNNnSvmoGcoI7NIRLg3W5qZvCLfCaKaJD///7P15uGVVde8Pj93vffrqq+hKKEADgoIRQSA2N0G5xgb0fdMZ1JjkPkmu6JOYGBMRL7km8cboNc+N4Xdv8qKY3OgvKiY2F/RCTGiCCIISUISiaKqo7pw6/dn9Xu8fc3znHHOtXc2p2lVFVX0/z8Nzztl7NXPONdeqxRzf8R1hukNGkm9pB1SW0RkO20BSUWhoe5ZcnLAzbkqta6GbnG+r2yY/Z6wViipLWa+aiaqJWS8siQXh28JCSGPvVtVhRYs91La6uGnBOCsg3FvR2jWVGS1tvtJIPrRoCxxBqnu06yZ0XZmLZSn1VWH/2Re5Y578ImfHseNBV31l7Nwpv826imv39vtcKe/qpH5hrk93SMdKi51ARlTYEvpz94Ir0rLlHFe05eqzXZnuL//4JX6b1pSTWjzTgS2FO8no+uDO8oqTnBPIg7uda0i9Gc7xpcdeKiIip612AzFRcfHfi097KrRj8xluv93uXMHpJPSnV0ZBIu2kukh05oNGoluE04z7GwVZ8qYekZd/6PRtaf0e69KBQhud7064cxuZC5xQ6loc6LRNzkJmuhLK089v14NqgQ0U8LGlphP9rJcKj0f3GDbXn+1gNuLpqGFOVx0eCqvCnG6rc8fWp51MpjTt/p63/yLpPEm0VDru4+JMkEigTbguBXWF6BnJRlPdV3yb9auikeR4eQ6KXGnJdhSlEQnPOrinoF8ipsx5alzstSukii3Zsuf+HJBa6HMRz4ParjBRsgVvUEwmWx0HLkZe8mGkH/65mkMRp7B/frfuV3IDAhlft5xdj8O44JmeGFlISZ/leD51qlre3fS92MD++lPHsmJKrZeK8ZyMCrt46YueQ++/kjFpCgV84rbDRSVqv3axOuW+a48YuUy2FhYhfeHKNSGEEEIIIQOCL9eEEEIIIYQMCMpCyLIoz0M24P7Om+IG+AyhQGSNR3IRlRuU5jRDHdUWzEaFdhwSheRCJIQ+kXUOVw4b7ss3XQgVjiCdEZUf2DChHru1Qp0DNNzXM/KU9jCkK8ju1wx64+TRratkYw4FRDRjfjikuueXTKUCEZFmCPEmK1yYPregsVGVieSKoQhNadrt74vxaPx0aLctLKGuJxrerszBRSX0p7LH/b7pSufA8cyXVPKwNjQNodGR7RrKt0UW1Ilh/qsbRERkTL+bza3028zrNuU5/XuTu15XvfJ+v80t3/lJ1/eSOiOoQ0llKrS1vMf1FcVFTjvVSU8gBRERyWnIftWYc8fojbqx2zMXZBB3P+vcMOqz2SonmzY6ectbT3IOJB+7+8rMNjmVc5TXu2O3FjUuvbSP+PCM2yZvwve+GAjcLDDf+hSo8FIPhNJtsRKVGSAEXgwGOP4W6s26gz+z2V1YL1eRIEtJJmB9oW4bo2FOduEeo24aUE6VjRwDUp58ylGka9qaLh5Tq4RzjNbcjrM6SK2G05V42Y2IiMovejV9DgypLKti5A/1YtRHuEHkjENRvhlLPrykrWe20f18saGZrD0Grlk/aUCvps8svQiQIdhr5+UbbrpKd6XeK/N2omh79PmEfewjFA42vQqefSiWZSQsnVg7AlclW1ALz9VeGdIPcxa4Fnl5is5bU0ALz7pODQOjn3eN1KIcF/RCvxLzvG6N4dju77JK0/D8FREpL+hnXgNiOoexVmlSGQ5FZgwgO/T3mJeXGDmiyhiDk5V+biUsRuZDyL7gyjUhhBBCCCEDgi/XhBBCCCGEDAjKQsiygOl+z4dITVitHmeGI0xdng9hXF+QRUOZeS12gFCpiEhPM9R9KLOUDVd6lw89f64VzpFoYRa0ozSv4eSqKRpRRva7ui9U458iIq0x97M9hgO7H7XdYZvapBZ00LB0ooUyOqtDPLgEV465PoVydu2J+iWrVrjP68HCI1dSWYuO74Z/c9/BUUAkjFmvmA1nAzhTPPLgC9wpN7n9azvD+K548zYREZn7onPXGN4RxrXyb3HGPrL7KyaEvnSma1tRC3WMPOXa/n+feIXfZljlApe/7XsiIvKvX7pQ+xfaihDv2Wtc4Z3/9u03iIjIpS99zG/zb995kYiEwiwIFa85M7iXdHUSlLWwy4XrtvrvejpBP/69n3Hn10IqcDMREUlUTdKadNcTUpR+zhlJKSWZMk4TmIyQFMCNwsoX/KZw7uj1uZYpx4ueaUdH1TCdYQ3lo2hLz4by3c/Cc5XoXEnBFE/Sajbl1e6CjA47ydL8YpDWLKk8J19354Ccw0omEi1qk9N7o74rWIo0Rtz8eMdL7hURke5ZbpvP/etlfpvqpEoKdru29myBGgVzOi2psS4sGHtINDAGdhs8KyBzQUGSnJHdeJlLDc8lI72oufukq84SeZUNwR1DJDw7S5Ab6Lka5p4d2qlykGL8fMoXY5mHSHBVAlY+11UXo/KMytX0WWH3aI+5hviCM0k4R3tUv1OHJMiaesYtJElPT30WFxfCoHWwHwx9KlmXHH+/4CckJGab1kh831kZoC8244vauP29g4uIfzYEqUgf1x/U89JHL65BwchcMn0mZC9w5ZoQQgghhJABwZVrsiywKoD/ha/M2hVj/T999YXO5+NEFfdlXAYXGVaJyf7yq9I5bGtWbVAlXJNv6uvcskVljzFrzsfLC/DGRtlhEZHSop4fyTC6Yt1YE/ZbOsm14xUXPCEiIvc9cJaIiBSNhy4SKuEnPfKc+1ndHTIBE1157qx1S+DFaeNtDc/rPJY0s161GIfyLrdfoh7duWhFRVe6hlxfO7rylDcrb2VN6OzqimBjra5c7wrbPPWE866unKTNm8qu/iB5MloZwiYLxejYI0+pN7EpIYwe3v5Nt2KNitdIZBIJ5dIf/Y5LSNxwvmvk/dtODX3GKpYmW5XUA3rmgXARO6e71defOGWHiIj86+az/HcvPc2tYvfUcxlBmHzbrDm040S5vE9INMmk9Xg1zicrmqcrVkJ7KDmPobP+0gX0B39rkqpJ8sNxOpXsOXqon46okt5TtsR6cRH3VNwfW2o6p0t47Xm30jw17r7Mm6THwkRT93MN6GlSW65l26p9G9KExrEwCRCRqOig/e3jF+m5Qzs62iaUEEdybc+sjluPdpGw+mm9oHFdCqlkNLvKnk/ddphbtpw7fJNx/3dC3qwvd14cdw0qaLZvuxkuUGe+pO3X54G2Hd70IiKL6/V+0bYiObxrVsCxwlzSJL+ujn3e3D89fTbg+vh+RsnhWNXWOWkihKV5N2itcTcAqCtgvbCbE+q330DdcE1wHMr6kLc1qRzjWW7bez1OJOzo6nbBRh8kXtG3K87FuFSAXx230SXMgU4tTmwUM08SJLPjnzistptoZr6VjSAQ0g+uXBNCCCGEEDIg+HJNCCGEEELIgKAshCwLn2Cj0cFQWtyU7tayunMbXex6dGuI3SIxBrKOwqL7LimGUCJCmcUlF8vLtUMoslfWpDNN2Cn4kKKRavgytrFsoTodjuMTGWupJD0TKoav7wP/+kJ3Lv186eQQWkXIfeTpWALTGQq3VmnGnTffcWHYXi3UrM63VW9g+u/abhKhlnT8VDKSdNVv2yY06jFRmrmn0pFCMxynrX196X/8oYiI3LvZSS4WNwRNwMrv6X46rja87scMShYdThvWbk5AdhDLDUomdIvwfnU3+qrdq5nwq4Zxx550n03Pr3PHPznoXFae4U48VHbjA0/sVj2Mb3mzy2J76mHX15KRPzz03JmurVq+HH7MNpxc3u2uYwkJtzrktnQ2rjkS3jCXurWs5ANSj0Id+qZwLkh4Cj6hSo9jpAlIouuudANUqIXx6M3hxHqP6jmKS6GtOCZUWL7EuZFX9LQfXu6i0oZkyiQ9quSjiPLpSO4z/UEeZa7kxvWkiVn/3ZJ6xn9t23kiIlIq6j2yJsipOnu0cYuQ5mSTJpFsjGvQq2QTRSEbwE8/vlZpgf0xPvDLttdHpRoo62494EW9xdtFTSTU67N2Xbg5FibcwM6NuTnZnVIffjPvS/Ox7AFyECuZgmQE8gvviW2SDSH/QKIzjgN5h+u0RBQaYS7BD7u+Rj31d7nv2sPhHEWUDofUr5OVi/mkwCYkSrEERCRINDDPcX3bley8Tfq8sXiJVSqR3s5pL3tCkzEHwqNC2irzwTXHONtk+0JKhkTI3uDKNSGEEEIIIQOCL9eEEEIIIYQMCMpCyLJoq9/o0C5kj4cwI8KC7VE3rSAH6ZmSu6U59xl8rntlDW02gmTDKyISlPW1psLuhw9zajn09qhxAlFf7Vwe+2frFXeGNOO/FoearbuG91/V75qr1AWlGcKVte0a9oRyw4d4wznzLZWwLMFyIpyjN6J+wbMae9S25hrGbWTUxStzdXVbqLn4qS3d651VWio9Kbs4aGkhK4X58bS6aWj4c/1PbfPbNP5/rrQ5wrhROfgheO9qN+DC0Azx5Ykfq3QETgr9ykBD7qDyA4RhrfzBu1l4Vwv3s7IzPLLmZl3Z9T3r3eCvXOXsHFaNhjjurmed+0naUUBEpKByCZRf71WysoOCDnm6zLfFl1KGI4iGmq0Pcq8Ux+CDF7b9UH8idN3nnI0xuNzotaiH8YC3cr6Ri/bPGScMf2uhj3q49grr1hM7KngnDVtqPVXGvYufRgpT2eCuw6/9xN0iIvKd6TP8dw9tcz7qva5r0aoJd+1KZeORXFZ3DbhZ1GMJl4hIZ0SfQ2tdDP/UVTOuP0bftW37Cm2cyksW43LdFi8DgdbA6EJQuj4tPxAJ17c47Nr/glXOv/7s0WDF89TiKhEReU4HdHdL/fiNNqE9jhri6sY0g5Obc5XhphF3oFvJ+vhDGldQL2s8dy0tfV7nTa2AxhqV9D3rJlFzhWsjnpsiInl1fPKuPcXY01rElhKHbE6fD8aBA2XHsU3Ol34Px4FzDJ4rKHFuv8Pkxj3bXGU6mXKR6XhHHtNWbRJcYSB/s25XXSNVIWRfcOWaEEIIIYSQAcGXa0IIIYQQQgYEZSFkWRSXUmFFGzKrxiW4fTGZlnG1qMQhWYQprfQj14nPYWUdKAiDkr0IO1amQ8UBlPWFZARhPVtEpryAkCZcG5DxLhmCo4KGla0jAkKHqQIVedMHSF+8BMYWclDHj6Sm5ajVDSXXCbdmrqF9K7uGQPrRnRgy22iZYh3f8rTTG6CMsUgY6/Y3XbnwIe3XU51QdGV9Dm4wWhDCOBm01CWhsVb7qJKG2q6wTWVWXQFUkoAwqg1HN8c0RKzVsJsaCvdFUMS4UYy4vnf3ZGtfFxe0r0+7sZvd7bbZY8qXD8/G+1hnE4SdUeCmA9lLJWwDlwFIM+AUEYWsVZqQdi2wBVF8sZiyujikyobb/YKziPvZmrDSKx07lYDYc3g5SCtuc1TmG1IPFGRBX5M+7Ui5Lthz+Tai3hPcYdYFnctvnvOvIiKypuhi+E+qjEdEZMNKd2FWVZ1eZ3fdTYbmknF6mVSnFg3T57QfPXOPouBPp+HuhaemccGyJatzOvbFde5mLRRCh0a1ktHZK52FzQtqUyIicu/UC/w2kJps3elkJpC0iIjki+5YE+NOCtPQ+/dHc+v8NkPFdnScfNkNXq8UnksF7Q/GHNKEzrpwfUa2u761RnUOqawibwob4X5rrHDbDOnzCM8OEZFOVeeQ7tZYHe4xSDM6w7DpcD9s0TBf0CWJ/4Z8TCRI0Xx7VsVzVCQ8wyFfao9COmK2SbmFNFeE77y8TC9nc2WqUJOE54kv/gQZoJH4Qc7SWKfPnnn3gZWU1SaFkAOCK9eEEEIIIYQMCL5cE0IIIYQQMiAoCyHLomNCfiIi5fnwd6GlRQQ0ExxykE7NOHksalhSnUBshjroVWAngXBhCN9Wt7sYcXulCwOXpl04tz0eYoilWRdzRKGZTs39P2R1Jnuu0iJkDNp2kw3eLWXdCUTiDPOSZq3nWyigo1/Y7H5k0SPL34Qik7xrd6Fa0r/d5wVT+KM7rm4hPjtfx8XIS3JdSGBcn1E8wsoxIA/wMgE9xdiq4K6xuM7FW0eey2bFtybcz+IL50REpN3Wwhka0hcRyUFeg2IrKiOy7gAoKNNVB5FezW08vH7Bb3P+uudEROTfHtvkPhhx86Zkiqa0yi4e7OUDs+pks9XKf7TPKHBh3E+CmwYKoOh1Mk9FhJMhhUkgNzDDM7rRSRy6WpWkWNBwv6lSsmLYdfqZbc7CAPIOGx5HsQqEuRurZa+gMAycPdzv6Gu6f2G/1nh8jrLKZApGCuP7r83vGqcXgGPiON1aL7PNzVte4b7TcXjNyY/771479qiIiLT1ZvrS5E+KiMiOPWN+GziP+PtFL2skhdG5XMKzIkHRFKPdGonv+9a8yqva4fo0Klrgpe7uxx/V3AVvtEzBJ9VPdFW6kjMFmnoqOZlquAHeU3b6odpwcP1ZO7oQHQeyEkhqRETyHbhr6N96Citn6ugzyhdx6WNggeJexXpc2KU5Fh5m5XnXZtwTkIKJBDkYJCMoHoNnvIgpuKPXwP/bYFV93t1J26zyuX7FW4qQKulx26PmODgmVHx9lgW9PEulH0nFPB9LKlFU+U6iY15YaeaGzodEqx919Bw9UyittEi3EHJgcOWaEEIIIYSQAcGXa0IIIYQQQgYEZSFkWfjCEn1cNSC/KC3CsV9/mDBhfY0LS9Z2Q7rh4oONVSFOOLzVhdARrrcZ7iiuUJxzcpCcum3k2yG8B7cRSCJwLlt0pVdWZxOEEMt9ZBAaloQMxBc2aZiNdLf0eCCM6s7rfmJc4KoiIlKoq8tHAU4VWliiYPZXWQkcHrwspBDanNMqHkEKU4j2tf1AQZemmjd05kLcP3eaG4/ynIaVG+HiDe10P2fH3MAka1yDFk8xbjA7dFw1+gz5Q22338TPhxLUKCq1WDMSZCEodPP6F/+7iIh8++mzRERkbCgM/pSG1TvqvFGd1DB7OFVwDNBzWhcXzGWErDuqbrEhZ/87lCNj7nqNrQxSGrR7x5yTNGCaLS0FrUWnG69jQF4SzUm9BXqpIj2dyAUCBW9UVtU2cwD1ZeDyoXPSqFP8MXt7cSaJ9kN7+sgxeiq7QAg/KcMyIrRnaqcbj/HVbnzeu/pf/HffaZwiIiIff/xn3LaPOQ1MoRH2LwdFRdSezoiRJqx093Z1xP3EP2jlfGjsuM6ZoZLbZqbh5vv8UpCSdVXi1NGf0003GXptW4BKnysqMchVw01fHnIDW6u4nxtGnXTqJROhQNOWxdXR+fPqVtIbC8dp51XWpfct5D/RnMR9XEVhFv3cSPZQ+KddiwvOQCYiEp5RKN7SNs+K0kLsSAIHkPoau422Q2UdkCHZIjJd4/jhzoVOhM8w3yAPCe5MYRtflAoyEyND8g4gaFrNdR4SEBGRQjmWBuV1viZmvuYgA4FcCM9247bT6SORIqQfXLkmhBBCCCFkQHDlmiwPrDjo/9XbcrhYFclrSXT4qNpEmaEdbnkDyXlYlR4yyXnwg+5WNVFtLixh5eHnXFDvaC0FbsunN9do6e95t+SAleykZBOQNHlFV3+xOlFfZZOLdFt02f8iWfSz9nB2pQnHxkqRXQlprdDkKiQepjxjRcJKr/f/RkTAjFln1K2SFpbcwZHQ2DWr2/k2VqXd30gsnB4PUYNiPfaltcl91WldaXvSHbupnsJ2daqlntXdNdrJBXeA9pjxwp6OV9yKM+5aPr091Csu6arg/3nwfPf3tNtmKj/it0EimK/kXUQfQnvgi9vVQbMr11ix9qWRkaRnVqewP1bRenV3trnJ0I65PW6V89zT3SrlYztcMlzu6XCgrh4U6WR2DgAkjIL2uDbMJOSNrdSE3o5rx9KukEyKxE7Q6XOOXKqv3us7LMT7FXxsg1XpzpDxjsb81kS+vPqRF80K4coRN8E2jrlsvOu2vcF/N9Ny49HVA+U2uIvWboVlz/ywerU3dTUXq8hm1XPD+hkREbnqlO+LiMiSLnsudUPi3lqd8A/MbhRL1yzpN3JuIFoNdy6Ulc+Z+xg+2aNjrl8njwcT9Ymya/+zCxMiIjK56AbxH7Zf4LfpLGoipK6Mopy6jT6kV6q9X7xJqvbXBQusiMCY6FtbpydKgUs++9DykZE+Jb2xQosEbx81MPcGVpPRNt8uMw1xTyLSAl/3aDXYR9Swuq6RpD7zrYcIifEx989jPA6bGrWz/dHriYhROsFRRKSr194nquIAvX4PfEL2DVeuCSGEEEIIGRB8uSaEEEIIIWRAUBZClkUvNWNyRvLhQ+6apAVP64KRdYiWOW+tcFqCXOLijaU9JpavkbrCogsLI2lRxJQrVwqzqm0ohHBydZeGmMdUKtF17egMmZLiKAWuiTol9WOuzpiEH/0OYc50gqOISFUT9TAu6ZCtiEhLJRHwjoU3tkjwqi3PuT5COmKTQMtz7qAFld34MTDJcAj7QlIDSgshWSqvUhhIeZBgacsvL56k/YEnt0loRAIVxqig4WybwASv21bDxYo7oyoTGQ7XsI6SyKvdvNi0wQ3i5h+c4rdpVaHx0PE5S721fzjut4H8w18PHQ5bGhlhcYTXbQg+neCZlkOIiFQmNdkLnrvDbjzPOnWn3+bJnS5R7ZHHTnX7a1jZJuT566nD4OdAVKLZ/WyN6cYr3Py/5Mwtfpv7nz3NHUZD1blh4/utiVyi0hVcV5sk6Mtqa0g/l0peFAm+4/66wmN8KMTy2wuqBWjEIfSNq/b4bdbWnISlVnD73bf9tNDWdjHqR17D9dWxkLB62gpj7mxYWQn1qF8yulVERGb1Ij46v0FERKYaQ36b6UX3e63s2rGi5vYfLoeMuUVNPu1BuqGJuPgpIpLodVmqu75vzwdP7iebTtLUxLjAw3rBeK4v6mcoS6+XqxTUJYI8TO9RDs/ydjYR1yfZQkJiPKjhN99NyTl6RiYGj/W0vETEJEtq8+Fn3gq3n5fNdVXyAemHPQ60Xyhdj2TUxCbpYqx9grEerxy28QmzQ/pvSsmcJBcnJ0I+lDNJrV7NiGRFlYn0jLzE+43rMye/CFmj6XMfqRUh/eDKNSGEEEIIIQOCL9eEEEIIIYQMCMpCyLLwWdvwvjVZ6LmeZmC38FPLQA+ZmLNS2bmg37kwamJkHQLZALyrE6ORUFlJYV41ASiNXjQuEHrM8qSzQOhV3PkLxlEE/s+1SRdmRLngOOynEgeVBLQmNHS9q19oNXbAsFn1C6ehNDq8ayVDY0XsOQtnDhHjgV0tRH/nEhtaVfeVDlw+YH5r/LLVQaSiZeBxnMRIE4bPcWH9hZYzwa6ZvpYXYkcTuMPY/eHD7D9T6UrH/H98bzw2W378qfVu01UhTL/pJCcVeXq3a0d9wcWlkw1hm/wzep3V/QRjbiU5jdWxw4qVhcCnNx0Wt/3xjggqlYCf8UIreFh31Z2gMKcuN6NufBsnhWtY21qMztEey7YVrisIr1fVLeOxPWv9NlX1UV5c1PFYMPcWwuN6LxQ3uQ5a14R6SraAffKVcG8USypDUh/moaprx2Xrn/TbVFQTcNuzLxIRkU+++P8VEZH/d+oiv82dW13p+qa6fXgpiaGk/tRjI+pFbaQajY7bb1Z9oRst9/eWXnCVeXLE/V5QCcBzuyfcF7uChQ0cKvSH4NayYw/Zjg6vnwNd61gx48Y6mXI/Z0vGH74HP2nt12L23sKzoqCPLu85bv4VxmeQY/WrJ1BaUr/8cuwsYj3pMc/xHED/bHu8AwhKk5v9W6Mphww8Zvu4yiSluNy4LTuetOPjFOZdZ/MtK1XC8y2ev5FkSmUkBXX3GBoKmqtS0c3XpkqN4KTTNR7lPa/H0jaitnnDuNOgTd2UNM8qUKzkhZB9wJVrQgghhBBCBgRfrgkhhBBCCBkQlIWQZVGbcnGxQjObGe7LjqtUwztXWPmCuov0tOx5ftGF9yAPsaAwSmlX0GrkF1z4OIHDhcpEkmrYv7Ck5c71u3zD/d2rGumJxkeL3bgf1o0E2feVmVz008o6kMUf5DJxKW3XZ/dZeQYfmD6mijTAJaAxEdpR26NjnkMGv8pVxsLtW55xY5SovAX9gcxERKSt5enh6oLvbH+mdmgJ73UuHp1vh3N0tEDO8HZ18JiPHU5EwpjBSaSJ3dcEFwhfUXzKXV+0cOi0YKMy13Bh/be88GEREfnmMy8UEZH5p4JdAZwMMHYVNZewjgaQ4qCoRs/Ih+o/4QY7UQeB0g4tSGQLXKgsAM4mlZLKiEwBklVrXLtbE66z/+nsO0VE5IvbLvTbPLPkXCzSDhx5U3SlN6+yAw2Bn7POOZIUzU320HZn55LA2aBqpE76Wa7l2tbY7TQthYkQQj95gxsklAKH5GLWlAIfq7lrVVRZyGLTjcuTC6slTV1dYX77kf+viIiUjLXC0kIsXYlC6nodOjNumz2L7jiztaCD2LB6RkRELl3v3FKe0PPPG0lOve2OvWeXu+iF57SA1II5Fea3XnoUT4rkPylJUaFPgRVfkEhP790lJHaUsMc2hhXeuca73EDOYVxlyvPqYlSLnwtwM7LHbo24AwxNqvzOPN5wH0LqAaeirukP5nlRn89d86yoTrvPmuOQbOjnwQxGWrp/t6oFq5p9HItSMgovyzJ2SD2VlfSGXT9y6kCTDJtBRXEtvVcX5sN89fcCHHS0cJV1JPHfoT1F/FtlJoH+DnlIEU5D4dHlpT2E7A+uXBNCCCGEEDIg+HJNCCGEEELIgKAshCwLZJ9DEmCLlCQqWyg0XTivW9PM8EaIDRZUBtIdqehPF97LN00sHondC4ijmv8HXHLb5druvL0Jp7+AXEREpDta0200rJiHPMSE0DV0iUx9FFZBURcRkUTdMUr6EyFVFKCx+KILejwbcq7tzn7m0a4hrIyQs3fmEJHiooZLvaQGrh9hzHoV7Y93EnGft4dDiBbtR4gY2/SsIkc/XHWyq2wxXV/pvyosqeQEoVSNa1uXgVwvHiPMl4W14VGTr+i1G3L9ymvRk4XdQUuzWHHz4pbZl7g2q7Sg0LPuNNp+PbQqL6QylemOH/tmMJqQ6pCL8Z6yYkZERGbXu3kz+eOwUb6uIe9Jd2HmG+5kzdEQyy+qW8GShqo/+dBPi4jIT258xm/z1ARi6O54Z23c4Y7TDeOyszIqln/f4VxUmtvDuBQXNGQ+igokZuzh+KEh74JKTsZHQ4GmatG140Vju0REZOO6Sdfndjj3XbvOcE1V6UtH2zzdDO4Yzz7jJBqFOdf++S4q8IT2F1tZxwyAAiHdMTcXyuoa0u2Eex3n2LpljTuOhvmLQ+GZ04MUZk/sHJO3datMfSoRkXwre/8i3G+LrIiEIi4iQaIBOZItNuQLw6QKxBRMO5oqV0pQIEbnr73XMValOmQL+tM0uTkO6Ve8Tcnch16q5V1y3M9KMzyL/bNCP2qNW1mI+7CiD6i0lEUkyEh8P+bgUBK2kfhR4ccpMRIUFDbqzmphF7iYGKcRuPWISp4iRxJfdAwVb1Te0Qz7Y75VpvJRe2zxJF/YCdIglQ9Zx5YCi8iQA4Qr14QQQgghhAwIvlwTQgghhBAyICgLIcuivBCnfzcnQlyttBgXfSnt0VhiO8RPUfgEjiKdUXVoqBtHkEWVeGhRmmQouAPIglYxGHX2D/lZF7uDPMSeo7XGuSUUl9SZoWkkLAipahy2NK8Z98UQSizVta9dZN5r5nzZhBs1vOndAjTkXJ0yLh3atMoC9gndQYEahEtDUZqwTXvEhTsxvnltT2NlOBDCxgVtMzL4I2eSKmQheg6NotqwZ1FDs8kG3XF1iGu36lqkQZ1MclqsoWZkGHAiKaHYBKQnxdDWxU3atKaGaFXakK+a64P4+FYntcCDqlc1LgMokKG7IUxfX2f6o1MJId/efBiQ+qSbH8/ouRrTKlGyxStUYlGeVnmIzoGmcRlopaQnHXU0uP/fzvbblOBaMuquz+PPOMlHvhTujRUTbtBeMO4cPR5RWYgY1wP0vzivMqCykYXMosiQ+7urUqFGNVgcFIfd+Re67r77593OhaVcCO34xVO/KyIi21sTIiLy0MwpIiKyczFIR3JajAPzq9CEG4WVCGmb9bPEmvUUYmkGpDX4KSKSqHyoq7KUnv60NaWSViE6P+ZC2biFYL6jAEp7FK4QYRu0Nd+O5UzW4aSbMjSykg/ILtJFtoz5kHcwwT0OWQfuGXuc4B4UF26yn0HmhXP6e16MvC0lHenWwkXIQZKmYzay1epcMEbx+a3bCPqRlsJYKU0XSiIdR7goWdlOkJXoPjrOpTnr1BLL+LqR85P7AekKpHXW9QdFwzCu3rnJAEcUzBNI/MQMS3EpnreE7A2uXBNCCCGEEDIguHJNlgVWbb2fsUlWxApCUnD/z9Ze4ZYt8m27DUrbqnf0U2qcWjSlaofdEgLKqeemg/+xjLnVs56uZueX3BII/LLd/u67yo756Fwogy5iPK91Zae44JY5OqNmWVlXlHwZd10JzHXMquW4fobcSXTTLKxUZ9S7dhgr3+E7X2ZZV3SQXFgyZYZxrMYqd7sWtfyxTXLCcfwKje6D5EWRsGrUXCFRO4a3heOUZt32cwvuGoyOmWwwLdndUu/r5qT7oGxWgytz2ja/KoeV/fD/8bmuG+PFF7trltOy0pU1YampueQ+K9bTHuFmNQsrb7pbS9vXNsfpaLnk3jNuTtjVxoKu9DbyOt8K8DzPJkLB7jvJ67xfCBcYq9s+eVL/7q0LJ+vqanZhUvulCXitM0Ii7mljrpM/nnQJfA31fs6NhP6U1uo81dLOeTMJMDQdLccuGmlYem7Eb/PYTvf7Y51T3Qej7nhr1875bR6qnCYiIs8uTYiIyObdLrGwZcuXYyVzFGEDeNqbe2PE3RTl1W4OrRwJhuo5bffkrGtPY8kdG0mmIiIna6Jpo+PGbPec27Y5GyJZeU1iKy7BA17HIORe+pVUX64bSX59SoFjZRb3RlR+XLf3SZNm5TvtU+8vi71HdZt8yhvfetpXZ3rRfn44TVux0g1P7Jw+XzsmebkxgWhXLzqXvX/aQzk9p0bETKInVsGRGKm3rBTr2ZVbm9gpEkf2bLl0157YY18kXCv4SWNc7fOtpVO4rFOoZ7z5/RgjipJKYBUJ3ubtIT1HarVdJCQroh3ol01yLzS5ck0ODK5cE0IIIYQQMiD4ck0IIYQQQsiAoCyELAsfTmtpKHIohCIL7U60bVMT7oafCbHBzrCWPUcSD2QiXeNbqqXNcxqmTEZDsmJSVi/UIZRPb0Sfi4jktPw5/LG9PMUkDnn/2HacoGk9rJM8SpnDf1WT0ky573SYtINEqG7WuxZYH1jIQJqr3fajW1IJkmI8YrtxSDUxnrxFJDJq+fNQItmEXzWaXtTEKjTDhl9R3rj1fTfmM5uCFOCV5zwhIiLfefIFro0p319LTse6qL66dgyGd6p/snqdN9e7edN5PCTMleKp5MegMhM+w9jh2EhoGtoSpD31Dd1oW5tMCr/u0pT7sDukEhJTIl3Ui7uH/D1NviwNB03AxHAch96lpbiRbCciUlZf7NIKt21B62J362F8f7jTZWJedtqTIiJyd/d0ERFp1kOjX7x+R3Suy1Y84X+f1BrvX336xSIislBwcpfenJFzYLprvy594WYREblgLHhy79BExv/P+gdEROTR8ZNFROSObWf5baa2Ow2O9xbWi9CrmvtJ/ajhXb1jV6hLD1lIot8hQbLZCH2dWnJzsN50n7V2u/u4uBjuv7LKmIpWJiASyTHS8wRzwFh7S2O9G4/Krjgp1Ca+5VNzMvL01inQ8/Kh+JwiQRKBBL5CKglSJEgRcBxIEqIy7HrfQ2lV6MJfuo+hOKQsmrCN5Gh7fpRRR+0CkSD38+Xgm9ljoz8Y67Y+a0pL4TgYMyRToz2x1ML9TEsOE6PbQYJqWgomEq4nzgVJXNGULUcb0WeMs5W0qAW8l+34/hkg7SNkfxy3K9ff/va3JZfL7fW/iy+++Gg3kRBCCCGEHGcc9yvXmzZtkssuu6zv54QQQgghhAyS4/7l+rLLLpPPfOYzR7sZxw1eotBDafB0rFSkrY4bQ9tcrBZe1iKhBHl73H3WHnFOBPCiFhEpzqmLxBJS722qvPtR0DBnUspOYS8dqZWitlqfa0hHemNqbqrylMScq7ioYe0aHAlU6rAUAj4+FJuLg0A21Iuwqw8VmyY317gQ6q/99O0iIvK3n/sZEYnDwAXjSiBiZBhR1BJlijWcW0CINWyRS0U5EU7tF/4sNGA/EsL09w29wO037eQcNZWQlIz3K+RCaBtC4NUpE8fNuWs/5tQP0prUAbHuDd67V/9GaN+MHTL3EQ4utLLll/PqqrF4mpsvtQ1BooTy3q3FUnz+JSMxgisIXDFQhXnJyBdU2jAxltImNMIkWHmS+25VzZ1/yx5XVn7jmj1+m90LTtbxyB71wFZnkt5iONcDjzipCFxLHlwMiwTeW1nLRhfUacVKbDB3eiXXtnvv/gkREfm3wk+EjbSPX9QS0/kJN4nyxRDuzxVjxws4PBSMZKPXcu3uqIwqZ+Q2CXzCG9qgeb1nzX0zM61uKbptUUvRR44vKsfwftRplw0JcwhtbY9mfbdBa6U7UEHv8fZY+A59hANGwShgMOdwL0EiUWxY+UPsKgNJQtlIyCD9gu04rqn12w7PEXiLu43Kc0HjUMT9r7KstjqJFFrZc0FKZl0+8B0kEqgd0DFe2pCnwb0IPt69spWwJNF54V7UqYb+QGrh3U/gj2690PWC4vFsn6+lhXhcIUGxc8CbrqRKztvjZJxZ4Cpj5IRoIyH747iVhRBCCCGEEHKk4cs1IYQQQgghA+K4l4U8/vjj8sEPflCmpqZk9erVctlll8nrX/96yef5/xUHQ223xkZValFohlAkwpMFFFnRGF5hKUgCEh33gspDCqbsud9GXT5yDY3/DoeKEJ2VzkEg13HxveK0huLrQf+QqAtFknLu6FVMuF/PkYc8ZEjLsBv3kF5Zt9E+ojhOLsmGehOUQdcwahRiHYr71zPmDbm1ro//z/0/JSIiVXX0sEUwfGEYOAjAoaRPERk4mSD82VgRtkEhBYSu8yiGEbmo6Dbax7IpAtGYdY1CKBXtQJ/tsUqzTd0WuoEwHrWdLo2/ssfNl446GDTHTWEWuJ2MIfTt/m6aMH1lNnYnwJjbEDocA6rqAlEfCfHo2qj7sqhl14sqexhaFWpnd7WgzOzkSNwwMwcgcdgzpdvg/CasvesxJ3/aUVyl37kfW54OHeoOu8FvrnRah+aCFkpaDOMCl4R8K+tagII3kPSgEEp7zFxfqFu0JHlPXUPyFVN2fN7JOcqTKofa5q57N9RukTIcHiDbQRGWmhkXdVbJ1WHfYL7TsSmq5KQHmchckMBADoJwv3cqsk4R2ibsjgIgXSs7wKXTc6KEfDIS9DJepgJ5F9xMzLz1961KUaykwJckL8el1a2bENpdXw13Dr1XjLsGZGbFRi/6295jcOKB/KK+WkuDG4lcKB6j55rt6DbGgWMela/cZ60x83z05eBjN6VC1GfRc8Tn7BhtT2dI5WraR+wftyOWg/giO1aip+OLZ6B1+ch347HHtSiYeWLHzx0n3lYkSOlQTCfMO0pByPI57l+u77nnHrnnnnuiz8477zz50pe+JGedddZe9spy7rnn9v188+bNTI4khBBCCCEichzLQsbHx+V3f/d35d5775WpqSmZmpqS22+/XS6++GJ5+OGH5YorrpDZ2dmj3UxCCCGEEHIc8bxdub7qqqvkhz/84bL2ufnmm+Wiiy4SEZELLrhALrjgguj71772tXLXXXfJa17zGrnzzjvl05/+tHzwgx88oGM/8sgjfT/f24r28UqvGDtf2JBZQR0/cl11BFnpwsml6eDmj++KO2bccUyY3m8DVw/IQUyBmcKCi0XmISfR75Ja0Fr0qi60DMlIb9jFjnPtEEvE712cX0OjxRlTeUDDhJ1RDc+rPKRn4sE+818dI7rIprcOJyheodHx5qrQn/UrnTYDRUWem3JOEd6tQ0R6KbeQnEoVcpFRS+ycATlFxfz/ow+p6umRuT+8w4xLF04KcAII17cyrfKYYpyNn7NzoK5zQGU7PS0yFG2j41iYVxeKdln3DY8jFLsoqSwFcpfmhJHbeFeBOHTeNoVz5l+g8oMFDQPvNgVm4OZRc+3pTLnzN0aMu41aQtTG3bx46YZt7pxmDhS14s+eptP/zLfcfDlnYqff5oHdp4iIyOS2CbfPnI5LVCxIHSqedjqGZFTn25DZaAnONdgnfFWeQXEh9zdkIb2KCe2Pu2OVht39Mzrs+vWm0x72m3zpyZeKiMhcyUmwurNuXOychIoC0qQg1TDzViUiuRH3ZS4f5kCv6Y7ZVbcQL0sZDbH8/I5KdF5IfKIx8+4n7ickIJDIiIR7NIEsBffsQphvKEzjZTdwoDHOJHn9PY8iMMYJxDteLKQkW+Y5AFkJZFn+OhlnoLTkC84XObPN0HZIaVTyMQcpmNWJuR+tUb2P5s2goT0q44P8zYJ7tDkRF/3KG7cRPOsgscB9V50KDybvElKNHUlsQZ6mPqtGt+l9WFPpoJF1oKhNTvfvmQJa7aHYGQkuLlaS0xrF81CPo8MB+Y2IKcAFNxb93DqkUCJCDpTn7cv1li1b5LHHHlvWPktL6TJdWQqFgnzgAx+QO++8U2677bYDfrkmhBBCCCFkfzxvX64feuihw3ZsaK23b99+2M5BCCGEEEJOPJ63L9eHk+npaRERGR4ePsotOfZAKLC4qCHrUgiZFVoaa9NQaGnGxVEh0xARKcxrbLeiBV7a8T4iEgq6FDV0br6DuwccRaSoU9hIPorbZ3RjDReqRAHFZVxHNKN83qX+J1UXs01K2coSpWm3TWuNC/sX54NOo1dGcQY9B0KkQ9lQb3NcQ8fTYcy2b1mt/Vf5grpAdK1biHfn0KarQ4I1vEFoGaFmhMJ7UdEV/U4joQiRRm4f2o+uyjlskSA4J6SL8iR9nHdwfbo1lRTUbRxYQ7M9FOxQ2YAJuRYX3GedEZX41LFP6FAIq+ODuH8iIr1V7lqtOdfd88/9aG3oq7pYdCEXKGt79tiiR3o9804+dM/0mSIi8qJNz4VtdLAnyu4Cray4CNpYKUiMzhh3xWLWDjsnklbXnbvdC/Nt09ikiIicpFqez//wZW6fFfN+m0vXbRERkS9+/0J37j3h3sIcQP/h1pEfD/N11YQ7/1zd9QcOJzc9F6rYwqWj0IwdSboV46ygl6FXg5OOSkDMVMiVuvqZujkY2Q/OkdeCPbkurrOR/ejp0oVirFuIV6FATYE5MWQkKCiGU8ec1nMbyUdZhxjFTeCsk4+kCSpx0Hs7b5QWuDexvXcAMSqCthaTgqsG5nRzhZFDqbMQ5CWQOuRMoZnmCjdWKBBTmckW8mqNF6N21Ne6fWqToUO43/DTPvkg/yst6HNen2uQbIgElw5IPPBcsEVkcvpswXEkV4ja7vZ3x4QEBhSsZKOKAkJwqQrfVWd0fqkDiZdKmX83UGgGsg70J8k+uvw888+5Ps9HQvbHcZvQuC++9KUviYjIhRdeeJRbQgghhBBCjieO25Xr//7f/7u89a1vlVNPPdV/liSJ/M//+T/lk5/8pORyOfmN3/iNo9jCYxP8n3u7T6JMoqu4AivsKpZRTTlcrDjnSvHfZmXGr2pr8qM/rohIt89Kt4gkQ2G1MdfUhJ/xlMG0WWHNdVr6U1cisCI+HMx84WeN1ezibCqzUMKKLEq++5Ua413bVq/X4R3u74bxKC401es5Vea74Zk1cAAAqEFJREFUa7yw4d2LBEKsFHXDoqVfsWuP6jbt+KdI8P5FeezSQi86rkhYecf1sD6/6ZVr7/ttEqn8NpoQVZ5yS3rt8ZC4mtPk0/xiKzpX3kQf4HEbykG7n9WZsE1rFJlHuro8nE30HHrMXc/Fle6cG88JUrBnHj7J/aIJouVxt5Rpr3IRpcd1zMq73N+Pz53mt+nVdGVUV3p9Mt2wrTvufhQ0cW+o5s4yPlT3m2zUevLf2OqSpAvqu73YDJMBK9bw0sbKvIhIb9E9zhNdgcctUjJly2vldvTdQh7nCFG8vJYZR9KXTxw1cxIr1b4sta5OV8bDav0pK2ZERKTZde3aOR08vVvz7mA9XV2HN74tSV7Q1WMkK2Le27VDn9Co/5IhOpOftElocYYajlcOAQF/j4UV6KzXMhLsSpPZiA9uRevfnKYy0422QQJd0Twr4AuNldXyHKJD2che2ou6UwuDZxP1REJCsO1Pr4rPdJ96NukRic2IENiV3pyu5PdqSH7uZbbpaR8LemyUaLfbFHPm2S8i+U7sW+/adgArxvA61+tigkI+wNFN1SNICvb5pttiXLGyb/5tynfjthKyN47rl+v3v//9cuGFF8rpp58ujUZDHn74YdmyZYvk83n5i7/4C3nZy152tJtJCCGEEEKOI47bl+vf+Z3fkW9+85vyyCOPyKOPPirtdls2bNggb3/72+Xaa6+Vl7/85Ue7iYQQQggh5DjjuH25fs973iPvec97jnYzjjsSTWAsz7gYKbytRUS6mnyWRyKIJjh2h0pmf/VWrcBXVpOeet3MNkleExob4Rzes7qHhCFNMhoNMetS22UDWl9rEZHumPHCVi/jwmI72jZfD1lOSID00pE8ZBCmXLFKWMrTKivR8bHhRngsN1ciqciW3NVx0Oh+a0L2ig+Loxs2WUoj7o2TXH8q2925ekY6AolIUcO5SIDLd0xotLf3sKeXg2DzQjYEntMQdXOdk+QgjGqTFTE2PZ0X+YZrWFSeXv3LvfeshnNLc2YuFEtRexA6b42G9uC7hX9f6X4ar+WSJs+V5t15WzV37MpEmAPdafdddbfKFnQ8redzK0F4P04o7E2HuHRnREPmeoD5Fe67hbkgl/m7afc//F2VMSRTbq532iZBTJMvi+vr0bYiIjktJd5Z0HHRvvZ6Yf/pRXddmq2iHlvbaMYF7UcfvT+6uYY5bVMX8hD9uzkXZFWb59a5X1raxraRaiBpzPtBux82ERFJvZD5QM5UDEqaIBlpx223Sa0h4c79LM/Fn4uEe8LLd1AC29wPkAfk+igUIEXoqOzCJ3xXrI5C21yAL7N6wZukcMgmvHREpRul+dBY7yGvz8mOJh9HJb5T8oWqPnMg53PHVL/5drYdXt6ST3nam8PmUmPVnNDntnkuIHkz4/+fmOdB+jECKZjRZ0Gy0dKk0PKCSXZEW1MJza0JM67zKuXROYzETDtm6Afas6Rl5Ye3h7G3JeIJ2RcnZEIjIYQQQgghhwO+XBNCCCGEEDIgGOMgy8JneWu4EFIQ96X7gXK63pN0yVhWaFgQpXe9I0chHMd7WVfMsfHdogvZe3cQPV55+1xoRjH+f8ZEvbA7Q6bc8UI72ibfVGmCdR1pIZ6MECkOaOKYGgJFPzrar64tmauhR4SKC610HFRkaa2GKVWRYEOi+AxhWISzm+Nhm/aonkMdKnoleOGGbXDtUG64NqWyAeNwAP9hHw42LgX+ujZSIW8bgi9oee15SD1UBmRCzmgHfJTxXXExXBOEvMszbiBaE+VMe+Bck1NXmsocQr5hm/qZbv/SkDt28mRwxShqaXVf6vpRJ9ForAsdKi/GnsZpBwt3UHUrGcd46rVYyPY5v8pdkNxulU+sDBf6P5zhKtLeuXWTiIgsQvIxE05Wmlf/cC21bs2JuytU4gR3EHWi6e0K0pP5QiXaL7+kYXbjaZ2WVpQW8EXYBm42hZb6dY9C9mI96SGjcn9X9ljHi/gcLZ3LiVFydWtoiI6vloNvm/kGL++Slq7HtcS1FQlOIIX0fdRHEgDJRi/lKiES3FMWN7g+jz4b5AINlURArlBf464ZZBEiQYYFJyHvtWyGBdITP81RxtzIEUqQnKCt/r400pEepF8qMdJzFYzrBp5Rvtx3wT4HVAKj/a+vUb9681zCNmmJRa5p3YO0zQuxPAR9t/2AZCPp46ntx06PAwcmEZHmmPbfS3n0nEvG67yIc0i0jfUq988T7VcNSiHTVjzDCdkfXLkmhBBCCCFkQPDlmhBCCCGEkAFBWQhZFnktO4sQYmHRuDdoeB6SC8gzIPMQEemOuhB1adLFmlF2vDNiKlSggAhkGbYkOdxFmrHLh5is/l7Nhb7h3FHQYiWVbUE60lmlpcy1tHmvisImRkcBCUtNnTe0+InNdIerBUqAV3a6fnUmQv1yZPdjPNoj4bZDmBWhdx+yNuFXuIMgLI1QsQ/Xi0hnRH9Ou40rzew2+VgJ40OtNsRaXoCTAWQuRkqjIeXGaneO4pI2yEg1cotuv9aEhpG1mMXSOiNtgIOAFr2AA8jSyUNmGy02AdmPykNQTt2CEC+K6qB0tYhI5RnX1uZanUPjIaxbntf5Oh/vV54zIecJ7aIvQ+1+FlNjqd+KiEjjDPfli1661X/zg8ddMauuOme86hWPiojIv/74TL/NrQ+c75p4UpinIiLFRSsxQjsgXwjblZ7F/NQfOlQd48CRhyQJBTfqscOJSHDnSLti2HLhvlAP5C6tWGLQb/+CcfnAfh29Taqu8ntUqKa7lJIt6PXq1kJ/uqvdgMCNBWNVDLVsfPEXjIeg7UaOAccJ3H8ZBwsJUpHqtEoTRoy7hh4bhY0gX7BlulGC2zuAaEnwWP6gzyxILNqxNMbtr3IfPBYhSRsJz8l8Mx78QqqojIhRc6UKNkXbaJ9rkyo3K2YHJjyzkuhvEVuSPBe1q1foU/AGUxMlyo1cDc8M9KNn/k0Y3hkX2sF1sfcG7lu0vzLt9umasUf/USoeRX+sFCTp45BESD+4ck0IIYQQQsiA4Ms1IYQQQgghA4KyELIsUBSkpxKHYseEG3sajoOUQKUakFxYWmtdpY/ypEvrzzdDmA9SALiF5FsmC76rcgEt8OILvZiCMdgGxV58UZqakSbsXojall90ceTeaHBWwDFRxAaFLxZPD1VKajvdfoW5up5bHVLmQgzdF0vRojr5jgmJqrSipmPVWcq6dCS6ebesWfSqnrCZ7pUplU9o4RKE5CMnAmTRL+IaZqUFCMXiO19cQ0RaY0aeIyILJ6kjwlKYA40JJ8mBrARh7rwJOSNsW9T92uqEYAt2dCAZ0eIZjbXuuAg922On294O6hIvN6jtUklBqHESHAOgPoK7gJH9lFQmg2sAGU8venLimumfW9ycenTq9LDFiliLcPdT7ruRsaBfWNrhLDPaT7uCN+hGYoa96J073I9uUB/54jkdSF+0wEtxOjQWshLIhdJSIREjN0gtvSSmz16Kg3GpZ7fBsdF+O89QCKaIQiR6u9g5DelJtxrvX54xThOLWgxKh9FLgmyBJYyR9qe2Wx1GjJMHpBmYg96sw4xBsR7LHnrmugzNqsQDBV32IbGAzKA1np33XkaSdusxcoQOij/pWHWqWWcTSHggY8h34VBiHGzgiFKPpX4iRiKyDxUEngeQsHiHFVtsCIWnUENGCxqVjNQCbiH+XPoTBXXssSGpaZgCMcO74oI/cKmy184Xj9GxQtshjRMRwb9SkINAggKJm4hIZU9fPRghGbhyTQghhBBCyIDgyzUhhBBCCCEDgrIQsiwQwoPcAA4hIqFgSFElFp1hF8ctGslGfsHFK/NNzfCGo4jZpjOqAToN8xVngnUGnDvgwNEZq+i5g5wDDib5ujqKdNS9pBY0AZCDQELSWe1i6sXJ+dAO/aww62LY+YYWJDEhzeKexeh4PXUCsbIOH/ZNUFwkhBa7VQ0No3iEFg7plk34FnVdfNi3jzODhtC9hES7mjNhdmzfHo6dEbpWFlJE2FZlHWUrT4nDvh2tx2ILxCB0jv3K8+7v5qjZRsO2Xh5SR7/CuRAeD2F29/nSOlNMYykO9UKq0Ql1Yrxsojzrfg7tMqFzuBKgwEYjLnThttFj6jaNldoHU6QEY41CKO0x6AbCNqWdJW2PnnON69BINciH5oc1PD+nkpg+0o2OTvN+sh/Jp0L5ZYT7TZ8XYwkLxszOEzh2YOxCkREjX2ioxGEpbk/eOoIomJuR5APth9sIVDNBAebHD1IcOIvk7TZ6/tJifFwrC4GcBNfJy1SiuY2GxXO8scK4SajMDHKFvDlHc6UbSIxncQnFsawuC+2I3UKsK4Z3YdL5D+cMK02AnMUXeulmnwcFLYiC50h7uJBpj3fe0PbkjJwDnxUX1FVDn/PW2aRoCtKIBHmIlbCgH3DlyMFtyhaD6mRlHCLxuIQiP+7vod32wYZnjp6jm32e4BnhJSPaRhT9ifrRjMfFtrW5IlvYjJB+cOWaEEIIIYSQAcGVa3JQYLXBetkWF+PVaJTjteXIuzW39FaY1+UorITb1Q4tl94ra2nlNSP+OyQi+kRGXaUoPxdWnHujukRVxGpJdkXFL5N0XBsLC261PamZ8ue6ItIb0zbrCnZ5MhgpY8W6swL+3W4JLTE+rL2qW+1oabJf0XiD4xw5LEFi0cUk1bV8eV/3N1awbTKOLUvsttFzm1xSrPogQQwrg3abtibF1Xai3HD4DvsV4Y2MVd0hu42uaOoKZnsY/TTbIPGpG688220aulJXncFKl57bJFj6S1iLV2Nt0mJ7Al7CmnzVzI4ZVum9F69JDLOrZ+4D96M1Zj7C6i8S8EbcL9UVIVmxudMNUr6pkZpn3TLszp0mgVZLebfG4YesK/ImcQ6rxyVdgW6sMb7d69ygn7d2l4iIvHDM/fzGlp/w2zS2uIbjGrbHsqvbMuSOWR11q+qFgiaemkTc5qRrf1u9qFHavGRW9LGq7VcmjVczrn1FIwq5PvPeejuLhFV767WMOdnWRwQiFDZJEG0q6yMCpdu7Jbt6Gp3KX8vh7dmkOpQbz0ce1pponSqfbld3097Z/nimHVjVxgpxZaaj/ZEsiGihbLddSdcVVrQLUYPmsJn/SEJFzmTLnET7j2Rj3BuV2TBQWA3310OvF5KQ3X567FRUKGfuMSRW4nhYAbdJi5XZnvZDI3xm7H0CpZ6/2yexEr7juHaikc+W8SpHJKw1qu1oIUEynKufXzgh/eDKNSGEEEIIIQOCL9eEEEIIIYQMCMpCyLIo1lGW2v1tQ7Q+QayEJMVsCK2o/s9ITESouLUiaBOqO108uZAqGy4i0lPvay/56MK82ZT+1RLmkIz0atkklOBhrcmOKt3ojpgwvSYwFeZceL+92mkcbOJPXsuwF6dVVqLt8O0Ukbyeo7JbQ6ND5rbrxSWRvY+zCSH78s2p/xUuz5uQs4ajO5U49mwT1fzuKofwIfVg2y2dte7LVqOcOWdZJSKQXSC8bvev7EGD9Pz6MyQtiu+bl3HAv9t4Nlfm0v64eq6hbIIYzgV5hpXItKuaGHmqG8TFTri+w1s1yQmXSiUJNoEQx0TCG3ycmyvNOcbdOUpaNr2ywx2wPW/8pX2J6Pj65NvGs1mlGV1NbKxscgPe6Ya53Wm53xuzbvCra4NE6dz1O0REZKHtvrtrxxkiIrI0H/qM3Kz2qN5bKmEp1EIov1RSKY0m1/bUm7i1ZPRDqeuLuWRlREgeg5THSjW8lCaJt7XSCTxrkMQKL2y7TXkWicDaDp2bJTPf2iobwhxaOMX9verRcP9AYpVJ8DT3T2m+G7W5sSpc346eF6XRO0PZZDgAaQHaY6UjSMrDs9RLJaw0oe462x5Hcnc2gdY/i8vxQ8M+M9BGnyxo5ClI5kN74MffHjFzuoUS73rt9N+CznCYr162N+NuKvyb0Bk2Y4dy8DoOKPk+1OojwcB4mnHt+ecHkqjjZFC7DcZlcV1BtzWe3NrWpARpTpxc6jbKNomQfnDlmhBCCCGEkAHBl2tCCCGEEEIGBGUhZFl01csa4b3CoomhqzShq5IIHxI1Wf/wdcb+kJVACiIi0h3WksZzkHeYjH0tJY7QIbys7TngJNLTn3l1AsmZksReKqLb4H8z22NBzpHO0PdhQyOFycHPVs8POYj1//ZZ/ZCgFEJ4Hf7eCHW3R7JhYJQJ9+WFNZseYV0RkcYKzeaficPk/ZwVMFRwRCjPhaZ2xtUPF97G5n+/057EvT6Wr3DRgDNDCK2GbSARwXHyuZRjitkv7SxifbchI0E7+nkcF/a467v+/CkREXlOJvx3+bYbkNx2bSPkMsZtBOeHTAA/80Z6UlDnjdZq9Vdf1HvESEC8bKGsDgSt2HHF9UPdFlY5G4eCakka9TCXunV1yVEJSWMyaGkeWDjNdV/lHIVZt21loU8sW8e6rSbn3UXzTwHcYLr6U/s6bJxA/DjoT3ilF4NBindfKKoMomPK1fvS4/CVTnkLi4T7rDbpToJrn+SNTAznnYebRMp1R4LECJKPsaejIYh+h0QCUg3r4d7Se6O6R6+zcbwYmo/dJ2q7O5n+QKZQVgkZnoXNVeF5AGkE7jUcz94/kFRgzEI59tAhOHbguYSxjCRtKYkSZDgiIklDf1fpCeZmVKo95ZzRzcO/28jV9N+AzhCkPbAoMk4eaKu2v7kCDiXh2JB6eFepxPYD1wxuHxizsA0cieBrDTkIrreIkbBhvkKqF3nAcz2SHBicKYQQQgghhAwIvlwTQgghhBAyICgLIcvCh+oQUbSygQIyy538oaMSju6QkUggexyyDmSEmzAfQm85lYfkWiEuh1BqQascdIsuht+aMKFVLdIC6UhPy55H8pIy7B80PLjoYt82NBoVtJBUKWMcB+XLVd4B95DEhJN9iXMNhSLb3/YVTgT5tmsHSsmLhMInKCyBn1FYerdKLVopyYipLJGH20c1ljr0TJeHni1E39kwvwdOEZB1NLOboPAJZCrWiQBh1rQTiHUUQTgZ7hwtLX7RNgVreirfQLi/r1xFD7n90XXuzzFTBEMLj6CkeXU6KylIS1/gGhKH6XU8tUBMb0hD2NYJBHKFVNlvMbdGeUavc8u50syPwAnHOEUsojR6Vm6D0LsvSa5dLQbFVXCeQXMms9Kt0Fn3w8t3jAIM4XVcO1yDylxoa1vnKaQ1pUV7/+m8n9N7VV1/2qWsLKutcxl/V2bDcZoq1QgltLV4i5FVhRLgcR/ra8I9WoCjCe41nNO67bRjR5OyKajSWO3aXdb7GI4ZBfM8gUSkuVLlSPo8KM+Z46SKv/jxtGY78WPJy0Fs0RTIWcJ9pHM0b+8x9xNOIF3zzPHFcPDMww/zzGmPQkIWS7fyS+Z5jTLqzdglJGecpHBd8zoHSkt6PCPZ8FI8HTMrb8F3eOZg3lunFjjWtIdTc3LJuKeoDCQtIbFStH7uL4T0gyvXhBBCCCGEDAi+XBNCCCGEEDIgKAshy2LhZBe2HN/i4tHdoRDGRWZ6rqchSQ0pFhomTKjhSoSFIZHojAaLhuJ8S/eHPUU4f2mmHm1faHb1p8lQR3RfHTuKs3DpCGHPxmonI6nsib8rzmZ1EChiU4BbiJGHoP9wjIA8BE4nIiLoRq6lxR9Wj4Tv6jh//P+5UThZw54+QpsKC4vY0DvcBjS0amQHCO830Z6OHtB0uYtmw4HAyCJQKKO0GB+vZFwk4OBRrOvxtDgHwrIWtLW+qpDZpleM5SQI+XZNoZnmah0jLRSTn1PJ0JJxc9FDJpgeS6YgyzqV4JTV3UbPVaiHc3gHkTLapZ9b9xPILjTOnmg4G24bcUOyco70JjhedVJD2NUwNyDNwP62YE51Uk+hXSwtxoV4+uEdYNp9vtTmY26VF408pRW7LUDeZcPm6I+fk8a5pmgkIm5jnScL5lmhcrLqpGtcP6eG2p5u1EZII6zTT0HbVlHZTVsdOKrTVgLmfkAOAseLaOy0jbge1o0CbYQcrLiksjXbZhTMgVxNb+j6mnCT4bx4nqHP1tkkSKzgnqKHt+Orzw8v6+hl7z8vK8NzpWu1JxK1A8Vs7LgunOQ+W/moFtDqVzCnGV/75piO71J2W5wf57DOJIleKl/wxowr5Bxw+cAzp2sKahXVuQauI9hHTJ8hzyku6rNcv2qNhmfG0lquR5IDgzOFEEIIIYSQAcGVa7Isantin9J+STSNVW4lprZbV6DNIkVBd+/UCtE+dnXbl/FFokolTFOsVGNVASvFNmnLl1TXJMck55Y7fal0ERl6rh5ti2RHJCiKBD9deGn3auqfXc0m/uQ6veinPU6+oatYo64d+Wboa2vCLQcjGQiJOh2TBIqVN196XseqWwvnwH5YrUFilV31RGIOVoi9R7BJJGys0MiCHtqOa7GJpCCskmM1NmyT78CLW7/CKrm9vAWcy/1Sm9IksJpJMNMVWazC5pCvahfgtCx3roSDZ/1xu1WMK7LQbCljPdhat/K2NKFJaFNhJbG6O14dDMcNv5fU07ugEQCfYGWfrlixRpSg34oxVjZb8d/VPWYFL5W8ZsfVe/b6lUjsY06Rj+eHT3gz9yhWb7GNT2KzCb09zDe9R7TNeVOyOtdFKW+9N5rZfvjEOUQNTASqNOcGp6lJflgpts8KPEekHK+EtmvZdaPOEPoer3CKiDQm3PbDO/R5Us+W+0aCMxLt7Jxoo5y3HtKv5Jsx88ELHXOsvkZzAFE3JCDiuWA7YleYJUS27Mq1990vY97Fntju9/g4nZEwUVCuXDTJsTqtSeq1sE1tMl5dxzNoaX1ILq9OdaJzhbE3XuU6dOUFhMuyzxXv5a19tEmGWOHG9UAyaGkh7I/6AWoB71eprTc4ju09vfWcuA9EQoI1IfuDK9eEEEIIIYQMCL5cE0IIIYQQMiAY5CDLwocLc/CDDWFChH+rU3ECUmlPyBDrjmgionrV+jC38bKG/AKfdYZDmDHX0RDxInQDSDI0CS4aoq3urms7NNy/ELLIkKTY0/Z0i+4cNqERZdRzHS13XEcbTPKkHifX0PYgGceGG8txyNiGO0vzbqxa49rHajbsWVrQEKZPAlUJi0n48YlPPuSsn9tS7fAYr8dhVJt0VVXZD8qP29K/SOrL+VLeCOWbUsYa2k17WVvpCdoBCQDmkE1ohNdsY4X7uzIjGZA4252HbzCOH7bprNRw+IjO27kwl6Sp0iS9MKMrnQZmsRySaxtS1X7pePRJRPR91KkD2UvJSmF0CvhQdZ+EUSSIQsbhvcJnjRfvUOxxng8Wyf5e8OMAlYiZJ/guiVUU3utYJPg3e8mGhvDtnISUAfvheEUjeYLHeUdlVHmjSYBcCfIJSJ86RoaB8t55n8SGuW2kW0i8QxIp5FF95FBtlYXgGpSNXzaSLjE+3VJ23Sn4Mbtz1FcXM9/BNxlJcCijbvEyCp/AamRi6tudkeIYKQj266T8v60kJ69Jk+0RlC9XqY/x1MZ9j7FHGXIRk4yu17NfMmllxm2PhMzynNt2cUPYduRZtw0SyHH+fDv77waeC42VeryOlf9ArqbX0IyrT+jUocLYWzlHa8R9OTQZP3NsLQN/PeqxdGVpbbjO/RKzCekHV64JIYQQQggZEHy5JoQQQgghZEBQFkKWBaQa3uXDhIHz6lndHUKJWxdCa64JNashg0BJcPzvnZVaeKmHSk9KsyEWj+28HEP/tpIPlEtfOtmdF2E+6xYiPpQKRwR11xgOkoC8+lJ3VrjjFLSsO0qci4gkGrvvrHQlq9tjLqRZ3RpS1fNdDbPD/7toMuVVslLZ4zQF7XF3/tozYf9exR0TspTmapVB2Gx6HeuKhnaR1V9sWzuJWAuQb0LCkS0B3M8vGGF+739ciZ1BRIyDQhJvY2UIcDWAtzhkC9Znt6zuHiPPxe4l/cp056Yl2qZnlB/dPerwMpw1ci7M4fzu5/zCqH5htoFNsH7mr5ydrpjK6qwCh5WuaUdZvcDhmgDpSsm4sUC2gHMN74C+w/r1QkYRXwuRIInwbgd95AII96M8NyRckdOE/g5vY7gvFExIHNKk1ribm5Xdbv5aJ50e/OGb2fsPUhP4QiconW3Lltdij2c4XrRHjXQE87QTO4Asrg3tGN7p7omxp9QBRGUD1p0G91LaVcO6IeHewDytTQYZBeQK2D7f6uf57M4P9xMv7THzHtcX5+9qNwpG/oPjQE6Be93eP5DX1HapRE/He25jmJQj2/Se8CXs7Xgk0Wd+3lpnIG3H0M5YKjH2dOg75gfKjkuupP20Pv56nVUKhrmN+SdiSqvrz9ZotnR9QcezNIV/Y8I2Q7v0GZy6TlbqBOkN5gXaXJ0JbbXtJmRfcOWaEEIIIYSQAcGXa0IIIYQQQgYEZSFkWUDOsU+XD4Sn4RYyF0LyPS1K4EucIyvfhL6R6Q5suDMpuf3TxV/iYg0qkdjjzuGdRfpIClAopgtHEpM93tPbAyXaIR1BG0RC+XO4dJRmW5lt/DHxs09fk6JmuE+pw0kl2EhYGYqISLGh3/UpaRyOm5VapEspo0SzDQcXF1VWYsL7oIUiKwjDNiHfCdsgPO4L1fiiQcb9RJ0ZvHxBy4Tn8lb+oMU8GnERl4IZirQ7B85hS4ujuEldXAGfZMgWOdG2qjSjskflAkHF5I+VLhNu5TLesSMlJbClyb0TiHYRrhIW9BXyEIS5raxDMEbd7LWHm0ZpESXBYzcJ94f7MbRDBw/FRvK2qIeWk045XVgHDV/qWn9CChbNbUi9ME9taXQdo6bOqSrKfZviInAJQXgf3xWsK0aqoAscMHyxKwlhfhQiwth3S6E9GGvfRrTZ3GNw00Df26boCq4rHCpwTjivuG0w31Lzv89tnJbC2GsISR7cLEIBHrM/JA7DsWRkfEvYyLt84PzmPk7P6a4+D6z7UGfU7Z/DM6wQ908kyDDKC3HZ8eKiPZeOh6714Qy+PLuE8Qhz3OqytI06Dq112i/jBuNdcnBsnUO9YriGmO/NCTeXK3PqVmOkSrnO3p+5hFi4ck0IIYQQQsiA4Ms1IYQQQgghA4KyELIsEIqEA0B7PMgXytMuDt7RELEP5ddDaLRQd3H1dDZ6RAI3Cf1ZC9MUBWIQqiulnEVcm1z814fTVfKRb4QwIRw78tqePMKGtniEHtIX0xitRv0TESkuQKfQi/qas1IO9FWdSHItU8hBi9jkmyrRqOixTfSxU1NJA7rYyxbO8SHZBYyvbmqKP8BloDWmDhptvZaLxvVAw7/B0SOMa3keRT00DJxHISFThGZKQ+cYR20HCuGIBLcGhG0ho7DH8RILDTmjKE1zPIRx4SrgFQrdeF8RkW4zdjTpmevbGdbj1HE8/RnqCHlXDyvxsJ+LGMlIN5YolOdN0ZRKHM72Dim2rSUcJ5aHlHtZOZOX/ZjoeLEOSYKG8H2RH+PSodcV8i7IugpLRr4wDKmT7lNBKD9sA9kQ5qR3/TD3oS8WBFcLU3CqoPdiZTp2OCmYexRSBBzHPw/McBTUgQTnRQEe62xi5QXuZNmxQ7gffcZcjCQO2sfiQuw84Q6g2+RjSQ/mukiQHaCvuI+6RgqD/dPuHD0jYcH2kJw0V7hrad0xMEZeoqdtxb1vSTD2Vgak+/tCNbgfjSQHz5ZeNX7eo5iMSBjXvI55D88TM3Sd1HUOxaDMdfP7ZecAJGSQgOU7sVzG0hpTBxzMJfPIwfzE/dIcU7eQPfZhnDkkIX3hyjUhhBBCCCEDgi/XhBBCCCGEDAjKQsjygFkBQmgNk5U/jAIBLnbWmtDwspEvBMcKOEVo2N84hMDdA5KJnC1Uo6FZbN8ZcedAUQsRkeKiSj0QYkZI0TqKoBiNupfANSRyHenCrQBVQhC6zsoovFTCy1yCXCZJhzTL4bZDX31RHIS5TRY7JCMo9tD1fQ7tiIrwiEhXpTRRaFVDs74QSR2Fc0J7ghOCa0+nGsZjaLcW3EmFeH1BEwkh+I46MyDEakPWKNwAOQbGBy4XbvvYnQCSC+tg4UPocHSoZ+UlOXU0KapJQnPMOERABgIDBT1M0UgKIDPAONSmtD+mQAzan5YvQAri+hZfH4xT7HKD9iTR/tahAE4ZOJeVuWDuFNqYb+oqUc3KbZbWuzk0sjU9b42DjY5vAssX45zh5Qb69+IGNyDD24N+BvcJnETyqTlqgaSlWwnz3ks1IKNISTdERFrjsUNRP0mBvx467xbXuwOMbgv3T2OVOkTAYQIGP9YJR5uGZ5i9Lmn5Br6zrjBe/pGL97HP0N5o7NLjXUfmQlsxd3A83M+2GA3ajfHBfVio27mk96HKKjp93E/gxtJcWdR2dDPbYE7CqcUW5/FyNe0j7l/rtIJr1ky5EUUFa3ROQipl71HMby/JaWD+hv1xPoxVc9x9WZk1zjMoLKPXsFjPuiE1J8JznZB9wZVrQgghhBBCBgRXrsmyQPKIT2ys20Q1rFQju8f9sAmAWLVB4pL3yTarLq01KDeuK1/VsD9WS4vYDxbWZlUNyWZY4fXlhs1KU3W7Wzb1K8T9PKNzWNnpRMezICETq+RYeSuaVbrmSpcIWXvOlTTvmZVrrBhidT+9Sh01B6XMtc43fGZFzKqNrvLDR9yu1iNa4FcdddWzZ8ui6zZDugJpk62wuhhW9LPet4KkNf0oXULbHdstFaNUvFaFl7ZZQcdKbwnXTBO8mqtDn4cmtZw1fIx9oprx9i5iXNxnNZOc1Dbe2yIipaVsohvmcHku9vK1q2qwL0fCp08GMyvGWPkOK6t9VqV90pj6qefj9omE8cTqnPWFxuPcr+Rld/fRgYop6Rx1QkQWT3bzFau4PoHPRKByKc/2ymzqeBKiSojq1NeG5f7qZDvqI+4bmzCHfvhS4OU4QuA+05+pVVxEXkTCdUHJbEQfOiay4BMXUWYbvsoVGxmI/fvtymgeftS4fdFWk4zqkwJTiY02UTTXixNFg5e8SWis4VnRi9qTs9E/RDjwEVbLzb3RRWRD+9gtZ/ua6C2J62vntI9w6LHxb4NNJMxErspIJAzb6OPMXyf41ZspKaX5OJpio1y4x3N4jugqtfVDl9TjHc+OKKGxErcN0QLb1jx9rskBwpVrQgghhBBCBgRfrgkhhBBCCBkQlIWQZYGwYle9dK2HLMKBPfUZ9aV7TRg3347Dx76cugm9+RAoEswWTZJUM5Xwo6FnlA0XEemMukRIhPAr0y4EbSUsXi6RxGG+qMywhknbq1zsGeWPrV+2L6tbikPY9rgl9Z7ujLl2FeZDf5IqEg817Kll0/NLZhuVkSSVuO9WzlHZ04i/U8lG13iEL2lZ4ImHZ90H8P82Jezxe2fUfVeeCeWSgwe3JmtpqXcksopkkx3LKnMpGh9lbA9JRAGhViNjCGFxhNDd+I48Z/3DdRskPWoYuJOziVmpxDJzuYt1lSTA57dPyXhcT4SMESq2CVnlRjezn0j8cPWha22G9ziumePMtnXblOwgb8PscbIX5qRI8IAvQoIDn2or+1FKc+5cSDouz4RxHX3K3UvNlW4OdCvZNRhcT8hUkPjWMf1pDyP5WK+z8dv2Pur4if7ZhNWC+h/DKxml5804Q8oDj3DMP1sKHH7FkB9ASpJv23HR9g/HsoyiSTaExzqugZ2vaHcrlZRnfea9lzfGSqUSCyeH+wf9KWs/IDexia94rkJal5p20faQtfjk0D5SIYxZ0UgtvIxED97PHxvjAClaexTe6dkG+fsGsiabBN2EbAgJ8ShNnpWr4TObNBkSGFUysgD/fJNsDxkjkkFLceK2iEhtN2Qgekq/u+lPVv1ESF+4ck0IIYQQQsiA4Ms1IYQQQgghA4KyELIs4LxhfaUBQpENeKIuIIM+KwsJLhlIyzcHgtuCSj5seBDZ2ghFIqTZXlENu2MbbWNrhcofjF+2975Nle61oWt4R1emnPwB0o2ekVrA5QCevgil14zUIpeSPfSGjOuIl8DEntol6wmM31XugD6XZ4x0RF1Pcnre9kjsOS4iMv54XMO7sOBi553xMHadUvz/214KIsHJBJIR34U+7hxesmEz9nEODelWdVwxp5JI/uD2a6wq6bbQBITjNFZqHyGV6GXPme9k3Qn8/itcO+DfjTC73bY5Hj8ivROBkQt4Z4VSHIK30WSEweHoAKlEvputp5yRg9jxhUc4ZAdFGx7HvRVfg9J8kHy0xlXipPeCl4OYPqMMNErWt8ZVxmPakTTdeeHa4EuVm3t9aEdL2+y2bU6YudRG++HmghLpWWchuGPguvTMJoWUBKG+GnI1s42eqzKDcuNZxxfv4qKe3vjObuPvX719K3NGdpAql96vPD1kIAW9MHDXGDIuH5DgYD9cC2wrEq5zQ+VqmIsd45Fdns+6MInEnufwnMY5+0n8MJcqWmrdPotxLEicct5rPCsLaalkxJeJN7I5OM9Up/QcmOOmPV4G4t2mrHxIpSJ6XfMo9V4K41FItbEAlZjx/a6v1mfvIq6h3k/WS55uIeQA4co1IYQQQgghA4Iv14QQQgghhAyIY0IWsri4KF/+8pflvvvuk/vuu08eeughabVacv3118tHPvKRfe67detWue666+S2226TPXv2yGmnnSa/8Au/IB/84AelWq3uc1+SBZngKLVrM7KRMV+ZjrPHk7IJJXZRjjcuM2wdK3opV4zmhCk+oc4fPhs+VVpcRKQ865wzfElxlEo3rhY4H35COoJQuGu/SmDgDlKOC8aIiJRSUonybLbwDSQjPTiBWMlIQ51EVNbi3TbKxvECpcxRhVrHp7QUHEK6KjVBIQVfTrpqQqOQiGDM2lk3l0Jdy7HDocQUDoH0xBej0X5YwUVOnWKC64JeJzMeCHHX17gxq+5RlwwTfoWEAOMJ2Ywt013bZSwhzHdJMZzLF5ZBaWNTOGRkW1zIJL2PiHUeQOGduBCPSJA9LK5zfR7Z6o5bNCXPMR6QX/S8u4U9sW6CIj0FtNk4TqRdR4yMKe0K0tSS3jUTgg+l4V0DIHOx5bVxbzVxT8wjPG4cffLx/eedK4w7BuQ+KDVdXjAFfEZi1wjID2y4H44OKP6Cwje2MAsKy6THpVi3Eoe4Xzhn5EYh8dhBipOYRxHuk+oefb4NG4kF3Ggge9BzQaYiIlKdRhGoWBaC56RImG8ox16dxPwP7fD9aNrJkypNrk3zZeG7OKeZLyiAlc86iXh3EYwrjmOlW5CjwAFE2wNHEJEgq0Ff8be95+BEgn8/CqkiOyLhevY6cPkI50Cfiqn98kZx1Rpz28MRBM5RvWJWood7BGMXObVQFkIOkGPi5frxxx+Xa665Ztn7PfHEE3LJJZfI5OSkvPjFL5bLL79c7r//frnhhhvk9ttvl9tvv10qlcphaDEhhBBCCDkROSZkIaOjo/Lud79bbrzxRnnggQfkhhtuOKD93vnOd8rk5KRce+218vDDD8sXvvAFeeyxx+Sqq66Su+++W/7kT/7kMLecEEIIIYScSBwTK9ebNm2Sv/7rv/Z/f/Ob39zvPvfdd5/cfffdsnbtWvlv/+2/+c+LxaL81V/9lXzta1+Tv/iLv5APfehDUiweE8PwvACh4fxitrgBwtkI7/swX8MUuhiKi8bk+0g2ENKE04V3ihAjQ9FQd17Pb0OaKKAC+URZi53U1wUZUG0+ds5AeB2OGCIiZXUHQcY9jtseM0UfVEbiC5ho/8rTpqgLIsap8XEHUMkL5CDa5sSErLFfV/cralGapVOG/TYolGPlMSKhWIiISL6hkg+Vp0D6Yfvc1cIyuB628I53hEg5KeSM20Gu47bP+Vg8dD8mhD4fF5ZprI6L/oiIVGbgHOD2Q8A737Xhfm0PXFx0fGyfvbuNOg9Ud4XrDjcaXDu4A1hZEkLeFXXVQKjZjktjpZtXY0+7Y/uwuLGayKdcU+BeYOcC5B8oOgTJhZWp+NC/Xudun2IauKeGtrcy+9d2u8/mT3NtHtmm0hqzTVvdQSDX8fO3YRwevCxMx2BVLIsSEWmugGsQ3DrCdUGxmbT8YPZ040Sjp6vOoAHa50pKwiFhXkAW0lhp5lsDbU1Je6yjCIoVaTsg+bDyEriDQJJgnznFRixzQ/8gQ7Dnx/MNchAr75g/xY398Ha9j7yMIpwLY592qekY+R2cP5bWu3NAUlOaD8fx91YlK8nxUg8UAkvisRMJ0rNEtWg4nr2PcX0xFyDdSD+nbF+9o4nZpI17Q/cvLcb3kz2X78NQGLTyPCQrKhXEs9jIfkrqboXr4V1UzDMnOSaWI8nzgeN2qnz9618XEZE3vvGNGenHunXr5PLLL5fp6Wm56667jkbzCCGEEELIcchx+3L9/e9/X0RELrzwwr7f4/Mf/OAHR6xNhBBCCCHk+Oa41UM888wzIiJyyimn9P0enz/99NNHrE3HA6G4gTpYmJCZdTUQCaFwG2aHq4AvPKDhxuJiiNF6p4wcsuJNwZokDv0hZF3o2Ez5OMMdjhW1nUGq0bGFXCR2Qgj9KURtg0tIyYYffWELdTTYteiOV7AZ8xrGbULqYL5DOB5hV/2uYIq/dHWsEe4vLLrQfs3IMRAaxv5w8rDyku5Yzf2i5ywsaZGPqi3coUUjdi/p/qaAAsK2Oi4IA9sIbw7tSElYxIwZjgmZCSQtkWNMan9IOLpGRhGy+dHnWDLkPkNxHpUqNWx/so43IrHrBqQMkL50h91YtVeHaFh5thvvh3lbN7oDpaMONAlkFbawkbrCeGmQzi24dYiEMUdfIb1yH8bFY3A/2iIYkDgN7WxH21rpCI6JAjqQotiwO2QPaawkYFglJyiEkpiJ4qUZOJ5en5Htxq1Hw/pwBEG43h6ngAJCKRcKyABEYvmH64f+NH3GOSAbgIzI9gdXoa6Sk9Fnw4F9m3RYIBPpVvqMk25b1AI8PeOwUtsTF7HB/YttRcJcTEZUVoICM6ZADI5Z26USLJVw2OvmC3I14jG05/MFWobjYlsiRloxgnsrllWIiLRHMF+TaBs7JyHFaU7ABUnvNTMukK546deSmYvV2AUmOKNki4aVUHwJ94aVsKAgmUpivIzIbtOnGBUh/ThuX64XFhZERGRoaKjv98PDTq86Pz/f9/s05557bt/PN2/eLJs2bTqIFhJCCCGEkOONI/JyfdVVV8kPf/jDZe1z8803y0UXXXSYWkQOlqKWUsZKhl0d8Il31biEr12dg/+zT4bzK6xmRVET1LAK1RmxvsXajiUkxcUrmyJhFQkr3lglyS9lVxKxalnZHXtRu766lTck+fl9zAorknlK6q0dkozC9jldxcIKsV0xy7XcebH6Wt5T1/3Nav+ibqMrPIsvGHXbmuSx0h630twddYlqdnUc4LpUts+5bUbUW7ttrmE+lShkl6WxIowFWqxkmtWcpJdaDUYUoWuPm0rMPMmtqNu5hIQsJNdVJvVamPLYPjKC1dx2NsnJl39vaOKrWTHDPEmvStvy6Vg969XURxy+vWbFGPPMznMRkcWTw+o2vJF9NAVjZtpTmnORhNbKih4v2x8k0S2td+2xCXPp+w99t9WoffnnZrwy2R4Pc7w87dqBa4ioTNveh504SdB/bqIG7TEkzMaJliIihVY+6g/8pLslu5LofmIlE6uW1iPZR4VSCY3W4xhJayir7b31TYImVtLtirc7YPgViW0V3cbexyFJUuetJiuWrH+4tjtJJaraqF2+5Rrrk/q8T7vxp9Y5iXmK48XXohe12UcPbKI0rof6httV6ZZGLYq60ozrYsce/wagH1hdTvvGu/PrHNLIQHWmm9mmMt2J9i+ZRGvMFx9pMX0tw+4etQ/QRxuwKcdtwjYl4/sd/MfjMbN+6P1KuxPSjyPycr1lyxZ57LHHlrXP0tLSIZ1zZGRkn8dZXHTh+9HR0QM63iOPPNL3872taBNCCCGEkBOPI/Jy/dBDDx2J00Scdtpp8uCDD8rWrVv7fo/PN27ceCSbRQghhBBCjmOOW831S17yEvnHf/xH+d73vtf3e3x+/vnnH8lmHfN4r+NUYqNICI0iOWn4OSeVsGE1X3ZcfYK7KuewiZH4HaHq4qKN8cZe0W31140lBXFZb4Qve0Z64kOrCOX7JEibBKPJhdrWUMrblCbHMXOp0KqRU/hwvSZRFhZMIhQ8p7W0eLcEf+mst3dPUGY4G5psrXU5BKVpyFP0eCahCt7bkINAopM3Jc4XT3bfVSezEpp0Mp1PBrKR1Wocsk5LfERE8lryHX0fftZFkeyYzW1y/UGYvaT9sNILLxFC0qOOb9InjItrhzLIIiIVldU0NTnRJ0LVTcha9yvPtKK/rUQCXtrlOZ0fmiwFX2QRkU4Nvsmxn3JUjhpSHiSKoSS4kVp4P+VptC801fvyotR7FV7F5t5AOB33US27TUt93DOls8244Do0V7r7z5dsN0loRS3ljecCpAYWJLohKVSiEu56/1ZiT/yeKX3tExBV4oFEROtfnPa1hgV7xyQAZtrlk/1M0nARc6Gb6Q/KlmNryCjy5lnRqcXnw5i3JoIkBx7tBc29juVU2n7c06nHgJUsICERcwDPt9JsNnEcz6yeSUhHUqIvW15FUqo5qZeDxEmguO6uHypl2+DGqjaVlYMEaVAs27HPDLQD93HXJm/qWCPxEBIj61GOZwXkITi29e3u6eWsacl5zOnWaDhXc+K4NVgjA+a4nSlveMMbRETkq1/9qjSbzei7nTt3yp133ikrVqyQSy+99Gg0jxBCCCGEHIccty/XF110kVx66aWya9cu+cAHPuA/73Q68pu/+ZvSbrfl2muvlVKptI+jEEIIIYQQcuDkkiRtHPz85KqrrpLt27eLiMhzzz0nzz77rJx88sner3rDhg1yyy23RPs8/vjjcskll8jU1JScd955cs4558h3v/tdefLJJ+WVr3yl3HHHHZnqjcsFCY17S3g83njN6z4mIiGUF4USNeQNGQMkCbZUtHcM2NesQ3SwGJfVFTEerwWUsYW3qnEkUb9g+FIj0946TfgMd90WbSyYsuiJyiZ8KFLlJaWZEAlBKLO1wskpKjtU4mAkKCgl7sO2Rv6A0uO5lNey3Sbx4c74/4Uj5wztf3HaJfA2ThmPzykipVk4bpSiftmxw3g21mh/pkJfvf8yXDYguTDhW5S6944IkDgYeYr/Tq+l96fO2xBtfA6Mh5UPBfeS2JHE+iC3VsSyIVtuHOHw1ljsjBBJAXQblLnH37YdLZUvIZSO+W89hYMMSbfxbh1mnqjcoaze2v7+aRhZlPbNHzvyfI69lRHytv3xbjbFODweSwria9hWmYh1k/B+xXDAKCI0b5qKStcYK+si4eVdsYtDztwGkAThOsO9oTmeLWvtpQHpeSOh/HnaxSKaS0q3Go9LyUgcvMMR2tjHOQJlvr2vcztsg/Gr7IHDkbptGBcVf+yUI48dJ+9Yo9cJEiXrL43+t9RtJz3OIuF5jePljUsOtvdSjTzmknnOwr0FEhic38zJxkp3zeCW04/g9Y/+9ble8G5XaU1rNEy01ojKdRZUQqbXDJIh910v2q+yR510zL9f6ecQ5rKVOkHududXfnev/TnWOdHeaQ4Xx4zm+sEHH8wUfNm2bZts27ZNRPonJp511lny4IMPyoc//GG59dZb5ZZbbpHTTjtNrrvuOvmDP/iDQ36xJoQQQgghxHLMvFw/9dRTB7XfqaeeKjfddNNgG0MIIYQQQkgfjpmXa/L8wBePQNly4yAAqYh3FPEFVUwo3pdmjkPXCLtbvBzCOm/oT++goSG7pJWSVUiQcSCcbMPjkEj4c0GCYgrGQLKRVFQ2oJKR5uqa3waFOhAu7ag8xLpapAu6REUjNOSPQjXeSaNo5Qv56DvJo0iPCTnrGNVPdXIQX7rXOrUsap+hzNHrYuUlRQ2f4rra8sA+i1+vWa6FeHLYpLG2Gp0/LTGw54eLS7ntxtU6tXTG3HFi9wiR6vbFcJgqnGZSZc/7uAz4Lpi2wg2gOqXl13VOLa0LEa3Rx13BHVxX6SOF8fIYSCNwffqUk05LpqzbR2leJUIocy9ZvPtDDoVDsgVvfHESDftj/ttzCEqA57MlnrsqOeml5TvWFQaSE73vulpMqW0cNHxp8m6fuZgqQhPcLcwF0uvZHomfFbZADK4D+oqwf7Fh7w3tsko+UMDEukC0hmOHF7S5vtq47cwlcZ/NuHoJjJcxoX2hreUZ1/B0cZK8uYFQMKo5Ecs5ajutFE2lESlXl27VtkfHF247fZ6vkEFAVtJYFfKP/PVBcZ52dp7g3vTuIOiGeS5VZrTNuPbdbPGh4LCku6uLkJWpQA6Cf39Ki+Y7FAnT5xGeNXYOdOBo0oRMrc8ztBi7XUEmVraFgFLPI0L2xnGb0EgIIYQQQsiRhi/XhBBCCCGEDAjKQsiyyKWKuNgZhJAusta9y4GVdSDEjCT0NooCZIPg3snAZvXDuQNhPpVjWEcRFIvxxTymWnq8cJheBU4g2o5m1k2iW9PiIgiR9lBYwjgIaFg+QZETtKeS7Y+Xg5jxaK5FsRQNa6vzRGU6hIHzLUgr3DHbE65dRVOMpqPFeCp7GtpXhD1N+HR8SNuMMYvdP1yfi/GxrZlQDu4ecIjQsTIRZ4SfcQ0Qco5qT+jQVHe5PmKsOkNBklPWYhdeoqDHiyQ5Kl1pj7j9MP9Ki/b6pApd9HFUgPNGruf6NWRC8M317vp4xxvIMVpGDlWKQ9aYizkT+vYuKsV89LedJziHl4zAtaBowv04pt539tr1vV8kuEK4dsdFbET7nDMyl/pqN5dqu9p6PJVB9LlHfUhez1mZNs5A2talte54USi/Ert6dCvZdR6MY6+MAk/aHxPKz6f6inNYdwxII8rzWvhmLHuuQiuWUQTZgnGT6MTnss4mi+vddqNb3TkaK9zfQ7ut/Yn74SVXrayrDKRXVX1mBWlMVrIBWUZTZTNFM7d9UR2dU7jXu6aQTcG747j2VExTvRRHz1HAd5HUKXYr8Q4nVqEHaSCmm96jeePC0hnW+19lO5WZ7DMdso6SPs+sEwjOh3HxshAjCcvhWDqe6aIyIuH+Kc+hYI1ExxMxDjaE7AeuXBNCCCGEEDIg+HJNCCGEEELIgKAshCwLK5tIAyeCthbl6JW1gIfJVE80PIcQHkKCNtzoQ+4IVUfKBA3bakjVF2Aw7UIRAnzXGYrDliJG6uFdRyANCCfroThJLuV6Yo7THitH7YE8w7oetEc0ZDzn5AaQbFgKdReCL6h0BNIPEZESCttoiBXFQqykwBfnQUgWphLGtQTfQSrixzkal7hIj838R5gW54JUwzpWiB4y0Sh2vwIitR11t6kW6cGYl6dDAR84vWBc4dTSHjPe9EnsaOBrUdgiFmtj14WhneEcBZ2XOZU7oF/efUREcil5D+Z/YpwvII0o9OLCKr1q2KYzrFKeOgobZV1HvKxD+4GQPEL0IiLlechusi47uQSuCShUozKToSAp6NZS0g7tKkL8IiK1Xiwp8LIXc5kLrdiFpbHK3QflWVvwRo83CUlM1mmhuKRzqY8sBOF4FPzwTe6zrZcNQBKUs88D3a8IhxM9vnXyUMkItoWTSMG6jkBZ4OU6Yf/apMoVhvS6LGYdUsTfP7GLinUxgpNIp4b+6LU08hfc/+1RyKnifokYydOoXnt/TU2BpEIsybPnqEy3o+/qa1xnq1PhWjRXuGPD6SVdpMe2I6cqszCuWRci2367rYhITi9ruxbLO0REKrOQAumxIX0yspK0e1J7OFUkR4IcBJIlK98DvXLmI0L6wpVrQgghhBBCBgRXrsmyaI1p8oyuOBVtOVysHmF1rZRdZcBqa7eWi76zyUIhMUU36bcigiQrrHA2u5lt8j6ZJlu6N83iSW5JYmyz8VEuxyuB/ajsctvDcxmrhZaSrrZiBdGW0y3vcavZ7RW6sqkriNYLGyu86CNWnHON7Ll6tbjUemLLjmtiXLfstkEiUsesstd2Y/lI+2zKc/vV7FZcct6uEGEVqjzjjoPrbVeDO+rpjQhDcwx+5OE4I0/X9ZzxKlLJlqfXeYHx9PPOeIRjJdWvyvW5lBjznI5r5Put12Fpg/O5hid2P4/x5ko3rsNbXQl6XDfb1ny7G32XN6Wv037oiLxUJ2NPdpGw8m2TF33yGSI2o3FURSSUw/b+0vPt6HMRUyoeK5rpJEgJSZbNFe7nkCY/2uQ87OdXiE1bi6nkM594auaiL6WeWm1P7ONAf0cyn/e9z2U2kaJ6HHe1q3beF3SI4XcNL21bah0e2Pk+JcnTiZD4266MYuW+Bc9mv2IbxqUL//A2km3dtjYigLmE1eVC3Y1PySQ4Y17gmeGjROZZjPsGq/P2uVRsx8+WkWfdAEVe2Po4RTTEj4u5XHltElbnK3M6BuNhI/hRF3QFHPdWacEmwMb/lrRMNKdYj+8Fn6Ru/k3B3A3RB4mOZz/Dcwi+2VFCfp+S94T0gyvXhBBCCCGEDAi+XBNCCCGEEDIgKAshy6K0EEsrbPKYL5WrCW45lOQ25aQrWgLYh/AQFu7Z8Hg++i46h0+eiz19+/lK59M+sjYEWIz/v3L0qXpm/+DxGic0xr60KnFASFT9s60kAJ7GPrmna/b3fdQ2N2NfWhGR4nycCIm2JyZRLSQnqdwA18AkGyIhrZfqe8F4t0K+4eUctkwxQqv6E57YkZ+ztr+1yl3zwhKSnUx/FrXcuUokcl23bWne+NoOa7KUhroxHlaC4pNZNUyO61KaD+FxX0q5k0puFZFuNyV7qMbhbbe/+hVvd/7hkIx07PXRPlZ3N3U8VDZTD+3wSay+xHMu/lxEyrNuXJoqEapMqme5Tdb1ntO57HhA+QKf7W42hI0EyNaolp7XvsJXXMT6bOvfOq4FI2GBF3Y+7KZ9NyWnNTkPkoBeOSuj8PNWw/4+mUyC9MxLnCABsWWtISVC3qxPXLNSpV60P7ZBGXSRIGUoqxShqfK30pKRq7XhOZ1NdsQcwLVCf/J9ZDt4hrbGkdAbmooy7pAowF86F/nNo19xf6Lk2EI83+BvnTcSFJ9U20dGgXs7n0oOtBIWL4VJl4PvI6NA4jrmaGnJPO9TzxUkP9r5i7bheCPbTSKvbgfJYmUaCZ9G3qXXxyeKLsXHEwnjB7/tah3jap5vrew9RUg/uHJNCCGEEELIgODLNSGEEEIIIQOCshCyLKznrkgsKSguoIS4+q9qKLA6GWLHCM97T99G/LeIcRlISR3ch+4HwuNpeYeIkQvgb/gfR2HT2KUAMoSCcR1BiLeX8ua2YfrFU5yLxNBzajeA8tjtcJy2es1WJp30pGCkGnB08OHkoT6uIxoSRl8RIrahb+/b3ca4xCWj3fYqJVBJAjyXu6Y/KLMML2HrBYwwvW+Hl7mYEK8eCw4ckPTkIkmOSjwq8EPPZ/qDNvZKKrvRU9iyx/AAhvft8HMNPYEJxQ/HbbXzt7iU8nGGxMhKLTrxXCromPVzHfFOOH0ix5njwHHF+EtjrHDf5Dsql5kJbiG5lLuO9VpGHzEnIXWKfLvh5a3ngATEznssuUBmU+zT55re07hmXrpl3DEgB0lKsauLSFw+XiSE7QtNIynwvuUS9dmG8nEOSALghwzvZxGRoZ2x/MHLZ0rZ54FWg/d+zpFsoBR7T1s5h39WqfQF5c8rs+b5qG4YmIOdWryPSLDrhzzGe3zbOQUff/2sOeEmQaluS5vH97b3tzYuKpCIeJmX8Q8Pcr147CCJEREpz8Z+29573ZS5z3tnIXUkgdzMPg/Ukxz3dr/y5xgjHMdeu5aeH24ujVXFTDusa4uImZvGAQfPOjjFwLkFHuh2G0L2B6cKIYQQQgghA4Iv14QQQgghhAwIykLIsvDSAEgLlkzIzEsRtECFhkELptgJ5BchExzyAxOe068QQoyKNeihvCtBLnYoscfy0grIKsw5EB5HVrxvn3GTKKl7g/9MC1WUp0KYvjzlfkIS0EsVZnC/a6a6FpOxBW8QVvfyFDgz2DCm1hJHKD0ROE2EbZrqyGLLYYuE4iciItU9Ks/x4XbEyc2p4Ggwp6WzTajYyyjgopL6WyRIgtLSE5v539HCPwjfluc1dGzmEuLQkEhgLllHA2T+Q2KBQiiVPeH6oIR3KEwRzoHtqztip5i8CVm3xp0spYRCM5BVGLkArifmOWRMduwqkzqXdA746z0SHF9QIAfFcBBuz3VDzWWE0+GEYEvG5/V6jG3GdY4dbETC/EQBEvw9d0YttFXD8gjTe1mIwcsNdDzghNE192pJ7xdfGMUUs4E0ArIy/8ww5/IyEj023EeKjazsAKWrvYRr3lzDsXi/bhHPrnCcQhPOQpCCZSUO3QIkOe7vSFbiCxl1o2PbwkiQWsERJEifzHNJ75Pabr23UGrdSLcg4cHzEQ5MCyeHuTQ0qW3WY9fHtBjNnBm7jtWaxGOPZ4OX8enftd1B4re01p0vOG9gZ+u2A1lYLMuICoOlnkOQeVjJIZ5ZGIde6Kovfw5wzSIpiP6K+x/Fiqy0BzIdFKWB5CoqSNRP80VIH7hyTQghhBBCyIDgyzUhhBBCCCEDgrIQsiwQTkN4rWBCibmO/p5LhQALJqQJiYhu01jtQt6VPbbghoYkVQaRb8fHEwkFP0K40LhAaOEROG8gfGrDez7M34tdNrqmGA1C1aU5dzzIXpprTFGcyWbc1lY2hO6PrZIYm/nv3R80LJ1XCUmUxV5AqFrDpVqcpFsLcgHvHqGhUBSvsMUaIGnIpxw8EKZ2B4gdGazriS9eg3ArjmN2x/a9UjE6p3VYgUwm39bHD4pATITHUWWqFR0b4WnsKxLkOkUcT8PlVmoB6QqKv0DqIyLSVXlKcD+BvCSMKwq7QPaDAi8l4yCAgjnFBRRIcsfB3BAR6YzqnNFrD1kH5C4i4fqmi6/YJZCOzvPyjJsDrRWhrXDrQTEPOBtY6RbGo4kiP3qO4W1hXDD3UCQE93i3T6GmphZCgSzDziV/L2RvXy+b8LKBXjbcjvN3IUNqZi1asF/Pu2JknSZwHJwLzhlWsoH7B+MBJ472SJiTkKCEwiqFzP54PnaqKPhk+qPuHDgriuHkFvvJU+IiTjkzPJCS+eJUkJLsMS5Ga3UO6WWtamEV+wz0hXzgUGLuUVwz7/Khc8peJxTc8c+zQvZ5gPFIy26ia6nPocp0XECnOWGe6Y1Y2gfpht0+LXPJ2+eatq01BieR7DyBnARyJD8+5lncHM3eA4T0gyvXhBBCCCGEDAi+XBNCCCGEEDIgKAshy8Kb76PQxHCYQrkOil+kCsPYggEFFOxw29R2aOEPIyXpIiSqUeXEfqcZ9/lU1jbCfSKhmAHChAjj2sIF7TF1LemguIg6PJiCDoVmLD1BGLY0ayQscElQ15Hy5JL7vBzag0IxxaW2njuE8ktzraiPvphM1YRE5/V8Op44HvYVCSHqri/+kov3lTD2XmKh8hkr2UgX1+kO7z0sni7M4D6MnQMwLggr2/07VW1jw/2s7jbFUlIFQ/xcMi4DJW0/wuKh6FD2XPgZ9QeuLXrMxZOGRESkMh0cV9JuIZAzFBfD2GOepOUynREr2dDrnCrAYwvn+IIuKWlCY0WQuYw8teiOo9fbuoXgvL02il9AHhX6jDZW1PHGO5tUrStMHDLHPZ43xZngHINrZ+UT5mTuRymWSoiIVGYwL2MJinXOgFMM7j8rb/FdRuEfhO4hQzCOIpg7Ce7tHI5nJFO4HphDley6E+QB3hXJqqlQoEmb7J1JzPMkj1o8ZRRaip0r7Hfp8eiZew3PXi/R0IlSngn3Otq2+yXuulR+IJl+5RI4gbi/y3PZgkaYnyhqA/mP20iPWUsVYSpmnws4L66LleRASoRzwC2kG9R3vj/+Hq9kHVawTVOdUeBiImIkI7obJCcV454CCRva2B6O5VUiRgpDyH7gyjUhhBBCCCEDgivXZFkgEaWliUw2iaTYSyU+YeE6l90fq4vwbLWroNYH2m1kVzni5DW/ktknSRArEc2VSJoMq3z4buYsXZlccPsM7QqrN1gRQWJWv1LROU3gw6pJ/eSRzLkAEu2Q1OOOjaQ67Ycep2jLYqM8dydehbWr/RgP/MSKceTH3HbH9F7juk2UhKmbd0ZRhj27WohEQr/KaMYevsfwMcaqj72+Ne3byDZdPS1nPWfT/uOIdBTnzWp9KV4ZDdfL+inHntORJ3fR9XFou2sHEppskhNWaDGHcI7iYtimrh7jte0uCoNkW1vuOyTeue9Kc5oIa1aumys1MRLJtjqutj9Lp+rquiYA21V6n8BYR1Ks+wBJhyIilWn3s9BDQrLOs3zYBhGaTs21B/7MlT3WB1l/6cX+1NYHGGOdX9Lk1LaNcul+bZwfibh+k0y5cB/VsdElHRvvX6xRLxvZ6ul9UmzC4F1Paca1l/LU9n0wy0/eux6LoObZl8Pu3fi7XDG7wppeFe/nI55PebfbxHGf6OmTurPJoJhDKx5DJEv3NW2GBzbGPPJw9mXY4Y/tjmcjLfAPhx91cxyrwaGt8ErPI/imXuGV2fB8S0c9UHreRy7EzIXRrNe5L80+HD9H7L87iCggwdt/12e++ucRLreJlpX7PNcJ6QdXrgkhhBBCCBkQfLkmhBBCCCFkQFAWQpZFc0UsCbDhVyQVImQNSUHb+AYjlIkknm5D43X5bBIMkmqsDANh36SL5CI9jpFa+NLd1dib1SZfljUpceWjsZ+z9Q1G6BCJgEhK61VDghm+87KBTjZEmy6LXZ008pQuYphuv8VTXNi/WM/69BYhe9Cy7kkxhE0R1kZ7EOLEOLmTaXh8IZUgOWR8oXWsfUKjkR34ksHwFi+irLUJwff0Mw3bNldAShO2WVrvxgqllL2XddNKclReMorrAd9gK6nR8HGlErXVJnFCooGy8K2J0Nfhp13Z8+ZqVyK+umtJ+27kAjW3fU1LpEMGhDLmIkamgJxLSJ2MbAehZcgwkIBqZSpoo0/AkySzDZJAkc8F2YqISHHatb83XInOYb2nvUwIMhXvAW+ShnWeQq7QQ8Jon3vUl+XGEJjnAaRX4u/jrLexT8TF3LL3D+YwfK71Piou9vHERlKbTxIM8xZJn+mEVyv/gcTBy36acVl2ESNxKmblKZClpOUl+FzEPDO9d7WOay47rvC59vdYI3yHfoTkT3g/m3NpG9vDSG7VeWPqCTRXxJKTqMx3Su6T+GeFuf9wOh0iSC5mXxCesxNPuPPteaE71/AueKdn5TJ4zqWvhUiQg2A8I3lLFYnacdvtfAsSD/0bHtYmgdbXGsB+mH/28vS5VoT0gyvXhBBCCCGEDAi+XBNCCCGEEDIgKAshy6Jqwooiccjal89FuBOZ8iabHRIAyDJ8CeF+JZIX2pnPgqdx7KBhPV7zcEDQ2sOQqxTrIYQOGQfagXZZf9x0aWURdfsYzt423i1Bw5Ud4y0Mf2CMR1dCyBoOBD31xa7thu91ODaO5aUeBT22GVeE972H9EgcVhYJXs2Qg0BiY10t8kYSIRKHVuHM0PXnQqw1tAMZ/vAQrkzDxSGcozyDUvGxX3ZrZTWcy5dIh7TA/YCEQyTIP7yTCMoXm+uDct9BEmMcL/S6Yly6w25OWLkA5ltpT133ycooRrc47+leRR1aOlkv7PR8hfe09RiHUwz6A/lCy7h9DO1yfS6q24gNU/eGXPsRwu9Xrtz7hnuv5lii4P5wP5bWqcuO8f1O4+dXnxB6urx25EaRg7+1egv3caVB/8ud2BM8L2FOLpzs2ghJAJwmCsYTG/OrvkbveZSuN32Gf7OXGOA+Mv7s6RLtrVHjTw3pSjvepmecjiBNwDMGz8tcvEvUtvK8SoVyWRkF3DmqezrR8UTC9R3ervdIH7kaSoBDxmT7h+eJn5P6HfYRMbI7yFy0XSt/ZLdxbRrZrte5hboCxgmkHjsMefch02dITuBe0h4x874EWYy6/cClxl4LXGsdo14ZPt5WFqKnhX+3Nse2ta+3PyF94Mo1IYQQQgghA4Iv14QQQgghhAwIykLIsvBhMW/UbyvExKFeSD5s2BNSD19KuE8BEYT5UHQFEgGRbKnr9OciIq1VTjqA0C5CmTbsmc6CT/qUPe4MOdeFgi+Q0cscJ12mG1h5RXssvs1syeq2FmtJl/e1pc3TffTl3aOCG1p4pJNua9gG8hJfnh4uDkYKAylBrpsNI0M+4kP42CTJjqsvfoEM/PnQWLg++HLdpez/44e+xu4nxQXjKJIq8uClDqbt9XVuLqDctp03/vdUyXYrR2qu0MIuum1bXUJ8H0QkySPU7H62VkNOYUvPwy0klrvk+hwHBXTKsy3d1hYCUreS0UrUZxGR0kxT2xE7O5TM2FvJi0iYA3a+Yg7UJmNJQdKnIIq/BpCbWGlCD2XcY4cS1464IBOuc2vCOPqo6w/uf0hOosJVWuJ6aS0K3Uh0XBGRpQ1uDvhCKpBp2WcI2p+ail3rJqGXCvKDoZ3h2vkxR9GVebhaGOcZzCGVGcCRpGcfoXovonBPt5C9DxOVWFVm4/vQPmdzrbiEN56Bu88LLjcrH4vHF8WlRLLXBf3oVI3czRThEQn3YVS4SmUghUI8X6wMEPPKF4bpZucbisD0+tzjeIvBd50aJDpW7qbuR+X4343I/SMXS5vwPKjtMpLDdtxnQvYGV64JIYQQQggZEHy5JoQQQgghZEBQFkKWByJ3Gra0RQWQcY9QfHEpll6IhJA39vchRBudSxWtsM4bBe8EItF3NsSL8+LYkCTg3CImpIndUHjASCR8YQyExTXzv2CKNcBxQ/QjhFGt+0JJHUngUNJYHUKz3g1A+4p29YzTA9wsELL2/Whkw/3FRe1fSpoTf5aP/rZjh89QxMKG4L10xRcFUZcCc32SlBtMQyUStnAOxtG7FKAoRzXMJYxrWnYTFTLBGOMzZPkbaU9lj54XbiGm6Ephwcko4AAiKmNorRry22Dsl04dcadqoeBFtkDM3Gmur6PPxkWU7Pm9NKEBBxmzvqGHLM02onNWd4UKIt7Bxp88K3PBNYQcxEpBIEmoTqnkpNvLbOPHWtvcGcu6yvh7GxIllf9Y9wW0xztVmGsHmYF3NNGvyjOd/W7TGbYOOK4dY8+kCn+YOT20vaF9x7MnlqSImKIt2sdOTY8fucuojAlOE9YpSYv7wK0ElwWyDIuXg+hY1VeZ+TqrshIUwqpk17/S7hyY04lxJoHUCnKophZPWvP9pmlzoe9xbPvxHcbOSvQW18OpRZ1NFvT+MTI4PDPQ15Iv8pN1WukOxa4f3XK27xj7Yt1IT2CCpPKpiilq5fsK2U4VEpRsoRn0Gc5G/v4x14BuIeRA4co1IYQQQgghA4Iv14QQQgghhAwIykLI8kBBCHjyL5qwmn7nM94hVTAyCh/WriC734WnbcELhOXgttAeC1nsaQlAoZXN3ka4EyD8ax04fDEPlVj0+hTcQJESLx2BFGU0tAcuHehrPycPyCa8Y4XJUIc7QnBG0HCwycr3LhjJ3iUSCB8XGiiOgDC3KViTKhbhHTmMw0MuVdGiX3Y8zttYq64sRjoCdwVcV1zDKJwK8wgvT8k6K0Dug/ZAzmCLWBQQXocDAGQV86b4EKQNGp7vjIRxrbTgrAJNj2Ta6kPmdXzpfuRboR1Ndacpaah69gwXLh9/MjQDYfCSyoA6WgDEXkOMR67t5hekF/YaehcYbVc/h4fWREX3g/OMcVjR/bwrDKRT5j5Kz4GeSmCKHSORwJxsx04rhXo4DsaopZKEovkO94l3gYEjjy045ecnHE3c3/OnhT6XFt1nI88E6YxI/3H1zjU6p9vmPkaxmKLOrxLkUaaIDCRBLZXJ9IyTCIomNbXgD5wvokImkLlV4oIz1WlTqKkOWRYKHKmMok9hIz+3h7KSDfSxuTJ2I7KSDfQVz+1e0cpKIGOKr5MdD8hACl7ilHXywFihWBa+s/I7nKukzi8dFPIxzxX83hHIdsy6oH8uxjIk2w5sDzlImB/m2aXnxXf4N8reG7ZIEiH7givXhBBCCCGEDAiuXJNlgdUNJDLalSp4VvtVAe9vG/bHyodfVdBt7KplsY5tdRXIeBtbT2WRsCKDhKToWPrDJwlaD15dGfZJfX08WuGzjUSftEewPab3MUbSoFkFwmeJ93UOyx8FX/q3GO1nk4u81zNWvFMrvyJhVS74kGNF0qw2YhUK7UDypS2NjP4XkLxlkth0lR5t9V7HdoUJTURpZ/g5Ww/elFe5T3oyHrTpMtRYAbf+0r7JpfgxZiMDxSXdTxNhi/OhIWgjfvbz2/Y+5CiDPu9W5BvrauYcboxHn3CrpyO60tzPU9tHGFrxHBURySdxKXA/p60dc8qH3I5Ze0wTzFrwOM/6iGPuYcxx7eyKJOZXUVdC8bNtVv1RRh798quPJmqAqJBPUDNJbDivXyFtZlc9kdRa0vt/dpNGCBbCNvB6xuo45nhtl0ncK2LMkHAX39fRuOCxlItX5u02WI0u2uRn7JdKeOubKJqPk2vtuDZXIpIVzwF7j+Fa2WRLkThhGyvGGM+8ntuWSMf16FV03tjkPtwbiFQikd0krBZS5e0RtbJl4XF90j7+NtETx+lq8zGubZMsjzHz21ZMUutSKoFR/41oTpiy5UiG9VEDPXeYJn6e4t82v4+5N2wyOyH7givXhBBCCCGEDAi+XBNCCCGEEDIgKAshy8KX7l1EslU2qWfxJBd2rU5raHPEhOcQEkUyDTyOTfgUYdfeUFxW2u3gfiDxyQcEjRQA4V+fgDisMgYj+fDhPT0OvFYLJvyK8zeGXYIYkmoKS1mphZdY6Dnaw6HN1Snd3jfRtBX+2qlwo03w9P7FRjojkkq0SSWIQdbR7TN2/vSlOIQtYvybISsxXsCQSCBxCtKGTtUm3KXCz3r+kpH2oG/oT0gGNZ7pM6lk0j6JRO3Rsu6nX2JutbPn8ol7beMNXnHzorHGXV+b+Bf2d8csz8Kf1+2DxEQR4wc97tqDEL5NBkVffZi+hYRaI8eAN3JKdmPHN5/a38oFvHd8GR/EEh+REGov6b3aS7LyH9wTnVwsLbDnSssf/D3bJzHYS69sTmspH+3n7yMjW/ByriK8n93ftd0hMbmt93avBrmNSgJWls027rvaLvd3ScvbW4/xtEwlh+Rsc491CzpvIWsy/YGcJJKKSGrM4OWt8wySD5vcl04OhFTDlmX3chDk8ercbpjS8V66okm/8HkuGJkLng2FPnMx75M/4wR0i29TDlKPOGnQtQ2/4MD6nDJvHj08rlNJhgXrVw0pnI5LdY+5/1D2PJWQ2DZ+6O1h93NkmztZYwXmn3nmtPFcS11fm2SbtdAmpC9cuSaEEEIIIWRA8OWaEEIIIYSQAUFZCFkWcEZoaSZ2bWdwB4CX8NBO9WxWSUFjVQjRwusZoe9Qrts4Tmh4LmlltQDeYQIhQ/3fQxs2TUsBEC5PonLFkLegrb1oH5EQls5rFBqh88j1IBWmR/i/YrP7ta/pksIisQe4/c62tZfDeVMlwbvZkDOkKz7Mb2120dYmyvrG4yQS5By4ztaBIF2qHmHlfJ92SMrZBOH7qI35WBJUNHKb4F3r/kQIvVMLpePznXisIDWyUhZ4jOd1nOsnhdLmcGpBKN7LKsx4lObjcvBhDLLSHswLOEyUjSwEsiPMHDhW2LHzHtrt+Pp2jMQIx2mPZOUXkHygBLc/tjmHbxPcMKAcMfPQz284NOg9kpSy7QA+XG4rvmuHwtiZ77QdSxvcOAxvd8+F4kJ4ngQnkmJ0DutjH+Q+cSi/GPmhwy0I8qqsM4l329Hv4LWPv6O+4vrYexTGLvpc8mNvLi+ej+3RtFNR2Kal/ufl+dj9J3LSgZwrF8976yPu56efy7FXuIhIawRWILEPuG2r/wzT3twbPe9RrvdRKyvn8GXP4S4Dtdh8aCra6J/teE7ZTVDWHo81+yxPuTj5cuimHeVuLBWBt7gtPZ9PuZ9AUmPlYp1q9r4jpB9cuSaEEEIIIWRA8OWaEEIIIYSQAUFZCFkeGiquaLZ2c4WZQghT1tvRLuVZE1ZLZch7w35TrriyRyUWTZTFzoYZMyWVbZESlFhHKB7hPlvsBK4WyJhvwA0ihP0g2YBbQXsCZdn7uEpU4zCydQlAyBhuKraIzNI6J5lB9ntnDGWyjSMJZBi6XxGFP4w0AKFqtB8ylcRIWJZWuWtVnVE5hwkDp7FFeQAKUfRSTg8t41KAdrdH4hLGNgTfWK3l4LXPkINYdw1fCryJDP5seL5fG0Vixwo4ecDpxEpP5k9xY+9D8ChAMmncKEYQwo/lICjSISJS3ePme9oZIemzdOHntP60Jbj9eOqxcdyobzr/veOEKXAxtMtt39DrXFrUcL2RC3jVThff6bw3Y5bvxveCL0VvJQGVWMrjCx0Z+QLmeaHRZ57pZmNbXOGdfoV8cB1RshtOHLb0Na4ZnjG+SMlYVs7kJUY5OFaYgihLsWzBS5VsoZYCjgPrCvM80YI9kcxHYvmOd+pA4Sy4UpjnQXVSC1YVYxlEVOAlh7FKObaYpnZViddJuah0zfXx8wPzbsRMWMxhPRfcPXJ2OFKuGpEsRenoMRfXuwYN79D72cwJP0YwOoKMx1wfSDS8/Mh23RciEz2XShYnzTmG0Ock6vPwztChIJGKHVsWN5Qz2xCyP7hyTQghhBBCyIDgyzUhhBBCCCED4piQhSwuLsqXv/xlue++++S+++6Thx56SFqtllx//fXykY98ZK/75XLZULKlXq9LtVodcGuPb6zcQUSkYiQfaacLXwTChHqR2e6dFTRyZyUBiyc7R4jqHg3VdrLhxpIeB64DbVM0QhPDg7QiVcBAxEhGUv2xGfM+1F2MQ8+2mAsK1Hi3kJQTh0iQg2C/5orQ1gKKPKQKINj/7cV4+tC3tqe4YNqKELy2A3IG6+qAEHMDTi+7NfxpYqzp8bDShqZKcapTLT0nCsSE0CquY74DuU1WChOOnYt+tsaDRAKuCbXdTuoAxwrrXrLnhW77ke0a3kbhC+N8UVS5D4oOdUbCOUa3BvmHSHCq6JXDtSvPuG0wTyGfqO027hr6WWnWbZtvYd4Z2YG2IynE19kWKcFnCNcD66RTn4CsKivtwRwqz2ifUy4MIkEm4B1b4NDQR1ZVXIilJ7bQjL+uuEcgI7BSi5RLh50DkET0UpKTpByuL2RZaKvvqzlHTiuQ+PsnVXxFJMgOSinZgpVISC8eF8huFk419yrcMBr4mZUxdWraP0wBIx1JvOwh5S7TR27j98Gf1lSmEM+dftK6BEoLbWKYf1mnlfQzXSRcHz/vdVztmHWqmDvqUqOSFiuFKdbdccZm9d4qZd1uIKXB+EIOYgtxFdqxbCdyYcGc1uMUl5KofSIiQ5Nu/+ZYLKlB++x54Qji7xtTRAYSMkL2xzHxcv3444/LNddcc1D7Dg8Py9ve9ra+3xUKtNUhhBBCCCGD45h4uR4dHZV3v/vd8vKXv1xe/vKXy9e//nX58Ic/fED7rl69Wj7zmc8c3gYSQgghhBAix8jL9aZNm+Sv//qv/d/f/OY3j2JrTmy8CwXChEbyUUCIVkOkrVG4FoQQui/kAAcPHxIM4TYUdoGMo2Uy/yGNQGEWQTEY4wKBUCbCfAh5J1llQijSoKH9Qt3KXNzPdqUU9dmG+3FMf65OHCZ3H2JjbbJxgcAYoc0lhG/zfRqrQ93WAg9WwpF2NsF16hqJQ2UWEgltTgnh5HCKCiQffYrQiMSODL7vRi6AdvtQc6q4jYhIaSEO5fssfRNmL2Gs9aPGWicVKs+EsVux2bUHY9ccVzcUc65cMS1zMdIgyGtQJAWFVawMCW4jKdeQvJmvmO9w1SgUMHbh3EsbKtE5IXexcgx8h3HpVuBAEbaBpMC7SBhDES+10NB9vgGnFtNWzHNfMCNbUAXj0BmNC4nYgDikIt7pRSUGC2uDjKI2hXbFBVHcCdEelbJA8mTHo5SSFqHIj5GQYQ7XV6rDikpiICty7U/i/bR/1pHHS1eKKNoSO+KIiHQqkGdlXYwSnWeQIraH9BxLpj/ecQOSHG1f126j1wOSjXY8f+3+6eJLzQkjZ9J7DIWFMHZWLoNCYAVtO8ZJxM4P93dxD9xtwrO4B4WV7tbp81zCBa2rQxCkGrU9oR1eolSM3WVCuSjjmFTBfDXyoxbcTvR+bkp0HJFw7QDkIHZO4t+gXA/tcH227jQ9BrvJAcKERkIIIYQQQgbEMbFyfSgsLi7KRz/6UXnmmWdkaGhILrjgArn66qtlZGTkaDftmKStq1lY8YpWb7pYdXF/Y8U6SrTBiqQv/Ytkp2xpZazg2SRDrJxgVQIJdHb1FD7BPqmom/Va7qYSh7q6olKZzq5Kox1I3LPlz33Z9FQp7q7xYPZJnHpO21a/qu1Xs3TVcMiU5dV+zJ6OBL5udG6R7IoxrksnsYlD8bl86WibHIQEM7+NWWFC2WddjeqlPMtFsomL3mfXbONXqlNlvu24YMUu30ZfdXXYlFHHMZvqs+29fM31QUKiT2Q0ffVt0rFbOsklN9d2x4mOImZ8dTysP3WhiRUu9YVGuXtzmeFj3tL7B/7wNulqeAcSZuNV5W44VTZp2JYt1xwSn1yIhFFzSVAa3V9DjXTYMcMKOFacMb6lJeu1LNpnvTd0jiMJWSSs/CHSYudA+vkBz3brK40Vd0SVEv3KenvjHigtxUmPJXOdFza49tf2xONhk7HRRn+7+IiLGNxBsUJsE0/THueFFvbvY4yMoA4W0s0mLU3iq6lnOeaQTXREoh9WmnHPdc3qbKOEyIK2WRP5bAIfEl/9tbe3rn9mxm20EULcr1ilD37iJnKUutdru/U+MKvsST5Obu/q87vYZ77k9Hok5s0F0ZvyfBJ91y/B01/P1Eq4SPD0RmIk5oTdJp1sTMjeOO5fricnJ+VDH/pQ9Nlv//Zvy2c/+1l5wxvecMDHOffcc/t+vnnzZtm0adMhtZEQQgghhBwfHNeykGuuuUZuvfVW2bZtmywsLMiDDz4ov/zLvyxTU1Ny9dVXy3e/+92j3URCCCGEEHIccURWrq+66ir54Q9/uKx9br75ZrnooosO6byf/exno79f+tKXys033yynnnqq/PEf/7F86EMfkttuu+2AjvXII4/0/XxvK9onCrEvdCpZ0XtJm/BeL05ShGSisdKU0NbQG0KQNqERXrVdyA2aWalGeS7lpa1hvqW1JjFyHskr7u+hHfAoNgk/6keNsr5eqmETGhF6L8OzWTLH8Yk+SJgx8pT0/90ipIo+uA/dj/Et2nfIS2yCGJIMNQsIfrRFk6Tkk5MgqemTaNZYVY7a0TbyFEgb0uWsIRUSMd63uglkCDbkjCRWjEtZ24Gy3SIh+bKtcg60Bx7DIsarVttTnob/djbryEsTTIIYSl4XllxceQge5UaiBMkIEkYhVUjy4RzYHnIF7/XdJ1GtNeq2HdrpxqU8G7ZB+DlInuKwvzsvkhzxnTVEd59VNGE2KWZLiqfnor9vbA5a1eoDghzKJvchhA5wj9ptUD7dy7RMYhjC8z6JTOUTzZVBAwM/dcx3bGNlFJi7aKO/BkaOMbrVjQeSHCEtgNxFJMzXtva9oFID2x+c15ctN7ID79XciJ8rvXI8liLhemCfSD406U6M55uXSpSz62A4f32VJoXOZxMSQbERS1pEwvOsrImdXTPP0FfMD696Mc+uXkpqkeujmFhci9L1Ol8rkImF4+CeQDIq2tGJpDBIhNRtkuy8x3PZJvn6TZCL3o2fa1bm4Z/dmGdIHDU1C6zkhZB9cURerrds2SKPPfbYsvZZWlra/0YHye/93u/Jxz72Mfn2t78trVZLyuXy/ncihBBCCCFkPxyRl+uHHnroSJzmgBkfH5e1a9fK9u3bZWpqSjZs2HC0m0QIIYQQQo4DjvuExn70ej2Zm5sTEVfBkSyDXCoMOxxCZovr3e+jT2upW4T1GmF3hL7hkQpZSbFhvJIhcShlQ6EhNKxSj3VOB2G9tCEv6NTQVjhohOPAWaK+Cl6+mqHe51x+n0Y27pkOn3rvWdMehC2xvy0R3SnH0pV0+fKoHci8R5lv69SivzZXIiyun5sYum8/QuDqvFE0jhMV9ZFGP6Ly6drupQ0u0hOcJ0JX02W1e94bPGwDlwHIF6CNKRvfYfgWQx6CUG9iLgHmhw/TF7PlpDvDbqJVptuZdkAO0lzjalbD3QIl7EVMSBiXoArph5ULqBPCLmew21itkbA+0qChXfDm1vD0iJWX6PiucddlWKUjTePZPKzyJYwv2iwi0tLy9EnJnR/Sj5aR7UCmUFUXiZw6gNhS0/C59uFx7YaVD6Gt3hkI186ML3zH4WveK9r98VPvGz1ebTLcpJAo+XZpaXHrItFByfd2fP4kenRAsgUrD9xrRuKgbavMpWQdps1tfZ6U9VRdY8TsZRhp1YC9N3SbrkocuoXYp1okPDNxzSrT8GAPx4GUwXuEz0NKFsZu8SQ3wBjXod3q5mLGF3MBfbUyJv+chu825CCRLzSkSbp/Ky53LyJSqscOImiPdfvw/SnH7lBdc/krs3Dw6PdvQvxvCp59cDGxfYQkCFK/aE56aR/kILloW9tGQvbHCTlTbr31VllcXJRNmzbJ2NjY0W4OIYQQQgg5TjhuX64///nP93UD+Zd/+Rf5tV/7NRER+a3f+q0j3SxCCCGEEHIcc8zIQq666irZvn27iIg899xzIiLy13/913LrrbeKiMiGDRvklltu8dvfeuut8tnPflbOPvtsOffcc6VUKsmPf/xjr//++Z//eXnve997ZDtxHIAwGkLE5dlsajbCaz7kZkz4IU3ATysrSYOCEGVT7hgSBLgCIBSaN1nspUVt21xcnCQqGACXgSWEALMFXhAWRzt8AY8olBiXO8+lCrSIiOS1oITdLw2KcXhXClvCGy4FHYQys2XLEYpF2WOEmjummA0cHSD9wHXq5EyhGV+8xf0sWjcYXHN1MoEkAa4QbgcNpSJErOdojVjXkazDi+tPGB8Um/BuC32S9HH+gpYvR7ER22cvecH1Mc413SF1IkkVbWmuCvH+UGo67ns09hrehyMJJBKRg40WLIFzhg9TG5kLirQg3N4eyToaICzt55JxrrHlq0WCGwakBSLBIcK79WCeWFcYlfvgnsB9Y68P2pguc28dOHDNvAuKlWHoDpBzoTz23MbgFgK5A+QBtmQ2wPxMzxMbvsc2uEfTpd9FjBShgvtQpVemHntO7TEwJ8rG8cIX7kHp+VY8b9yO2p4lSE/i55NIGE9/zeBGZG4xPLu8W462FYWJRETKKm/xbkF9ZEiQYeGzQit7rwMvezHP2aQUy4cwJ61MDAWQCm191qgKM5Lo6RhDdpPv9DmOziFsg+e23Q6OJF4+Z2pB4Tu0FfOjPWJtjPR4+shI308i/d1fCOnHMfNy/eCDD8rTTz8dfbZt2zbZtm2biIhs3Lgx+u7nfu7npNPpyAMPPCD//M//LAsLC7Jy5Uq58sor5Vd+5VfkbW972xFrOyGEEEIIOTE4Zl6un3rqqWVtf+WVV8qVV155eBpDCCGEEEJIH46Zl2vy/AAhUYRxk3yYQgjlI/yZb2lRDhNKS2fh+wIRRkZR8EUasFPYH2FWL9lAMQ0TxvRZ+RqWx7bWjQKh1ELd/Q2ZSc+EXxHmLy7FIeyILuQT2YIQGRBZNcU0cqn9fcEP67owAecA3R/yFlPIA+PnCy/4kLwJj6sEALISP05mm15J26OhazuucIhB+9OyAZEQssYwllS2U6ibtiZxuBXnyBsJing3DBRkyYbyu9oPNBFh6UI7Kx/whTsiuQ6kSVoARftcWggx66Y6cKAwDK6vDaHD2QVjhsJGPTOuGDOE+9spWYaIkVyV0Pc+cyoVqU5La0SCUw32q68J9yjC4/a8IrEbhXd78M4bcJUIJ/dyB/3p3UJM+xCuRz/g3uPOHztLoKhTaTHsj+IikIdgLtjnCdqN64vrYp10cI4wHirfWTBzIXVPhHvDzP/FePAjWUkjLsrTTRXiEQlOF+grpBpR4SqdFyiW5Z8vxrEC41rb1Y7Oad1CWqN4Puth+jxnfUEZbWokpUnJKPo9i3Hf4rpWZrJzAGMGd5CiOkdZOVRzTNu/kHIU6aMYrM7EEp+4jSodGcZcCA2BLA1yEr9/5HSkP1G8CfOsk73OhOyP4zahkRBCCCGEkCMNX64JIYQQQggZEJSFkGVx15fff7SbQAghhBDyvIUr14QQQgghhAwIvlwTQgghhBAyIPhyTQghhBBCyIDgyzUhhBBCCCEDgi/XhBBCCCGEDAi+XBNCCCGEEDIg+HJNCCGEEELIgODLNSGEEEIIIQOCL9eEEEIIIYQMCL5cE0IIIYQQMiD4ck0IIYQQQsiA4Ms1IYQQQgghA4Iv14QQQgghhAwIvlwTQgghhBAyIPhyTQghhBBCyIDgyzUhhBBCCCEDgi/XhBBCCCGEDAi+XBNCCCGEEDIg+HJNCCGEEELIgODLNSGEEEIIIQOCL9eEEEIIIYQMCL5cE0IIIYQQMiD4ck0IIYQQQsiA4Ms1IYQQQgghA4Iv14QQQgghhAwIvlwTQgghhBAyIPhyTQghhBBCyIDgyzUhhBBCCCEDgi/XhBBCCCGEDAi+XBNCCCGEEDIg+HJNCCGEEELIgODLNSGEEEIIIQOCL9eEEEIIIYQMCL5cE0IIIYQQMiD4ck0IIYQQQsiA4Ms1IYQQQgghA4Iv14QQQgghhAwIvlwTQgghhBAyIPhyTQghhBBCyIDgyzUhhBBCCCEDgi/XhBBCCCGEDAi+XBNCCCGEEDIg+HJNCCGEEELIgODLNSGEEEIIIQOCL9eEEEIIIYQMCL5cE0IIIYQQMiD4ck0IIYQQQsiA4Ms1IYQQQgghA4Iv14QQQgghhAyIY+Ll+kc/+pF87GMfk9e85jWyevVqKZVKsn79ern66qvlzjvv3Oe+W7dulXe9611y0kknSbValbPPPluuv/56aTQaR6j1hBBCCCHkRCGXJElytBuxP0455RTZtm2bjIyMyMUXXywrV66URx99VP793/9dcrmcfOITn5D3ve99mf2eeOIJueSSS2RyclJe/OIXyznnnCP333+/PPnkk3LppZfK7bffLpVK5ZDadu6554qIyCOPPHJIxyGEEEIIOZrwnWYwHBMr1y960Yvk5ptvlt27d8u3vvUt+cIXviAPP/yw3HjjjZIkibz//e+XRx99NLPfO9/5TpmcnJRrr71WHn74YfnCF74gjz32mFx11VVy9913y5/8yZ8chd4QQgghhJDjlWNi5XpfvO51r5NvfvOb8pGPfESuv/56//l9990nr3jFK2Tt2rXyzDPPRCvUO3fulFNPPVVGRkZk165dUiwWD/r8/L88QgghhBwP8J1mMBwTK9f74iUveYmIiDz33HPR51//+tdFROSNb3xjRvqxbt06ufzyy2V6elruuuuuI9NQQgghhBBy3HPMv1w/+eSTIiKyfv366PPvf//7IiJy4YUX9t0Pn//gBz84jK0jhBBCCCEnEsf0y/XmzZvla1/7moiIvOlNb4q+e+aZZ0TEJUP2A58//fTTh7GFhBBCCCHkROLgxcZHmU6nI+985zul2WzKz/3cz8nLXvay6PuFhQURERkaGuq7//DwsIiIzM/PH9D5oENKs3nzZtm0adOBNpsQQgghhBzHHJGX66uuukp++MMfLmufm2++WS666KK9fn/ttdfKXXfdJWeccYZ8+tOfPtQmHjTtdls2b96815dvQgghhJBjgc2bN0upVDrazTjmOSIv11u2bJHHHntsWfssLS3t9buPfvSj8ld/9Veybt06ue2222TlypWZbUZGRvZ5nMXFRRERGR0dPaD27C1zdv369bJ7926uYO+FzZs3i4hwbFJwXPrDcdk7HJv+cFz2DsemPxyX/mzevFna7bZMTEwc7aYc8xyRl+uHHnpoYMe68cYb5UMf+pCMj4/LrbfeKmeeeWbf7U477TR58MEHZevWrX2/x+cbN248pPbs2LGD1jX7gGPTH45Lfzgue4dj0x+Oy97h2PSH49IfjsvgOKYSGj//+c/Lb/3Wb8nQ0JB8/etfl5e+9KV73RYWfd/73vf6fo/Pzz///IG3kxBCCCGEnJgcMy/X3/jGN+Saa66RYrEot9xyi1x66aX73P4Nb3iDiIh89atflWazGX23c+dOufPOO2XFihX7PQ4hhBBCCCEHyjHxcn333XfL2972NkmSRL7whS/IFVdcsd99LrroIrn00ktl165d8oEPfMB/3ul05Dd/8zel3W7LtddeS+E+IYQQQggZGMeEFd/P/uzPSr1el9NPP12+8pWvyFe+8pXMNpdddpn86q/+avTZTTfdJJdccol86lOfkjvuuEPOOecc+e53vytPPvmkvPKVr5QPfvCDR6gHhBBCCCHkROCYeLmemZkREec6smXLlr1ul365Puuss+TBBx+UD3/4w3LrrbfKLbfcIqeddppcd9118gd/8AeZsuiEEEIIIYQcCrkkSZKj3QhCCCGEEEKOB44JzTUhhBBCCCHHAny5JoQQQgghZEDw5ZoQQgghhJABwZdrQgghhBBCBgRfrgkhhBBCCBkQfLkmhBBCCCFkQPDlmhBCCCGEkAHBl+uD5Ec/+pF87GMfk9e85jWyevVqKZVKsn79ern66qvlzjvv3Oe+W7dulXe9611y0kknSbValbPPPluuv/56aTQaR6j1h5fFxUX53Oc+J+95z3vkFa94hVQqFcnlcvKRj3xkn/vlcrl9/nesj8/BjovI8T9n9sa3v/3tfc6Jiy+++Gg38bBTr9flwx/+sJx99tlSrVblpJNOkl/5lV+Rbdu2He2mHTVe/epX73Ne3HrrrUe7iYeVBx54QP70T/9Urr76ajnllFN8v/fHZz7zGbnoootkZGREVq5cKf/xP/5Hueeee45Ai48Myx2Xj3zkI/ucR7//+79/BFt/+FhaWpKvfOUr8u53v1te+MIXSrValeHhYXnJS14iN9xwgywsLOx13+N9zhwujokKjc9Hfvqnf1q2bdsmIyMjcvHFF8vKlSvl0UcflVtuuUW+8pWvyCc+8Ql53/vel9nviSeekEsuuUQmJyflxS9+sVx++eVy//33yw033CC333673H777cd85cjHH39crrnmmoPad3h4WN72trf1/a5QKBxKs446BzsuJ8Kc2R+bNm2Syy67rO/nxzONRkNe+9rXyr333isbNmyQN7/5zfLUU0/JTTfdJF/72tfk3nvvlTPOOONoN/Oo8da3vlVGRkYyn5988slHoTVHjj/6oz+Sf/zHf1zWPu973/vkU5/6lNRqNbniiiuk0WjIt771LfnmN78pX/ziF+Utb3nL4WnsEeRgxkVE5NJLL5Uzzzwz8/nLXvayQTTrqPO///f/ll/7tV8TEZGf+ImfkDe96U0yNzcn99xzj1x//fXy93//9/Iv//Ivsnbt2mi/E2HOHDYSclD8h//wH5Kbb745qdfr0ec33nhjIiJJoVBIHnnkkcx+l156aSIiybXXXus/a7fbyVVXXZWISHL99dcf7qYfdp544onk3e9+d3LjjTcmDzzwQHLDDTccUN9EJNm4ceMRaePR4GDH5USYM3vjn//5nxMRSd7xjncc7aYcFf7wD/8wEZHkkksuSebn5/3nf/7nf56ISPKqV73q6DXuKPKqV70qEZFky5YtR7spR4U//dM/Ta677rrkn/7pn5Lt27cnlUol2dc/59/61rcSEUlWrVqV/PjHP/af33PPPUm5XE4mJiaS6enpI9Dyw8tyx+X6669PRCS56aabjlwjjwKf+cxnkl//9V9PHn300ejz5557LrngggsSEUl+4Rd+IfruRJkzhwu+XB8GrrjiikREko985CPR59/5zncSEUnWrl2bNBqN6LsdO3YkpVIpWbFiRdJut49kcw87f/Inf8KX6z4cyLicqHMGnMgv181mMxkfH09EJPne976X+f78889PRCS5//77j0Lrji4n+st1mv29RF555ZWJiCSf/OQnM99de+21iYgkH//4xw9jC48OfLneP/fcc08iIkmlUkmazab//ESdM4OCmuvDwEte8hIREXnuueeiz7/+9a+LiMgb3/jGTBh/3bp1cvnll8v09LTcddddR6ah5HkP58yJy9133y2zs7OyadMmueCCCzLfQz711a9+9Ug3jRxD1Ot1ueOOO0RE+kruOI9ObPC+0mw2ZWpqSkQ4ZwYBNdeHgSeffFJERNavXx99/v3vf19ERC688MK++1144YVyxx13yA9+8AN59atffVjb+HxlcXFRPvrRj8ozzzwjQ0NDcsEFF8jVV1/dV1d5IsA543j88cflgx/8oExNTcnq1avlsssuk9e//vWSzx+/6wMHcu1FRH7wgx8csTY93/ibv/kbmZqaknw+L2effba85S1vkdNOO+1oN+t5xWOPPSbNZlPWrFkjp5xySuZ7ziORO+64Qx566CFpNBpyyimnyJVXXnnc6K33B95XSqWSrFy5UkQ4ZwYBX64HzObNm+VrX/uaiIi86U1vir575plnRET6Tlb7+dNPP30YW/j8ZnJyUj70oQ9Fn/32b/+2fPazn5U3vOENR6lVRw/OGcc999yTyVA/77zz5Etf+pKcddZZR6lVhxde+/3zX//rf43+fv/73y/XXXedXHfddUepRc8/9jePhoeHZWJiQqanp2V+fl5GR0ePZPOeF3zuc5+L/r7uuuvkrW99q3zmM5857hd2PvWpT4mIyOtf/3ofHeWcOXSO32Wfo0Cn05F3vvOd0mw25ed+7ucy/+cLu5uhoaG++w8PD4uIyPz8/OFt6POUa665Rm699VbZtm2bLCwsyIMPPii//Mu/LFNTU3L11VfLd7/73aPdxCPOiT5nxsfH5Xd/93fl3nvvlampKZmampLbb79dLr74Ynn44YfliiuukNnZ2aPdzMPCiX7t98VP/dRPyec+9znZvHmzLC0tyWOPPSYf/ehHpVgsyoc//GH/wkD2P49ETty5dOaZZ8rHP/5xeeSRR2RhYUGeffZZ+bu/+zs5+eST5Utf+pL88i//8tFu4mHlG9/4hvzN3/yNlEol+aM/+iP/OefMoXPCrlxfddVV8sMf/nBZ+9x8881y0UUX7fX7a6+9Vu666y4544wz5NOf/vShNvGocTjG5kD47Gc/G/390pe+VG6++WY59dRT5Y//+I/lQx/6kNx2222HdI5D4WiNy7HMoY7ZBRdckNEbv/a1r5W77rpLXvOa18idd94pn/70p+WDH/zgwNpMnv/ccMMN0d9nn322/MEf/IH85E/+pLzuda+Tj3zkI/Lrv/7rUqvVjlILybHA29/+9ujv4eFh+cVf/EV5zWteI+edd5585StfkXvvvfe49NP/0Y9+JG9/+9slSRL5sz/7M6+9JoPhhH253rJlizz22GPL2mdpaWmv3330ox+Vv/qrv5J169bJbbfd5rVLFoSX9nacxcVFEZGjHmIZ9NgcKr/3e78nH/vYx+Tb3/62tFotKZfLh+1c++JojMuxMmf2xuEas0KhIB/4wAfkzjvvlNtuu+24fLk+1q/90eCKK66Qn/zJn5T7779fvvOd7xzXeQgHyv7mkQjnUpoNGzbIu971Lvn4xz8ut95663H3cr1t2zZ5/etfL9PT0/Lbv/3b8t73vjf6nnPm0DlhX64feuihgR3rxhtvlA996EMyPj4ut956a18zehGR0047TR588EHZunVr3+/x+caNGwfWtoNhkGMzCMbHx2Xt2rWyfft2mZqakg0bNhyVdhyNcTlW5szeOJxjBq319u3bD9s5jiZIzDtWr/3R4qyzzpL777//uJ0Xy2V/82hxcVFmZmZkxYoVfFEyHK/Plz179sgVV1whTz/9tP8fiDScM4cONdeHyOc//3n5rd/6LRkaGpKvf/3r8tKXvnSv2yLs8r3vfa/v9/j8/PPPH3g7j2V6vZ7Mzc2JSNB5nShwzuyd6elpETl+5wSv/cFxvM+L5fLCF75QKpWK7N69W7Zt25b5nvOoP8fjPFpYWJArr7xSHn30Ubn66qvlf/2v/9W3PDznzKHDl+tD4Bvf+IZcc801UiwW5ZZbbpFLL710n9vD7eKrX/2qNJvN6LudO3fKnXfeKStWrNjvcU40br31VllcXJRNmzbJ2NjY0W7OEYVzZu986UtfEpG9W9Ud61x66aUyPj4umzdv7hsB+OIXvygizgOdOHbv3i133nmniBy/82K51Go1ee1rXysiIv/wD/+Q+Z7zKEuSJHLLLbeIyPEzj5rNprz5zW+W++67T173utfJ3//930uhUOi7LefMADjaVWyOVe66666kVqslxWIxueWWWw54P5Syfu973+s/a7fbydVXX33clrI+kEqEf//3f5/cd999mc+//e1vJyeddFIiIsknPvGJw9jKI8+BVq48EecM+OQnP5k888wz0We9Xi+58cYbk2KxmORyueO6QiHKn7/yla9MFhYW/Ocncvnzu+++O7nllluSTqcT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6fj6+nqUlpZafU/ipZdewv79+3H06FGEhYVBo9GgoqIC+fn5CAgIwPr16zvz0lxKqnlrT+x2B8aX8pKSkiCTtb2vhKff21rr6Jx19r3No5LrcePG4cUXX8ShQ4dw8uRJ1NbWwtfXF6GhoZg1axbS0tIwdOhQh/qKi4tDZWUlCgoKTJ++7dOnD2JiYvDwww8jNTUV3t7eLr6im5Narcbx48eRnp6OHTt2YPv27QgMDERaWhpeeeUVqFQqdw+xS/GkWBs1ahTmzp2L/Px8FBQUoK6uDn5+frjrrruQkJCAuXPnQqFQONyfJ8SalHPmSbFmtGHDBowdOxZr165FXl4evLy8EBkZid///vdISUlxuJ+ePXvi4MGDeO2117B582bs2LED/v7+mDNnDpYuXYpBgwa58Co6nxTzJvV/7zcDg8GArKwsAMAjjzzS7n484d5mJMWcdfa9zUsIISTrjYiIiIjIg3n8PtdERERERFJhck1EREREJBEm10REREREEmFyTUREREQkESbXREREREQSYXJNRERERCQRJtdERERERBJhck1EREREJBEm10REREREEmFyTUREREQkESbXREREREQSYXJNRERERCQRJtdERERERBJhck1EREREJBEm10Tkdl5eXggNDXX3MCS1ZMkSyGQyfPPNNy47R15eHry8vMx+amtrzY4pKirC8uXLMXPmTAwaNMh0nKPCw8Nd+rtZsGABBg0ahH79+iEgIAAzZ87EhQsXzI5RqVRm15iZmWmq02q1UCgUmDdvnsvGSETkjB7uHgARUXdz6dIlZGRkYNasWRgxYoTLzzdkyBDExMQAAHr27GlWt3TpUuzcubNd/Z45cwbnzp3D008/3eExtmXatGlYuHAh+vfvj8rKSsTGxiIxMRHHjx83HZOUlASdTocTJ06gpKTErP2tt96K3/3ud1i9ejXmz5+P8PBwl42ViMgRfHJNRCSxv/zlL2hsbMSiRYs65XwxMTHIzMxEZmYmevXqZVb3q1/9CosXL0Z2dja0Wi3kcrnD/WZnZwMApkyZIul4Wxs3bhz69+8PAAgODsYDDzyAs2fPmh2zevVqZGZmYvr06Vb7eOGFF9DS0oLFixe7bJxERI7ik2siIgnpdDps3LgRv/jFL3D33Xe7ezj44x//2O62OTk56N27N8aPHy/dgGw4f/48Pv/8c7z66qtO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esydOxdFRUUWa6AB4Nlnn0VWVhaio6Nx7Ngx5Obm4q677kJ+fr7paaa1fZvtCQ8Pt/gipPHfN770l5iYiFtuuQWbN292+jyuUFNTg/z8fNOP+N/n1VuXGbeu27VrF4QQN+V6682bN8PHxwdz5sxx91CIyMNxKz4icjtjwnejMWPGmNYAOyo+Ph7x8fFmZc3NzTh69Ci8vLwwcuRIp8cXFxeHd955B3q93vRxmKysLISFhZn2bzZSKBRITU3F22+/jaKiIkRFRZnqQkND27xWAEhPT0d6errT47Nlzpw5Diec2dnZ8PHxwX333We13t74bT2td2Yczvr++++Rl5eHWbNmITAw0CXnICJyFJ9cE1G3UVZWZrHHscFgwAsvvIB///vfmDRpEgYMGGBWX1NTg6ysLGRlZUGn0+HMmTPIysrCnj17TMc8+eSTaGlpQWJiIg4cOIC//vWvWLt2LRYvXmx1HIsWLUKvXr3w2muvSX6N1hw+fNiUvDY2Nra7H41Gg1WrVpl9ObIrmDdvHubMmYMdO3ZYrc/IyIBMJsOSJUs6d2BERFZ4CVuPIYiIbiLLly/Hyy+/jKioKAQHB+M///kPSkpKoNVqoVarcfjwYYtlHHl5eWafSzcKCQkxbfkH/Pz586effhqFhYUIDAzE888/j2eeeabNsSxZsgTp6ekoKSnBiBEjJLvG1qyNvaamBmq12iXncxeVSmW25n3Dhg2mp+BarRa33347UlNTsXr1ajeNkIjo/5hcE1G3UVBQgBUrVuDYsWOoqanB9evXMXDgQMTFxWHRokVtfr2RiIhIKkyuiYiIiIgkwjXXREREREQSYXJNRERERCQRJtdERERERBJhck1EREREJBEm10REREREEmFyTUREREQkESbXREREREQSYXJNRERERCQRJtdERERERBJhck1EREREJBEm10REREREEmFyTUREREQkESbXREREREQSYXJNRERERCQRJtdERERERBL5L3bnhRVlIb3lAAAAAElFTkSuQmCC", "text/plain": [ "
" ] }, - "metadata": { - "needs_background": "light" - }, + "metadata": {}, "output_type": "display_data" } ], @@ -151,27 +142,25 @@ }, { "cell_type": "code", - "execution_count": 14, + "execution_count": 6, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ - "/tmp/ipykernel_188985/2125385323.py:9: RuntimeWarning: divide by zero encountered in log10\n", + "/tmp/ipykernel_9824/2125385323.py:9: RuntimeWarning: divide by zero encountered in log10\n", " p = ax.pcolormesh(xRange, zRange, np.log10(dens_data).T)\n" ] }, { "data": { - "image/png": "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", + "image/png": "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Xh294vleN+ZvB1FVauYdsOnTp+NjH/sY4jjGBz7wAeywww544IEHcNppp2HevHm47LLLulzm6NGj8b73va9D+kEHHRTM/7e//Q1HHnkkmpubceCBB2L33XfHX/7yF5x77rmYNWsWbr75ZkQayEIIIYQQQogNpCYWYG+99RYmT56MUqmE6dOn46STTgIA/Pvf/8ahhx6Kyy+/HMcddxzGjRvXpXJPPPFETJ06NVPe9vZ2nHrqqWhubsYVV1yBc889FwCwevVqfPjDH8Ytt9yCY489FqeffnqX6iC6jz88873NXQUhqs/Jm7sCQgghhOhOakKC+Mtf/hIrV67EhAkTKosvANhpp53wwx/+EABw+eWXb9I6zJgxA4sWLcLo0aMriy8A6NWrF66++uqq1EEIIYQQQgixdVMTC7CZM2cCACZNmtThu/Hjx6OxsRH3338/WlpaNksdxowZgz322ANPP/00XnrppU1WByGEEEIIIcTWTU0swJ588kkA6xY676S+vh777LMPWlpa8Nxzz3Wp3CeeeAJf/epX8cUvfhEXXXQRHnrooQ2qA6fPmzevS3UQQgghhBBCiDKb/R2wlStXYsWKFQCAQYMGBfMMGjQIjz/+OBYvXoxRo0ZlLvuuu+7CXXfdVfn/xRdfjMMPPxw333wzdtppJ5P35Zdf7rQOALB48eLM1xdCCCGEEEIIZrMvwFavXl057tGjRzBPz549AQCrVq3KVObAgQMxdepUTJgwAXvssQeam5vx2GOP4fzzz8dDDz2E4447DrNnz0aeXGeX69FddRg5cmQwfeHChRg6dGimMoQQQgghhBBbF92yAJs4cSKeeeaZLp1zww034MADD+yOy3fg6KOPxtFHH135f58+fXD88cfjgx/8IPbff388/vjj+P3vf49PfOITm+T6QgghhBBCCBGiWxZgixYtwoIFC7p0ztq1awGs8zLIaX369OmQd82aNQCA3r17b0Qt113rK1/5Cs466yzce++9ZgHWq1cvLF++vFKvja3D/Pnzg+meZUwIIYQQQgix9dMtTjjmzp2LJEm69CnH9OrTpw/69u0LAFiyZEmw/HL64MGDN7quw4YNAwAsXbrUpO+2225Vq4MQQgghhBBi26QmvCCOHj0aADBnzpwO37W3t+Ppp59GY2Mjhg8fvtHXWr58OYD0na4sdeD0rjgBEUIIIYQQ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E96NEEIIIYQQYmunZiSIEydOxNKlSwEAr776KgDgl7/8Je655x4AwMCBAzFjxgxzTtnxR3t7u0nfa6+98KMf/QhTpkzBYYcdhg996EOor6/Hfffdh+bmZvzkJz/Bnnvuac6pq6vDb37zGxx11FGYMmUKbr75ZgwePBgPP/wwli5dikmTJuG0007bJPcuhBBCCCGE2DaomQXYP/7xjw5Bjl955ZWKdaurzi/OPfdc7LnnnvjRj36Ehx9+GABwwAEH4Pzzz8dxxx0XPOf9738//v73v+Oiiy7Cgw8+iCeffBJDhw7FV7/6VZx99tmIomgD7kwIIYQQQggh1lEzC7CXXnqpy+ckSfKu3x9//PEd3vXqjJEjRwbfAxNCCCGEEEKIjSVKOlvFCCGEEEIIIYToFrZoJxxCCCGEEEIIsSWhBZgQQgghhBBCVAktwIQQQgghhBCiSmgBJoQQQgghhBBVQgswIYQQQgghhKgSWoAJIYQQQgghRJXQAqyKPPvss/jBD36AD37wg9hhhx1QV1eHnXfeGSeddFIlWLTHkiVL8JnPfAa77LILGhsbMXz4cFx00UVoaWmpUu23TNasWYNf//rX+PKXv4yDDjoIDQ0NiKIIU6dOfdfzoih614/aPcyGtjegMb4pePDBB991HB988MGbu4pbJM3NzfjWt76F4cOHo7GxEbvssgsmT56MV155ZXNXbatk3Lhx7zqO77nnns1dxS2SJ554At///vdx0kknYdCgQZX27Izrr78eBx54IHr16oX+/fvj2GOPxaxZs6pQ4y2brrb31KlT33Xcf/3rX69i7bc81q5di9tuuw2f/exnsddee6GxsRE9e/bE6NGjcfHFF2P16tXuudUY4zUTiHlb4KijjsIrr7yCXr164eCDD0b//v3xz3/+EzNmzMBtt92GK664Auecc06H81544QWMHTsWy5Ytwz777IPDDjsMjz/+OC6++GI88MADeOCBB9DQ0FD9G9oCeP755/HpT396g87t2bMnJk2aFPwun89vTLW2Wja0vTXGNy1Dhw7FoYceGkwXXaOlpQVHHHEEZs+ejYEDB2LChAl46aWXcN111+Guu+7C7Nmzsccee2zuam6VnHzyyejVq1eH9Pe85z2boTZbPpdccgluv/32Lp1zzjnn4KqrrkJTUxM+/OEPo6WlBX/84x9x3333Ydq0aTjx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GzYMjz/+uMbxJqazsb9mzRq8/fbb2G677bQAqwKav7vGW2+9hQ9/+MNYvHhxZfH6Tqo9xvUO2Gbgd7/7Hc4880z06NEDM2fOxPve9z43b9k8OmfOnOD35fRRo0Z1ez1FR+I4xsqVKwGkWmCxcWiMbx6WL18OQOO4K2is1h4ax9Vhr732QkNDA9544w288sorHb7X2K8uGvfZWb16NT7ykY/gn//8J0466ST84he/QBRFHfJVe4xrAVZl7r77bnz6059GoVDAjBkzcMghh7xr/rK3vTvvvBOtra3mu3//+994+OGHsd1223Vajuge7rnnHqxZswZDhw5Fnz59Nnd1tgo0xjcP06dPB+C7VBcdOeSQQ9C3b18sXLgwaJ2cNm0agHUx7cSm54033sDDDz8MQON4U9PU1IQjjjgCAHDLLbd0+F5jv3okSYIZM2YA0LjvjNbWVkyYMAGPPfYYjj76aPz2t79FPp8P5q36GO+WcM4iE3/961+TpqampFAoJDNmzMh83iGHHJIASM4+++xKWnt7e3LSSSclAJKLLrqo2+u6tfK9732v0zb77W9/mzz22GMd0h988MFkl112SQAkV1xxxSas5dZDlvZOEo3xTcWVV16ZvPzyyyYtjuPkmmuuSQqFQhJFUfL4449vptptmXzzm99MACTvf//7k9WrV1fSL7/88gRAcvjhh2++ym2FPPLII8mMGTOSYrFo0hctWlSZN0444YTNVLuti4aGhuTd/iz84x//mABItt9+++S5556rpM+aNStpaGhI+vXrlyxfvrwKNd06eLf2fv3115Orr746WblypUlftWpV8sUvfjEBkOy8887JmjVrqlHVLZJisZhMnDgxAZAcdthhmdqqmmM8SpIk6Z6lnOiM7bbbDm+//TaGDBmCD3zgA8E8hx56KD73uc+ZtOeffx5jx47Fm2++iX333Rd77703/v73v+PFF1/E+9//fvzpT3+qxDEQHZk4cWJFJ/3qq6/iX//6F97znvdUYj0MHDiwspsEAKeffjp+9atfYfjw4Rg5ciTq6urw3HPPVXa8P/7xj+PGG29UEFuHrrY3oDG+qdh9992xZMkSjBkzBkOGDEFLSwueeuopLFq0CLlcDldddRXOOuuszV3NLYqWlhaMGzcOjz76KAYOHIjDDjsMixcvxqOPPooBAwZg9uzZ2GOPPTZ3Nbca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U7du3ayOUacSEhLk4eGhAwcO1Ns+tm7dKpvNVu7rzJkz5ZZJS0vTnDlzFB0drS5dujiXq66QkJB6fW+ef/55denSRW3btlW7du0UHR2trKyscsv4+PiUO8alS5c6+3Jzc+Xl5aXJkyfXW0YAcFdNrQ4AAIAZfvrpJyUmJmrUqFG68847631/gYGB6t+/vySpefPm5fpmzZqltWvX1mq7GRkZOnbsmKZMmXLdGSvz8MMPa/r06Wrfvr2+//57DR48WGPGjNHu3budy8TExKiwsFD79u1Tenp6ufU7duyoiRMn6p133tHUqVMVEhJSb1kBwN0wAgYAuCH84x//0MWLF/XSSy+Zsr/+/ftr6dKlWrp0qVq2bFmu75577lFcXJySk5OVm5sru91e7e0mJydLkoYNG1anea8WERGh9u3bS5L8/f01dOhQHT16tNwy77zzjpYuXarhw4e73MaLL76osrIyxcXF1VtOAHBHjIABABq9wsJCffjhh7rjjjvUq1cvq+Pob3/7W63XXbdunVq1aqUBAwbUXaAqnDhxQhs3btTs2bNrtF7nzp0VGRmpzz77TD/99JP8/PzqKSEAuBdGwAAANfLtt9/q4YcfVrt27WS329WtWzdNnjxZP/74Y6XrrF69Wv369ZO3t7d8fX01evRoHT9+XPHx8RXuH6oPq1at0oULFzR27NgKfVlZWbLZbBowYICKioo0ffp0BQQEyG63KygoSP/85z9lGEa95quuM2fO6Ntvv1VUVJSaNWsmqXz+goICPf/88/L395eXl5dCQ0O1bt065/qrVq1S37591aJFC/n5+enZZ59VUVGRy3395z//UZs2bRQYGCgPDw/16NGjxnljYmJ0+fLlen9/AcCdUIABAKpt+fLlCg8PV3Jysrp3767o6GjZ7Xa9++67Cg0NVUZGRoV13nzzTY0cOVJ79uxR3759df/99ystLU19+vTRyZMnTcm9fv16Sapy1KikpESDBw/W4sWLFRYWpsjISOXk5Gj69OkN5jK6DRs2qLS0VA899FCFvpKSEg0aNEgff/yx+vXrp379+ik9PV0jRozQli1b9K9//UsxMTFq1aqVoqKiVFpaqgULFuiJJ55wua9HHnlE586dU05Ojvz9/TVs2DDl5eXVKK/jfH/++ec1PlYAaLQMAABckGQEBAQ4X586dcrw8vIymjRpYqxd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", "text/plain": [ - "
" + "
" ] }, - "metadata": { - "needs_background": "light" - }, + "metadata": {}, "output_type": "display_data" } ], @@ -203,7 +192,7 @@ }, { "cell_type": "code", - "execution_count": 15, + "execution_count": 7, "metadata": {}, "outputs": [], "source": [ @@ -238,102 +227,99 @@ }, { "cell_type": "code", - "execution_count": 16, + "execution_count": 8, "metadata": {}, "outputs": [ { "name": "stderr", "output_type": "stream", "text": [ - "100%|██████████| 500000/500000 [00:01<00:00, 269913.01it/s]\n" + " 0%| | 0/500000 [00:00" + "
" ] }, - "metadata": { - "needs_background": "light" - }, + "metadata": {}, "output_type": "display_data" }, { "name": "stderr", "output_type": "stream", "text": [ - "100%|██████████| 500000/500000 [00:05<00:00, 97611.51it/s] \n" + "100%|██████████| 500000/500000 [00:05<00:00, 85160.64it/s]\n" ] }, { "data": { - "image/png": "iVBORw0KGgoAAAANSUhEUgAAAbIAAAF0CAYAAABGwry1AAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjUuMSwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/YYfK9AAAACXBIWXMAAA9hAAAPYQGoP6dpAAEAAElEQVR4nOyde3xcV3Xvv2dmNKPR6P2wbEV+27EdO5Gdp1+EJMSk4RYSHiZpL6SU3tKQUmjghrQXCgHC7Q0huJQC6YNCA6UJLpBASwgmISR+5uU4iWMnfsuKLNuyZT1mpBlp5tw/9uwz++zZ58yMYjmxmPX56CPpzD57r73nnL32Wuu31rJs26ZMZSpTmcpUprOVAm80A2UqU5nKVKYyvR4qC7IylalMZSrTWU1lQVamMpWpTGU6q6ksyMpUpjKVqUxnNZUFWZnKVKYylemsprIgK1OZylSmMp3VVBZkZSpTmcpUprOayoKsTGUqU5nKdFZTWZCVqUxlKlOZzmoqC7IylalMZSrTWU1lQVamMpXprCbLsv7JsqwjlmUNWJb1omVZ73yjeSrTmSWrnGuxTGUq09lMlmUtBA7Ytp20LOsS4NfAHNu2T7zBrJXpDFFZIyuTL1mWdYdlWW/4aceyrA9ZlmVbljXrjealTG8usm17t23bSfkvEAbOeQNZKtMZprIgK9NZS5ZlrcwK2vozMFa1ZVlfsCzrl5ZlncwK1Q+V2EfEsqy7LMvqtixr2LKsbZZlrZkglk8bH5ZlXWhZ1s+y805YlvWSZVkfP5M8FyLLsr5lWdYw8DTwGPDiG8xSmc4glQVZmc4W+j4QBQ4p11YCnwfqz8D4zcDngEXAjnH28T3gk8C/A58A0sAvLMtafToYnAg+LMt6O7AFmAJ8Kdv+v4D2M8VsMWTb9i1ANXA18Cu77DP5naLQG81AmcpUDNm2nUZsuG8UHQGm2bbdY1nWxYiTf9FkWdalwI3AbbZtfzV77T7gJeArCKH8usmyrMeBg7Ztf+j18mFZVi1wH/DfwPts286cDh6LJcuyNgKrPD7+sm3bn1UvZJ+RRy3L+kvLsvbYtv2LCWeyTG8KKmtkZ4Ckn8myrHMty/qBZVn9lmUdtyzrS5ag6ZZlPZRFXfVYlvUp7f6ZWdPJK1lT0AnLstar/iLLsqKWZe3O/kSV641ZRNdmy7KCBfhcbVnW05ZljViWtc+yrD/zaXuOZVn/alnWUcuykpZl7bQs68Me855nWdb3LMs6lZ37dy3LqlLa1ViW9XeWZR3M9nXMsqwNlmVdqLRx+cgsy7oDuDv78YHsZ7ZlWX+c/f1uA89/mP1shXJtoWVZM/zWBcC27aRt2z2F2vnQ+xCC+J+UPkeA7wArLMuarvBUcG3PBB/AHwKtwGds285YlhWzLKvoPeP1Pve2ba+2bdvy+Pms17iIA/q8Yvks09lPZUF2ZukBxJr/FbAN+Czwl8AG4DXgdmAv8FXLsi5X7rsEcVK+H/g4cC/wNuBxKRBs2x4G/gjxAn9ZufebQB3woeyJ1UiWZZ0P/AphQroD+C7wBcAkEFqBrQgzzj8gzE17ge9YlvWXhu5/BNQAf539+0MIk6Cke4GPAj8GbgG+CgwjzHhe9BPgP7J/3wp8MPvzI+Aw8D8N9/xPYJ9t21uUa7sQWsdE0zLgVdu2B7TrT2V/L4Vxre2E8JGlq4EB4BzLsl4BhoABy7K+bVlWZQljjve5L0iWZdVlDyjVlmWFLMtaC1wJPFFKP2U6y8m27fLPBP8gBIMN/KNyLYjYcDPA7cr1eiABfE+5FjX0uTzb5we16/8XceJ+C+L0bQOfKILHnyKExwzl2iJgTDwmrrb/AnQDTdr1/wBOSX6VeX9Ha/cToFf5/xTwDwX4+1C2r1nKtf+tX1PWYASoU661AKPAHVpbG3i8xO/z4ux9HyrhnpeARw3Xz8v29WelrK3POI+rz854+che2wHEsz9/D7wn+9sG/mOin/si17UW+E12bfqBZ4H3lNJH+efs/ylrZGeW/kX+YQvt6BnAQph15PVTwCvAHOXasPzbsqwKy7KaECfYU4BjfsvSHcBO4N+AbwG/RWw+npQ1OV4DPGjbdqcy7i7gEa2tBbwX+Hn232b5k21bZ+DpXu3/J4EmS/hgyM7jMsuy2vz4LIHuAyIIQS7pBoTJ6QdqQ1uYqa44TeP6URRIGq6PyM9LXdvss9CstasAIvp1xSRYkA/lWjVQBdxn2/bHbdv+iW3bHwf+EbjRsqz5Rc59XM99MWTb9oBt21fatl1v23adbdsX2bb9k1L6KNPZT2VBdmapU/u/HxixbbvXcL1B/pP1f33RsqzDiE2oFziOOMXWqTfatp0CPgzMRpjz/ti27UIIrhbEBrbH8Nkrhrb1wEeyPKg/3822maLdo8+7L/tbzvHTwBLgsGVZT2V9KyVtaCrZtr0bAcZQzYv/E9hq2/be8fb7OmkYIVx1qlQ+L3VtVxnarUSAOfTr0g9YDB9of/+H1vaH2d8rKI7G9dyXqUzFUhm1eGbJ5KPy8ltZyt/fAP4Y+DsEFLofYbK5H/Nh5Jrs70pgPnBgHLx6kRzvBwitz0QvaP/7ztG27R9ZlvUkwh/3duA24HbLst5j2/bD4+TzPuDrlmW1Izbu5cDHxtnX6aAjmIN0p2V/d1P62u4A9Pive4AeckAYSRKoUgwfKH8vBo5qbY9lfxcrdMb73JepTEVRWZCdHfQ+4N9s23ZQXVlne73e0LKsCxDxTt9FOO7/xbKs823b7vfp/zji9G0yFS0wtB0EgrZt/7qEOfiSbdtHEKbQb1mWNQV4DvgM4CfI/DTN+4GvAX+A0DZHEaCDN4qeB660LKvWdgMtLlM+L2ltbdvuQ6RjcsiyrD7giM/9xfAh6VmEoDwHt2YuTcDHC/FYpjKdCSqbFs8OSpN/Uv0LhOPcIcuyKhDBrt0ItNuHEPDpdX6dZ/0WjwDXq1B0y7IWkdPu1LY/Bt5rWdYSvS/LslqKmZDSPmhZlm4ePZadg8kEplI8+7te/yBrtnoY+ADCrPhLgymraPh9sWRZVlW2z2bto/9EfF8fUdpGEJr2Ntu2D5/utfWggnwobX+U/f0nWh//CwECevw08FOmMr1uKmtkZwf9F/BBy7L6gZcRvomrAT0p6mcRWtjbbNseBF6wLOuLwJ2WZf2n7R8g+nng94AnLcv6FuLZ+AsEcOQCre1fISDO2yzL+ucsT40IIMLV2b+LpRqgy7Ks/0SYyoayfVwCfMrvRoTGAPBly7LuR2hdP7dtWwq4+xAbN8DfePSxCwGIuaIQo5ZlfQwhNKVG8s6s6RLgG1mt91IEiu4LCOANALZtb7Msaz3wt1mNcy8iXGIWbkFxOtc2j0rgA9u2t1uW9a/Ahy3LCpFbp7XA39q2rZohy1SmN47eaNjk78IPORhys3b9e8CQof3jwEvK//XAv5IzPf0SYfI7SBaujNjoRoG/1/oKImKEXgPqC/B5OQJRlgT2AX8meTe0nYKIc+oEUgjfy6+BPy1i3h/KXp+FSPD6FYRJawAhyJ4HPup1j3b9s0AXQmvV4flh4CQCFVnpMeei4ffZ9bY9fmZl21yR/f8Ow/2VCN/VEQRK8CngmvGsrQ+Pj1MAwl4sH9m2FYhDzsEsL3uAvzwTz335p/xT7E+5jEuZJi1ltYhuhJamm8fKVKYyTRIq+8jKNJnpegSk/Uxk7ihTmcr0BlFZIyvTpCPLsi5D+PX+BpFBRA/QLlOZyjSJqKyRlWky0keBbyPinW56g3kpU5nKNMFU1sjKVKYylalMZzWVNbIylalMZSrTWU1lQVamMpWpTGU6q6ksyMpUpjKVqUxnNZ31mT2ypS/aEIHCZSpTmcp0tlAN0G1PAFAhm4s1PM7bU7aoGn7W0FkvyBBCrOuNZqJMZSpTmcZB7YisO6eNLMuqnDolONxzzLMgfCHqsSxr9tkkzM561GK2OGP/4cOHqa0VdRqvq7uJh/rvc37rdPWHvsGvv/cXRfV/XZ1Ab+v9XLfmK/DUS851OdbqT36TjV/7c9d9elu/ftXPJKlz0eek/u8aU72+5iui8VMvuT5X+5frEvvp077rYZqDfl3vx3jPpUvy12TNV3how6eNfaufqaT3p47nd49pXK/5uL6PS5e4+pRr67pWoB/9+zK1zZubMsbqT34TgKYX47l7ffjXybQu19XdRPzdl+S9F6s/+U2avrPN4SF+TtT5bv3WSP8uiiF1vup8vPpQvzfT2vmtp+n7eqj/Pq7+0DcAGJgRYNqWuLF/uX/I91qS6b1S9xp1nP9R9wds5BcgqpirVQheN8k98cCzM6mtKc17NDCYYfZFh0BUO8gA37Rt+5unk7+JoMmgkQFQW1vrCLKQVUFtba3zW6dQRaXxuolCVoXTv+t6qBKU/uVYwXClM7a8T2/r16/6mTo3rzmFNB709g6vANrnav9yXfSxdTLNIe+61o/xHtOahCrz5uLwGzJ/Z3p/rvn43GMatyDP2XH0e/3a+33npu/Zc27K58FwZXbstOter3F1Mq1LyKowvhfBcPa7zPKgfrd+a6R/F8WQOl/9HfKbh+k997qm9q9fr62tJVQh5hmMBAiF0uZ3LrtOIWWezv36/xX5z3RtbS0h/N+z00G1NYGSBZlCl55uATuRNGkEmUobMutdvyWtCaxlQ2Y9sfVbWbN+rfumFR1s2PRZ1gRy1zdk1rMhs951zZNWdADQvCPujAOwZtWdsGVHjodVdxp5Uv838S75UPmR/Jn6MV1X/9b7B4h1DTvzYMsOZ010knPKW9/s9c2Z9U7lrzWr7szjTfafN8fs+pvWXfKhfxemtTP1p/Otf8/G/lbdyYZNn3WvueQj21fvzStzYyvrZRrTtVbKd+m1jur3po6z3WPOavuVN9xDbP1W4/NbzPMmqXlHPG9NTO1Na6STF6+m58Dv3rwx5TOrtM2b94qO3DX1fVTmL9cMIJa9R583AO1RVt5wD5u1/WLlDfcQU56BlTfcw+YHzAUcHuq/j7q6OuNnp4vSdoZ0iQa3tJ2ZGGYmmCaNILtuzVcIPf2K61rey7miI29j19upn6mbqok2ZNbnHvAtO5yND8RDDDgPu9OHfIkUwem8DNmXTZLOn/5b3zyNG5byMsr75AvmbErZ++PtUefFk3MptNGo8zeuk3bday1NpK+FMx9tI/ITzq5rPkKs0DyNvKBtzrK9urFmDwRquzWr7hTXVt3pbKCAI3hMa5mYWoAP5dlzrhkOa+raybbqs563+Wefgfja5YJHjTf92ZX/F3q39PH1//X3zkvoe/GSR9l5y/U28RfrGs7rXxdOawJrhZAD1nS5D6WxrmHX+jrvmDwUKvMfs0fzeTzNlMEm41t71nzP2UgTKsgsy7ocUbb+IkQp9Xfbtv2g8vn3ELWQVHrEtu3fK3WshzZ8Os+UkPfge2222j2Q/4KZPpd9mto7AsGkjWj3mXjO09yUjUqSugn59qXNY7Pc+DWBFNuyI1dDWRG48nN53WsNTTzq/MgN0eukqvMuyaSRyuvj6cPUrtAhR+9TX1fTs1OIP3Vj9Gv7yuduNfbp8KNp/VKTzGuf/R6X3SJqrUqNy6jxaIIRgAc8nmn1PcgKasmfaW76Icw1rr6+PpYBVcDoY/TevJLt37rVPSZubcvFR/YwKuezIbPe+Jw6c1TWfENmvVjTjpWutYyvXS7G27LDtRYDAwMTrpFlyFCqflX6HW8OmmiNLIYolvivwE882vwSUZ1WUnI8A11XdxO/ycpIl3lq1Z3E26OA2MC9TDrOS6E84L6amM+JU96vXzP9b+obNCGTfdmMfRo0O9fJeNWdLuGRpxlkx9qw6bMu4an34an1FWFG8pu7l3bkOV+9naGvYrQnU3/FaI6Fvs81q+7MO4ToY6sHFV2ISC1N1zQ9n0eT9oF2IFKEjHxWtitr4rUujuaujL349nXs9Fknk1ZUaM3070cXxM56apqtM2Z2zXRqvnczKIIsvna50Lo0k2CeEMa95itvuEdoWyppB1G5pi5T55YdwlSpmuvPIKVtm3SJYL5S279ZaEIFmW3bDyPKzSPCvYyUtG27ZyL5KFOZylSm3zUqmxbPLF1hWdYxoA94DPisbdsnSu3kof773BqJybH/gE8H8oTloXno2k587XLHMWwik+/F5H8At2akjmc0Dekn0i07xMnZwz+kmq54QJxKPc1eivnDNdf2qOtUbCLdrKjOWXWi581fMxt5mi19NGQvfvL49TJReZgb9XmY/lfHc0xxyok/75k03FtIY1x5wz2571Ch+NrleVo24Db/GrQAl+la+s1WdLDslnU0K+2kWU1t3wZ5Wl5e34G1ZpO7/uwY/HUSROG6nrUW+PlsTTzplhMV/OLS9rTn3rmO+E42Zzy0Zs2CYVoPuRZe5tsynR46Y3FklmXZ5PvIbgQSwAFgLvB/EaXuV9i2bYzmsywrAkSUSzVA1xWXfobfbMs+fJr9Wqc8G7eKWMy+bDryqNBGpgsu1dau9yl5NAlNU/+l+G/U+eikC+OC/kKPOahoLJNwVgWXy5yjbTamtfK7Ph4yrq1h7U1rW2iNTM+Lft20oRs3U6UPZ9NWTZTas6rPQ+/Hr3/XHNS18PA55ZnhPXyVXj7ZPL49/GOm/lSSgtvEu3p/Mc9Qsf5M6ZpwDmJZwS/71tdLfTekSTJvnqvu5McPf1z6yCYujmz3NGpKhN8PDmaYvfDIhPA1oWTb9hn5AWzg+gJt5mTbvc2nzR3ZNq6f/v5+W9LV1vtyf6/8Ut7f6ufyet417X/9M9PnxmvK+IXay35XvP+rxnH8xnXNM9vG+b3yS84c1b4LkdfY6njyet7/WvtixiyGp2LuMY1bqG9nXbJrpd+nz0kdyzhXrR8/nvO+5+x9Sz/6NXvpR79m5MG0pnm8ezx7eX0Ynv9iSH/mPJ/NLC+m9TT16bpH4U2uRTHfp9d3VcxcJMlnwsSfa276O6B8Dzo/8qe/v1/uXbX26d9rawF73+6p9rHX2kr62bd76oTxNZE/bwbTokO2be+3LKsXmAc86tHsb4GvKf/XAF0q/N7ltFfNVprW5dJgCph3XMAIw8leHdekBcjrOqCgkGanju+lNeTNU96XhXibeClExfClO9mNjngNXOOn2XqaFTWzktqH13cBOTOq10lcJR3UUAy/gEsjc621ouXE1y53AQb8ngn1/+Z7N3u2U3kx8VhI+3StexFaja55mL5rP43HD51oum66J3oii6hT47u8+MlqTqbv2/TMmbQmsiAxfT6e85Vasyk8RAl92JBZz5XW9ca5n076XQJ7vKGmRUObdqATobn9rMh+a4H+K7jOQS3q5LLRFwiI1e8xbR5+G7PTzrCp+fUr71FNcH58yT5MphN901t8u4Ba77zr1oI8eJGnYPMyZyntJQy6GHi+F1/qesvg4OZ7Nxc0fxUzlv6dmvrw4k2NAVP70ynPLFZgg1U/k+umBjn7zdPPPOo5rvJu6KSbUP3McrrZ0CgMizRhes3J65rJFCs/MyIPs+38DlVeZl5n7ooJ2bQHeLkPrrzsszz+1JdhAk2Lu3e1jsu0uHDR0QnhayJpouPIqhHalaTZlmUtBU5mfz4P/BjoQfjIvgLsBR6ZSL7KVKYylWmyUxqbdIkoxFLbv2loIu2WwBUY/FnA94AoQmAdA1LAQeCfgNbx2IMvefedOXu0h83fZKs3tvHwsYzXx+Pla/LyhZUyptPexx9SbJ+mPvLWwMPvI++/euWX7HO/8LWCPHjx6jkPg9/Bi8dSqeC6+PmlPHxNfs9Rwf6159fPx+j4jTx8MqaxvP43+llL8PEW6tPEm9+zYfId+q2LyYdo5KlAn3q/K97/1bznT1/zYtZCpSu4bsJ9ZC+8PMU+cHhqST8vvDzlrPSRveEMnK4vzQvs4UVeD7rXBuTXztSmJCFkuUEexfDq67j22UB1YT7evr3m4Nu3z6Y2njH92ufN1wBM8PrOCm2uhXh39WUCEvmAQErZ+AuR3IBXvP+rzt95PKoAhXEIiby19TkMmf7PE8A+h1A5J2M/Bv5MgmbF+7+a386nH9P3K/swUSEhLttcceln3uyCbDfwMvDnp5u/ifiZNGVc+vv7eW/9n4iLBqgvYIR+S1L9BLKNiYqBJTv9ZamQo9nLWV+MH2dcY2vQZxdUuYT5m67rsGc1f6POgwkS7QXjdvlBCvBYiE9Xf0WAUfL8Xh75LUv17+jfZyEf4Xg+A3/4fSm8qn975ev08x0X6xc0pX/y47dYX6Bz3SPn5LJb1rkANvrn4AYeAZ6+Q50/na60rudxHoIJ9JE9//KUcfnIlp53bEL4mkiaXILs2r8H3MCDQvnYJBXjaIZxbPAesS5+/fny4gGYyIvRMgBG/EAAfrwV64T3E5Rec/WdQwF+ffvyQugVEMJqu2IODTr/ptgoEwCk0OHG1LdJgBs3T5+2RmAE5D8rPsCcgoJTPTySDwRSedH5iLdHc+hOr1hI5WAqQTTLbllnzKvo+fwbQEpq/KNsox/ETOvgzNNwGHSNo/yt5FqcMEH23MutVJcoyIYGM1x43tkH9phcgiyrkXlpMH6ntEIbloNOy2a4Nmk/pr79+je1K5R9ohh0np7VxAtNpQseE9rOa4M3zdcr+4LpFGwSkl6Cq5A2Wuxa6W10/k08+P1tur/YsUrRsExlXbz68+NJrseyW9bRvCMu2ppg5+CLgvXjfzxrrt/rp5Hr/RTzt3H+Wc1Lf07yKhFgPozmvf+mAG81oYBCGzLrz4hG9szO8QmyixeffYLsTRVHVqYylalMZTo9lMYijWeOW897zkaaVIJMPVU5pUo8Tmc6eZ4ws6cxV65AQ4Z8P9+A8ZRp8LP4ao5KLTX1c9Op0XUy9KnN5PCn1NHyMoPq8zGRWvZDn4M+VzmXvHVadadxrYohld/xmCJVfpbdss5VwNJpZ8hOb+LB9P2r5KWR6msCeGoDef/rJXfA9V3LKgjbv3Wr63tweDQEz+tmQvUer3nnxWxltbtC1gr9t3FcrWaf3zpK7UptuyaQzfz/rVxMpVwXrzmBh6aqmUWdGoQyR6VHKjE4Q4U1f4cE2RuONjldCJ0ruM5WqZT0OV40HlRfoXsL3aPfb0RW+aQ/cvVXBKLMqw8d+TVe5Fwh8h3bA0Gqpy5S7/P7nv3490MreiLUlPV0hVJI/jzg2SZUXSEqlXfT516oSL3/QkhMv/t18kLimvguRIWQpn5rrv5/tfU+B8np6kdPo5VFfKpj5N1TYF28eDkTqMXNO6fZL3SeU9LP5p3TyvD7N2QCBvi9pGJfPK/4H72dq19D3I7an/G6z99e0OdCwnC8QjqvfaENTtmcS81NWcznso1fnjqvfsbDS9EbkM/3bLpuyjkprxfzbPnxWXDsEg9ZfutWrOAsth/bNhysfASTMc+hz4HCtE5+61XonfMT/uo1P6HvR2ci1+LGl9rs5w+1l/Sz8aW2s1KQTSqwh1oh2s/hr5seTNWc/QAO8pqJvEyMpTjMjf16QKhLQdAVNcY44feefWpIOb+s/C7yAL0UOybkm2rlNfV/tRSKCaDiWVB0HIAG9TOJsjNBzfPMednqA+P57k1zNwEjvObj8OkBQDEVbfV6/nU+9FJIfu+rX7Z8L5O8imRU+zCZzHVAkjS1epWOkfd4uSIAd/kiDew0Zo9OONjjty+dMy6wx1uXvDYhfE0kTSofmZ7YVz6wpnx4QB6s1vSw5vkrihBMXnyZ+l4T0Co764hCOaYHaq2Qv0pv7/xv2BgKldXQ+yhG2Ln8GR6CybjZaXBlv3EKHR68vsNCPHjW8tJ8cep1r0OTTrJ6sf49mRB7YP4+PX2HBpScHy9ewsbFp8Fvtyaw1vGFFbPZ6+NsfuBTnjUC9fnH26PGXJN+PrLmHXGjcNWFirPmWhJsl8/Xq9SQ/s4r30msa9jTn3ZmfGQB0pQmyIy1s84CmlSCrExlKlOZyiTIti0ydmngDbvE9m8WmjSC7Lq6m1zZ71VTgaN5PZD7zAv5ZTIN+SHLvJB9LvIoxCfvMWkB6nWdXy/ePE2lRZS98DKJ6Wg2T5ORouF5ouq08XQtRj/pFmvC1NsbzYRae0/SAnn1e7y0P1Mbr2ulmmf9nis/ytMwDOvq9Wx5mdnVfsCNRvWzFJj40E38TgVnBRkqyTFdrujItdf5lBq8HMtDM80rcOulTUuzb5EanPzMeQ89zJg6mnKi6HcJtTipfGRqQDQUtmGbqJBvy2+T9Nrg/Pp39WEof+F3nz4vL/+WLuCMPPn4pPyEdSFB7lfF14uK9Ul49aWvp5d/x3VNF/Ae30Wxfj5fs7MhrZF6n9+8Ch2wnLGK9DEWm/JLH9MrSNjr/XEOlvibir2C872EsJ5+Tm+rByUX8/44fXgENAO+SQTy+DY8M2ciIPrhF2YTK9FHFh/McO0FByaErwmlNxptcroQOir8XkcVlUJeKDEvaG8xqEE/lJcfEsvUp984pjmcDjKiuwrwVyrSsND1M0FeaDa/dTfNU6Lu/JJAeyHz1DaFrhWq7Oz7mSE0w5WQt8D747cuprHUMb0Qf4UqLHuN7ZV4uNiq1MXOy+u7VturcH09wbH6cyZQiw+/MNt+4sDckn4efmH2WYlanDSmxYf673P+1k0XpZBX+zxghGY6Au20rlWh9gq69Bsv72SeDYrW7zc6nA0pqor525lLoVN99pTqZ5I0UZ75Rx+zRPLTKPJO8CW0dZEBVOF1v18/ujnZU0POVpU2jWnSbLxAMXnPRoHvMwY58MWWHTmzm4/2pZsFfcf0SdrtjOnzDHhpeybQ0prAWhdgyFRhXe3L6/8887zB9K+2jWl9uL6vM2xazGCRKRHskTlL65FNKtOiCr+X5LVJ66aDUgVesVSSf8bj3mI3RlO1Wk8zXQnwfE9BZ+DNaNIp0myp9mdK9uznnyrEk6vvIvxVxX5vRtOyV3UB9ftS4Ot6dQA//guZtvXrav/OMyL9PpJKSNRsWkuvsfV18TILe2XQ18m0tnqiX6/7vQ4xMou/Cyqvz8cn8XjBg6VHlYcfn/rOhCcN/tkLc4nVBEu6Nz6Y5l0X7JsQviaSShPXZSpTmcpUprOC0nZgXD9ZesqyrJcty/rzN3IOxdKk0shMZVyKpWLbFwIcGE9ohtgw9R5T32sCuRxweuyMfo9XfyYe80ABPvcZ+9KQXIW0Gc+TrQeCU/5frLZl5NHHzFdIA1MDfD379wmU9QU7ZMnrM6/552neSj9e2erV/vR+vOpx6XP0qvJQjAlVNaOZ1tKkkUkNVVaYMPGngzJcoBxds/PQpFx/a9+lXt7FWS/Jh/a961UxXO0V87665r03r6T+27+dcLDHj3ecOy6N7L0dr04IXxNJk0qQmUyL4G3+UR88v9pHXkXzgLwH38934pedQO+7YF8K6eap00kmP1OhoqV+fZmo0LyLobxaUsom5LWZqWP7CRx9DqVcN5EuUIoSzqb6cnITLnBQMq27yYTrjAN5sHPTOhUjyEzXdCEWb4867VSYfaFMHnn9GhCKRZublbWEXEHYYkypXuvit1Znoh7Z+h0LqSpRkCUG06zt2D0hfE0kTRpBdgXXEbIqxMUioMfF+ED8XhyvjQXyYdWePoIVHf6F+wy+Az+eC73opZBJgKm86Pz4CfhCfBTStjyFh36aHoeGqY/hpTmZrpn8IXnfVRHVpPPi/wpUSM57zgwallfl4kLPtMn/lPccKILCGAOmx2n51dfzK0ZaRDaNQt+RV1ygOpY6F6P26AXN90gt1r06BkDb3Zs9DxNnwkd2//PnjUuQ3bj05QnhayJp0ggyVSPzezjHs7GXugmPp71+zY+HYk+JpfLit6n43X86ePHly8PU5sW7X65BrzH0+/Rxi9Imi6jM7PTloY3pRVGNfGc3Z/UQ5GdG0/k1mtY84v1M83TxaxDYhaiQyU8FYEBOSPoBMsA7FZ0+n2I0NX1OeTFl2vdnErJqHk8dXHMmci3+LgmySQO/L1OZylSmMuUoQ6AMvz9bqBjTopdZzM8s4Xdd9llMxgovJ7MfqWZHwJid3XRP0ZpXEaa48WTkKJkvn/gkv3H8qhbIfgsBUYqdc+/NK2m+d3N+lnePE7nf/HXfkNEHpPhkvbS9QjFNqvaimuiKMbf7aaguPpWxvO737buAudbTB+UTNlLI2uHVrx53qbb3+551rdWlgWlj6trkmdDIvr/9/HFpZB9c9uKE8DWRNGkEmZ6iqhgnbzFmMK8XMM9E43fdB0xSykvnRQWFXAn+qmL79LrH2YhPY4yeNDUVMn0Wu36qqaeY6sueG7oiXEzxYJIX4/jgiR70E4pqn7IScyEzqolv0zrmzaGEcjB+vBeaj0OK0FBdAn5C0Ot71MlowiX/nSgU/+jlv/R6VuS6xtZvdR1Axi5ZwONPfRkmUJB9b3vHuATZh5btmBC+JpImjWnxujVf4TeFTsdKgtA8u7VG8n795XSdcJUxivnbNIbet4vfIv0Usq2XUDS95H5BnsWQSatzbWw62q1E/5tKuhDzEhKmdffa3IvNK6lvcF736ZuuaYNzkSLwC30/khxoujKm096H77zvWc2gUQA56fUMmp5ZT42qwHvmfJ8KMCW2fitrutzJqgu9J35ZYwrSig7zM6qGm2R5XPDFdbzyuVtd7eJrl5vfwRUdOSGmvBMCtfjl0vksgTJ2gIxdomnxLFVsJq1GZiIT8EOlYs0i+mfyXr/Nww9I4DWel6mkFHOOWrxQ/l3KPMcj5IohL02q2HuK5c3TDFaEua2QJlZIk5djepoRwTMLCGjgBQ/zlyTddKV/buJNb+ebwssDQavHOvodqLyoWNO/37NZTDJwk3mwEC27ZR3N927OG8frey4m/i0nyCYWtfjPz100Lo3sTy98dkL4mkj6nRBkrtNwEYGj6mfG/gq8nL7Z1UuE1Mv+VKh1nv9P2+B8efPoo5C2VEioFrs56P14mvNK6NtLAMtxvMIiJBU6NOj9e8G09bFN/amkCgFjWwWdaELrFfrunT48kJTq3E0arH6P71w98nvKNqW+Q662hSD8uoA2+BkLhTR4zcchj8z9vvuEj9XjTGS//10SZJPGtFimMpWpTGXKUQZIl1goMzMxrEw4TRqN7Aqucwprmk7d4B3r5GdSc53Q8D6RqWa7iTLHgfmUZ+S/wCnW2HcRGl0x7f20KS+NyK//YkywRk3KBxlYKKuLHy8mE5LKpymwWNfg1IwWun/NZAL01Bp94s78NCG9X9O7oWe7cO7Jzk2CTYCikH1eGqiJb309/RIb562JxzPu+u61WDxT6qtCFSRM/ReyHEhez4Rp8dvPXUK0ujRdZXhojI9e+PSE8DWRNGk0Mr2MiyQv9d7Pv6F/bvIrmMbiAbdJSO83b8Mt0m+mvgCF/AB5PCsb9cob7mGzskHpAad+/RoFZRGbh37NtLEWEqDFrL3puzPm4DNkT1fXST249HbEaN4R9zRH6xuc9FPF1y53jZkXFCtzCkpz4QPu+ThCRN3Ilc/V8AN1LqYDgy5Ejc+ymv1CN4X7+Kc2+whPkw/QKLAM1cu9zJzymldJJOM66NlBFMAXAAaQRt7YBrCKn09SFfwmc/aaVXfy44c/7juH00FaEuCi7zkbadIIsuvqbnI0MpW8ctCpQsRPuPl9ppLrZVBQYbpA1Hkrqj8PUl9IdVMwOaMhd/KXn2+W/T+Q35/Ohy5sTD4+Pw3KS4j7HRL0efqth5cG47Xmsu3mzHrnAGLiMa/kCRjrwrGig+GmgLOmeYJE0QJV9OGGzHqW3bIOgOZ7N7u61K0BLp61dl5r42gbmJ83P63exItL2HoIIrUd5AtiSbrA1sdyPc+Kn7igYEZ5vgocFFUriovkmhs0tTWr7iSmPReutS2QkBlErsWJJlGPrFTTYmnt3yw0eUyLl36G32xzm0AKnSpNbb0+k1SsyW08pkWv077er8n04hdYbOK/WC3Iiwc//vX7VJOO0QRYpLlx2S3r2P6tW/OuQ775SR8X8MyFqJ7Wi0l+7OpbpyKDll18mrQGDxi4lwnRxLMTf1eEgPeao5clwRRe4Zq/SobE275akEfuyDwAh48Fw8i3z3WdCn0PDp+STM9Y1nysxvpJOhOmxXXPrByXafHWizdPCF8TSZNGI3tow6edv70e9mJeYNNm7PXCeQlJ00vi92KZ7itGO/Ta0PS+vfqSm4/XC25aN2nW8Zv3mlV3Fif8tcq5KpnWqhlAEWSuOXpkIXF9/8p8TUVITdqX6fCwZtWdLh8LuP1calaWmOxHuUeO4ymQDJk9vExUulVB5dmUEUbyoZvOCqHxVF5VU7UkNVt83vPvIdx0H5zzfZkQvR7Vo9Wg8LxnUtMW1fm4rhsEp2mtQdPoTSZnbR3lmpR6GD4dlCZAusQUVaW2f7PQ2cl1mcpUpjKVqUxZmjymRQ216KUVqZ+/XpOjX/tCZhTjvUUEW74ek1CpZNJmjKUr8NdaSyFT6RAvniRfpgzlGzKGygfZNXQBLRQqZT6SD1UrkYHLvR0xoicEkNll2tOQr17oR318o1ZFvu/IpKl7aVYOGQKy9c9NPOs+Mv25LcZc7dmuUHBzAVNsqZYXyZPXvmFK3aVr7xI8ZUrx5YoDzY51JkyLX3n6LeMyLX76kicnhK+JpEljWlRJ9x3pD7WnyVDbFE33mjYO5zODOa9YoQrkmU8K+UCcjcPjxffjz69f9TOnryICuKUPq1Q/mrrRb970WQd8YuI7r19VEGj+qBiINEfq9VV3ukEZ2U2xtyOWZ5pVxzPxCjigDWlK7O2I0XzvZnpvXumsSVQKziwfju9EWxvJX7w9yppADp2ngzvUQpTO924wVZrWq5AZ19NvJUmaRT1Qq7K9nwCVbf2EkMpT3uHG4HfMSwEmedDMuV6mWNP9aru8g5xmjlwTWOtCBOetmdbXmUAtZsZhWiw1W/6bhSaNRuZXIdqL/DbyYrI3FKvVlUqmE5w+tiTXyVh7wf0EoVeOv9OhwRXjl/Q6CDj8+2Qb0TcV44aoaA5qOXqZJaP7NiFodt51qyM01MSuus9HF2Amf5qrqrAG9tCBJiatsPfmlTTviOf7wzyyc+jrpvv9vA4dJk3KmYOS5V9dc9d4BTLBmJ49Ex9gjkXT78mr66WthTFOz+P91IWi/FxWOfDSEL1izPLa+lgM1LCJM6GR/d+nrqSyRI1sZGiM/3PpbyaEr4mkSaORXbfmK3moRfB28hYiPyHmIg0aXexYfoKjlJxx6j15m58fLx5Z1wuRl1bHio6cOc+gEej3eWmGXk7zlTfck9NgNOEgN5q8+J1Vd7Jm1Z1Cy5PjrF0OKzpo2xjP9buiQ2ymyiYZy2odUvtQ1y2+djmsXU7/rACJdmFCPPAXohDkyhvuEWNkSZ7S1fV2Nub17vXWN1IvU7jRLFZAo3Duy35PLlIQgXnPvQYM2ZAxxzKqBxhd8HtZMACjUNH51tdAn1PMIxzC9K5szqxnTdedeQATfe1dWqoKSFGeJf3A4vUuy77Uw0H/9Uvz2p5uSmORLhFOr7R/yrKsDPBN27a/ebp5O900oYLMsqzLgduAi4BpwLttOxfsZVmWBXwB+FOgHtgEfNS27T2ljqWiFgHzS4X2gOobRQnZMNSH3NWH4STo8itoL5BrnAK+AXmfc7JT5uEVj6NrMEYhlO2jGEGvbyb6PbH1W3OB4Yb2hcxf6vegtpUbv1GbyG7Osr3Utno7YqRq3POMrd9K5x0rqeoR/8uAZye2S4fUZz87dtcKAGY/mGC4KUCqRpSyP5C9Pusfv4q12mLe/cPO2GD+TuUa6VkmvPLy6Wtd7HOrBw4bNSYN+ahrZ65DQJbynu0s79Kc6uIhayb1015MfRdqZyLX/LJ8OzF6etsCgeTg7a/10rhNQtbrIBf76dO+czkdNL7s9077S88mjWyiDaIxYAfw5x6ffxr4OHAzcBkQBx6xLKtygvkqU5nKVKYyTRKaUI3Mtu2HgYcBhPKVo6w29pfAnbZtP5S9dhNwFLgeuH+843qdaL1Ohg75IMh0TcLPR+Z3EtNP3ap9Xz9Ve2kxamojNYOB2s4r04DLn1JC8K+XBuVqp2iFeVqWoiEXIpND3ulHMaGpvib1et3BjDAXyXlmqfu2lSTaM9jhNOmoOMM161+57gvJZuwgWwL+wPVVRHoRJsXH2hl7RZgWI0eDhIS1knh71AncltpznvZt0CRd2rqiKS27ZV1eqiynH017Vdcttn4rK7nHmF3fRDqPqo/QyyKhAliiWRCK6fn3smp4mRNd7Vd05JmsHX4V06XJx+oE0KuB9IaYMa9nzXPN/HJtFmGNUHxkE0ZpGIdp8eykMwb2sCzLRjEtWpY1B9gHLLNt+3ml3W+B523b/oRHPxEgolyqAbqKBXv4petxtfOyyRd5v1+f+t9+7dRrUBh1VtJnKozbRyCbIO6l+PH8eNOhzepnLlLMcLrzPC8J7ao7HQj8sYstmJkQfRyqYqw2Q+Ro0G1alGugJPI9sThA086MkzvxxGIh+FJzRwjvqySyrI+BEzGsCiHIgt0RgsOWI8zqDrrh9yYTr8nXJQ82sg6Wa16G9TKa3bIB2V5hDF7+XN2X52eGVsfWeYGcSc+UicULaORLBcrR6GAauSYm8Io+dy8ksiooVaCGaW9QD1Wu9STff60JsgkDe3x269uprK4o6d6RoVHuXP6rCeFrIumNFGQrET6xNtu2jyjtfgTYtm3f4NHPHcDn9et+gsxPCEw06aczSX68ePoUfHxoRuFXCF3m4TvzmkMxvOeN4XMQ8EKGqtoq4Eb3KRqWTP8j5yB9NE7OwhUd7L0liD0qhND5c7vYdaSV2V/P+bCad8QdyLy6WXbftpLwII4wTLclAQhWpFk07SiLans4NVrFhi0XAFDVFaBtY5zOa2LMeCTum29P3+D0E3tee20NTZuqaf38tLVi3olintdiLRLFHM6KQdK6DlUFLCw6/8Ue3Ar2Y/ARyn5d9/mgj8+EIPvrLb83LkH2tyt+OSF8TSSdjYLMUyN777V/DxSnLfidJv3I7+Uute9itSz1ZKjfV2jMYgWcH0/Fro0X+fGiZhH3Oh07zvUtOxwBA0LISI1puCngSrrbfdtKks02Yy2jvH3JywCEAmke3rWYeR98zigQdcHIig66V8cYi0Hj8qMALJ9ykCnhASqsNP+yaxUjx6tE3wMBpjxjCz52xF2a3Yw7BF+OoM1qgfH2qNNekl+qLc8SJD7fsb7xq+ssxzNpdV5CR88lWEwgspcZ3i+GrNDzbqJiD6ylCFo/a4bfITFvHA35+uNT35lwQfZXW64lUqIgSw6N8v9WPDwhfE0kvZHw+6xxh1bgiHK9FXje6ybbtpNAUv4vfW/X1d1EyBJfmt8DqNrdjdcLkF87+Vmh06na3sus4tpsDPZ7vY9iTI7GjRHciEqPbOamPsCt1Zl4LSQEdfi1aT4qorDuYCZn5qsJcCKLQNz+rVtZc29OYCSbbaY8Y3PsvaP86tnzAbBSFlVdAZcwTNXkzICAy2x5ZDVAhuCIRd+QEFg/7V7Grcs38J09K0m+FqNtY3YeXQk6r4nxyududa1LrCvHv8z2IddLD8qOt0dzJkX1e1DXWN/gH8j/LtSs7yp0XP1OdHIJSu36hsx617Niaiv7zBOKWT+j7uOSfXjli3QJCWXOKhIz73nRnl2TGVb3S6pjuN4JPA6YSnYYXZgVY8aV7c5E9vvfpTIubyTXBxDC7G3yQvYkcRmw5Y1iqkxlKlOZJgNlbGtcP2cjTahp0bKsamBe9t/twCeB3wAnbdvutCzrduCvgD9CCLYvARcA59m2PVLkGOPP7PE6gBt+fZRi/jDZ3wtpQfr4fiYkX96LNG2arnvNwzQvdW6muRpNpQrwwKks3DXM3luCBCsEtirybIz4nLTLrAfC5HhicYBQHOJz0sT2B51xx2I4GhzAgi+uIxSH8GAupsyhFR10XhMjFIdks3hPxlpGmTX9OAf3TiVyNCj8YUD36hhtG+MOyEKl7ttW0nb3ZpdWo2fPl+SAEjx8QaYMJsUAl+T65vXn8Qz4PcOqb9PkZ/WzQpj6L9Z3rM9HDYg3aZ56ILOXdlTseujX9f70bC15lgaFlzPhI/vUpt8fl2nxnlX/NSF8TSRNtCC7AiG4dPo327Y/pAREfwQREL0RuMW27VdLGCMvabBOhR5CP6FTinNcv0f9v1hHslc/pZCfSVEfU14vxuZf7NjqWL58ZVGC+uYtN8rFtwvkmxQQw00BBmfbBIfFqTHVkGHe/cK3dexii0ivuJ5ozxDuE0KtqkeYDyXtvOtWY8qh7tUxB9whabgpwKlFwrQ41jIKQKhqlMizMZLNNjUHLJe/K9Y17KoqLfuWJkeJ5JO+PblOuumwtyPm5KyUfXgm6i0BAFToeXYJKI8Di3OvIdmw1wHHZPosxK/pGdWvm0zSXuQ1Fy8qmLhYE05AHmjKL83dldb1PM5DMIGC7C83vWtcguzvVv1sQviaSJroOLLHwTuQwRZS9HPZn9dFD/Xf5/lZMQLC76XX+9DvUz/32ij8fHZeJ0UTL8XwrwsLtdqtmghZ92uUSl73efGubyZSe1nTpcSGZVNKLbtlHW07FG3n7s10/+vFhI5XOBD3dFQ8WrGuYWZ3wZ6bRBy9Cq+PnsjQfK8QGr03r3QLB3AEjhSWkvpnCRRiqiYGQGiucMuO7aum7mCGfgJET2Rc90gkpIu27OCVTdk0SMr6uNJTaYlomzEU7MRjw1biuEy5NvPW3wegEVu/1cWXr69ZA+Q4ffsJFMlrEc+b3+fFvmO+wtBUFLOI8fMOQYZirvLvPP+c0vdD/fdNeBzZeEyFZ6tpcdLkWvQj9YE3mbTkZ67TbgHBpbfxEnyeL5OHk9uLN68x1Xl5kdfGZeLR7wSu9lWs8JMbnFMpV5n/5k2fdWWnV/NWRhWnfngQ9n59OdYgjjYGEOm1XMi/hh3ChLj9W7c6JsPmHbm0Uyos3xFAijkoplyvO5iht0MgFkNx2P0ecdZadss6jqy2qd8lNv4DSuoqEIK59+aVRNuz5tD1W1nwxXU0ZXMzutY7C4KQ4q97dYydmzwSFCvfRbFmQNN1r2dOXtOfV9Pz4GUWNgkEPU2WiTfX81fIVKqBMbyEps6fK/GAj6bptbamcbz41k2fKr/y8x+f+o73HE8TZQiUnM3+bM1+/zshyMpUpjKV6XeN0rZFukQNq9T2bxaaVILMBBqQ/6tU6LpXf359m05+et+6ScjkBPbTvvw0NT9+/eao35/nd/BIRqyHL8haZPr6ONpYFmbvcr5L2Hn21C7BGs10OHFdAIOzbead38Xhkw2EZ41R/QNhkpEaTvO9m+m8Y2UO+h5YS5PUBExpx7bscNcCU4AXxy4WL3LNAfG7aacAjkheo+1R2BUgMRX2fv9Cgt2iCxlvFuty1ynrvGOlAwiJdeWG3JBZz+Lb19F2dy7ruvShOeutZdnwSnelmwz156oY35DXd20ir3fLZEI2VULw6ssL4CLfKdNz59en6r9yEjV7zUkzi+rPsdeYujVDHTduSNkl7z8T8PvfJdPipK5H9noAE16kv2A6Qs1khiiWB5lTr6AT/zSgLY39mkytHn/nCTc1w3/AnRpIjb2RQt6pQ6XV9ZIv/5HVUDOrH4BYJMX5jUd4tb+FQy9PY9rG3LhSmLXdnQuG7r15pRssoc7JVFtKGxvIC2yW37PMrA+QvCjOWJ/wy4UGAo7w2/6tW3NAlbs35wK2lXRYcs1UsMvKG+5huCkgeNdABJJ/15qr81PjunQ0nwewA9zfj+vZ9Qh81j8v5lk3+Z9NNb1UEEnemDrgBX/EYbEmWD90KFAwQ4tX9Qt9PvqYP3744xOOWvyzJ947LrDHP17+4wnhayJp0ggyHbXo9YCPh4rpq5DQ9Pu8UMqiQnb8UqmYPrx8GJIKbSIqyYBgNXOGmttQrbIsi14mLhhhyQyh7lRXJOkdidH5xAzSUZu9t33SGdMlMFXfUjZllSsImWymjUfirsBniTYEXPkNF9++zpVFBHCQk1OesTmyGkeoytyMgBGCLQWH/Lz7tpW0bYyz98ao04cUKiah4QhUmXkE9/OiaitqCICfdg7ePikXpF09bCjCxGgxKBL96ndI0nn1e+fk2mx+4FN5qbtM/RTz3ANuwemRg9JzDbSxTWtyJuD3H/ntWsIlCrLU0Cj/9Nb1E8LXRNKkMS0Wi1oslfxAHF6nT9OYXmbBvH4UwEMhs0axPJv6yHsJfbIUFBLQee007UCmkVI3m5U33EMsa+JTUzfF1y4neVGc5TM6mR7tA+CXnYtIjYYcQZG3UQTWsmZ9/knYpJXBctemJLKERGm+V2hOcv0XfHEdTQczLsEBwjzYvEMICztsM9wkACahOI42tawpl/BXboLDN69kcLY4NE5hOXUHBeLxwF98ijX3KyZAtUikqYqzItTkNeez7Lxk8Uiv2Cmv59CrXTHPoSrE9AOGiVwxVwZzodfzqJs11wTWEgPWrF/rmIvVZ8FFhndLXwv9umldIGeKNF13/s6O45XvcqLpdRbWPKto0ggy8EbxjcfU5zyEHqdAr1OpKXWPl1AwCRxT7jtPTc7Dv1CsZljMy1X0qTOwNtdWhydnN5DFt69DAo5j67fm0IRKLNaJxQFuPv9Jftt7LqdCIi3U4ECU8L5KYuuFcDAVjHSZ4rLfge6zUDcU+XuGco9j6gRmkNNAZGyXJCmQYvtz+R17b15J872bWZZt03mHEM4zHok7muGpReKzYxdbTgC3+h303rzSEeYqL3qgryMcHvD5DpX5q9qg1wFG1+q8MvR79aOSbsKUFZzV647P1MdMXcx4flqPF++uZ0J9frV3yM+8b7ou17o/a37eedeteYJX0nV1Nxn7PZ2UsUv3eWXOUgPdpBJkZSpTmcpUJkGvs0L0WUWTSpD5OsOVNsWk9fFqV0hTkn4Fr7FdpJlU9HZ+tvi8/rbsKC5dlkecnJ8fwzSm7vvZrJ/elZN9zg8WdcAZKFqHalrsvraCYykB2pHJfmP7g8IUlzVHOX0ofKs1o2KKNmHyOUnNR107PR2W9LPItqcWCbPmvPuHgZgDBJHtm3fEYUWHU/ZFAj86r4mRbE3Tp6zr7PuHc/4nRYOPnsi4/FJOai5Fe3WtudTM1Li4LKnPqVqIVSbqNRZblWuB+RmUY3n5ydTvQ7bXi2GChhA0vAP6O+TnX3PdY3hGi/WVeb7LJVpzYl3DbH5A83Ea7jsjAdFYZEo0FZba/s1Ckwbs0d/fz3vr/8S5rjppTQLBy2TmRYXMfF7tVSrGXFgKvV6edSi8vhk4ZlQPMIAJBKCPrULrE1PJASI0IQaQmCrKpfQNVWG/VONk8FDTQXVeE3OBKlTTkiQp1HTIP8DeG6PM+0TuvsW3r6Ntoxv8IfmNnsg4Ak3OQ5oFj6yG+l05gdp872Ynq35fR5rIUeE7a1x+lHgyzMCJGLFdYUAEeCemwow7Nufl51OBKlLYyrRXB66vygZe5+bp9wzkpQAzAEM8cxVq742RNDN6KSZt3Z8pxzT1YwKDmP7Xg/b1e1UYv5d53XgYVAW/itbUKxEY5qHfK/s+E2CPP3zsDwlXh0u6NzWU4odX/XBC+JpImpSC7HQAInRSizz6bRxednr9BKsLWS8eTVSSMPUQRKWSaR7qfBffvo6dd93qagtCkEkNqk4BTzgZOZSSJd2rYyQuGBFJgQ9VObkTIZvU997N+ZucCh1X4nekcHD8TcqYiak4sV2ykrSacBhyWtCGTZ91oRcTU3ElGVbRhJ3XxKjqgVOLMkTOEf3PbznOS8/PYt75XXQ/PCO3DtkMIKpmqCI4JV+QQ0TK/JOSF1ASHWsAGyBPE5Vk8pHplLeuWvorP+FTil/VJIyKrZVXkg/ZNJZCJguMn5D0motr/FV35oq2anyWBdnppUkjyK649DP8ZtudeZ/LQF2VvMwN+rVSyMv8V+jF1F/w8WQzN43v174UMEneOKqpTvlbDQRXN9vt37o1V2NLIx2IIGHwUrAkprrbz3gk7uRdlPdLbUnC6nVSBYIUTr0dMSeRcHxOmvn3ZQstaBqi5D16IuMSMKkaER/WecdKkq0iE3/bYxbdV9nUtg2QGA4TCokxZeHNyNGgo2E6MW9aoUzVrLj368uxa8YAsAZD0JgivK+Spp05oasnJ3bW1aPwJeRryl6oQv2eUqwausZnamvqW+UPPMIFfISTau42FRwtJjTApP2pfxs1aHAdJnRt0yT8zoQgu/HRD4xLkN3/th9MCF8TSZNHkPlkvx8vFaO1mWLAink55P9efRpPyUUKINN9pvalbBpe10wvePdtK13FKo+shnmf2JqvNWQFhxRYcpOWJj0ZVByfk6btMSsHb1eyyJtINWPG1m91EITpqE2k16Lt7s2OwJI+reCwxYxHtABoQzzasYst0pW2k10/HRXvT6TXEkJxwWu0VQ3wxB5RvSjYHSFdaTNtI3kboJMpX5Lip+ufFXCtoQyolpnxQQvI9wiIzhOUPr5bLyGhft96hnyv+DK/w6J+3USegs9LO/Sap8H0bXqG5fNbyqHONSdDILfkVzXvSjoT2e/f/+gHCcdKFGTxFD962/cnhK+JpEkF9ihTmcpUpjIJsscB9rDLYI83hlw+smv/HnCbaFRNoRj0k/qZySFdKH2UibxOt5LyUGgefXjNwe9asSYd45iaGRHyneBqfJUsaDnjkbhz3fFHaXFBeqwUiNirpp0ZJwuIzHsYHLaYtuo1AE4mqhjoFqhGWVBTmv26V4sxdcCFCg7Z8+3LsKpH4aQ4qVZ1BUg2ZzW1jRqfChpQ8iL9duFBEU8WmjsEQHK4gnnnHKOtaoCtv1zilJFJ1YgSMYARGSm1S7l+3VfZzP/oNnrVAOrsHKU2Jp8XWWpGBR/I78jLZyP58DJLe/l0Xf14tDd9biKTr1jvoxjye690/5QkXx+rQWMsxiqhk+NP7xr23CfOhEb23l//ERUlamSj8RQ/vvrfJoSviaRJJciKzbVoNI95ofPG8SCXco8JhVWsOa8oP5fHRlHsHDzNMNmXVB1/2S3rqLz+KCe3tjq+o/kf3eag+aTJUOdP9bMNNwVI1YhKzpKqL+nlHe0vM6/yKBVWmi/88EZACKj+WQGn7+6rxLPcNKOPJU09bPrtYtdYY7UZYvuDxOekqW0T7+jgwToHfSjNjCDKsvR2xBzYvUNZX1V6YZzg7hjnXrlfXI4k6E7Usve1KdRvqnSZImsOWC4/myQdaAJC8IUH3QJQVp+WwBNHMEKeqVaSF7DBJUCy9+t+JPARhgXM24XM4ur/eXwaUIcOTz7AKC8wi59vT29fCEhiFHIeeRpVvj0F2WWf5fGnvgwTKMjeveGPxyXIfrrmuxPC10TSpBZkUDw6sZiN3URFaUiGWCYvIVEIgFIKqMOL90IanKldIV5m/eNXIZLmsyv/i4d7z2fHJuEjMvmkIJvz8I7N+XkEt+wQuRbbc8i/6Y19/O+ZjwCwcWgBLw9OA+DI1+c6vqO9N0ZZsvQgADe1bWZD3xKe/telrurQ8UUpSAYJDQQYqxV8tD1mcexiS8DasyALEJqa1Oys6lFqaoUQGjwoYn8+8rZHaQkNckmlGPPf+5bz0EMrSTVkXLB8yMbHZbPjg0A9qkJK0ljMjaZU4fcqYElPaKuDhFTfmYraNCLyDGAEE+mbtxGo5KOpFZuDUb1ejHAZr+bk8u0aNCf9IFfsgdHTP6jF7o3ZoxOukV33qw+PS5A99PZ/nRC+JpImvY/MUwsyFL3zEiy62SavL49x1M9N/JQC1hiPBqiPI68V83Lq62HqX0X4NewIsvCmV3lr1T5STSGea5sOQNuDaeJrl7uKWgqKOmPEFMTd3q8vp34XtN0/zIHrqwHYc7yKv02/g4pgmqFUhCPdDQDM7xqmf1aMvTdGoTHFda3PA7A43MNf7383ZE1z0vxnDVcQrBolXR10PAH9syqJ9AqBEu5YCQgBF5+TpmVeD3OiCXb2TGXghBA4DbsCLLxpFzPDJ1ga6eLvjl4NwNYjM0lHbebdP+xCSkptSw092LDps8y7+2sEhy0HLAKQrsz9nZgKZPe9wdl27jtT4+UyAvUp81aqISJyrfXqDOq9RtLRhj4Z9NX/9dyDeQImmzLLGSMLzvB7tvOua++snqpM59FPmzQd3PwOcbqbIU/T8kkqbJrjldb1xjmXaXw0aTUyPw2ikPDRaTynPa9x/bQc/XM9m3exmpRfn2rf+kndzyzk5X+RG2tvR4z0tX2kRkNMb+xjz0EBRYx0hh3Ny1SyxeUnW9FB5zUxZtwhNLhTqwQsPtgdYaw2Q+Ro0IUslAjH7mvHmNbWx/+Z9wsAvtezmh2b5hHptRiL5ZCFYy2jWBUZ7KEKYvuF/yzRniE4IlCL1pJBBy7/9oteZHbVcZ45NYsTw1V0nagH4Obzn6St4hSPn1rIs8fbGXm8GciPkVOFiYTsJ5sFH8Fhi2RrGitlYdeMOYHSY7EcclOF1qt+XrUUjsks7fUMOJTlR2p4xTzHxWZ/B0XzMKEFDTkv8/guIlzFk88iDpXFmOBVvvw0TJO5M+/d8Gjz41PfmXD4/Tt/9Sfj0sh+/vbvALyCONV907btb55O/iaCJr1GVqYylalMv4v0OgtrXlo2Lb4BdF3dTYSsCud/L3OZ12cmkqcr3datVnI2mSNM5hf9tFyM704FRpg0Ol/ntZbdW2+n58Dz8o/oaEWpnTlrk72+7JZ1JHbXk25L0v3wDKx2YVpr2plxeFADo2Wxydh6t5amBjXXbxJFK2V6pqadGVeKKifQeVeYI8lm7ki/E4ATR2uxKm3ii0axBkNOva9jF1cQHLZcPiq+fILDJxu4fMY+NryykA+u3ARAXSjBNdU7uTh6gCeGFrI31gJAVSDFN/ZfSc8rLY4fDYR2ONwUc0Aa0uwqwRs6eKUaOHmymoZNla41ia3fKrKnexR0XBNYy5qurHlRq8UVU9quCaw1gz2UnJSyD0n6s+w8O5pW4dRwu3llQf+rPrY6bp7mVWQWGk8+DXkbC/nqHGuD5t/yNJXK9z+rVfr5Fb0qCGzIlCtEn26aVKZFPdeiJJMZw9fEQL4vrBD52cOLuUflT3fej8ckWkqIgJ8JRe0P3GZIdYNbecM99M8KsPOuW11mSyAvG4dsr2baALHp1x3MN60BHLhrhfO36kuatlEEXAPYYVleJUjighEi0VHG9lU77au6hL9K5joEeOs7nucvWh/lsfhCXklMJT4WAeCaxpe4pPIwu1PNHB5t4tETogbLcwemO6bO+R/d5vAVHLbyUJQgeAv3BUg1ZJh3fhcAyxq6+NH2i4ntCot1MWSHUEEwjqDS/V3ZNnpdL980aR5pmDx9yeQfxKRvzuR/K+Yd8AKILL59HW1356chc+4rgXevcf1Mk148qkHgkg8g77AhKc9HZjAxnonMHtc8/JFxmRYfufafJoSviaRJJcikj6yQg1qnUn1gxfTjdVLzExhePg/TqU7vy68fPz79rvvBnvWXWUXHqYJL8uCketI23e7VMcd3JJGD8jMp4E6tGqF+U6Wj3Ug034HrqwgOixOkhPsD1LYNUBFK0/9SE+m2pBMzZodtIkeDpBfGeee5LwFwS/MTvJhsZevQPH6273wun7EPgPc2PQ1Az1g99x64nJNbWwGhYZ5YLATTtI1w7L1izmOJCiprk8SiSYaebsZaIlS1keNV1LYN8Lbpr1IdTALw5LG5HOppwh6qoO0xy5WLUuZV1LNMLLtlXZ5wl8+F6jeT36PaRv3OnITK8qDhk/HCq7/x+If92sn+9ZjP8R4q/cb1bF8gwbgk12GziDG82p4J+P2aX/zZuATZhnf844TwNZE0aQTZFVxHaOXFQO7BzztJFfnggT/k3e8Ep99biIrVnIpJW+W3ufjxpTro87J+Q57D3tECtNglHWIPuDZMcCPNhpsCDM62nZIngAOKmPKM7Yrp6rwmRnJGCmswRLBV9Jk+GiU4IuK00tfmCqVUhNLEhyM0VCc4vmMKU54Rz7iM6Tq1KMPM844AsKypiwd3dmAPVRA5GmTJ1XsAaK0cIBIY46fbLsaqHiUSHXX6D1eMURFKc1FLF6/2C5NjMh3iSHcDkc4wqbkjTvuRgQjzZ/Vw5+wH+a+BpQA8f6qdXVtnw8wEY32VhAZycH2Z5V9dMy/gAZCXjV39vmSeUT2rvfo9SCCRTnljas+CapLz5dFgtsu7r0iBVYpg84P7e8ZWahUU9AOx2t4PuGWap37vmYDf/y4JsknjI3uo/76cRpZ9yPTgW9dLVkJW+GJOmEWZ+4ow4XmO4WHGUMc3+bNUH4Iu9PL8B/qGJoWbxkusa5gNmfUi4/2m3L2qxiCF2nBTjMRUeGVTFmqvaG3pywZJvxYjesItaCqvOMFfv/fn/NNrbxV9dcSwhjI0RZP81Vt+yaGUQAq+OKudbV0zqbtwgJpw0oHfV1hpvtu5kmQ65FRiBoj0Qt+lKaa19XEyIdCJD/Z0UPVCJcmL4qRSUXY/NB+A57I+PqsxxZ9f+DgLIkLwjdpB9qem8NH63fwi0cyfTzkGwPdOruLnp6oJxcOwr5JgXPj3IjGYf8FxdqemMZQWZstDp0T4QEd7N931tfQNCV6C22oYnG0TPRF11hiyJjeUzVn1BenVuJVnYbt8vg25CdUaZY6pUImnkpWdJanPlPPcFLnJy2t6X851zbel8+KJ/vMxNfq9256faWM47fSq79n3LK+idGCt5/7gVaNwIsmm9PpiZ6taM2kEWZnKVKYylSlHZbDHWUReuRYljcfXVYhMJhevMb3+lvea7jsdPJcEOvExb+o56+Jrl3PsYsvJTZiXLR5RvFJS5Jw4wW0ivUbdwYzjD3LqjgGRZ4UvLNlsk25L8uXLHqQlOMCGgSVOP7sGpjItOsAHmzcRtsR9u1PT+NnxpZwYruItU/bx9poXAfjN0Hk83TeTl56f5ZpLsHWYlvohjp+qhkNCC7rqyh1cWrufHxy+jK7n2pxcinUHMxx5V4olM7r547aNnB85CsBvE3OZWdFLBoupwUEClnh/nkzM5zv7V3JybyNVXQESWY2ufleAwSvi1NUMc6KzweHl7Re9yLmxHuqDCR7uFZWw9/9AaIPNO+LGDO7SvyXXcOddtzrfnYoIVTU5PRAb/P0/6veu8uBUq1bK2Wz/1q0FgUomMvmj9D7y7tHWwiEt438xZHonxwOoyuOrQH1Blc4E2OOK//oooVikpHvH4kke//1vTwhfE0mTSiMzPcheduxCpDrGvUyU6pheQsjr5VBNKipUvhTgibGkBYh+Zd9FCDSvlEOA6L9jpdPficUB2i98jWQ6RPxgS84HpqDswn0B3vb7zwLw2MFzGYvhJNF1ClSeDDMWtgkN5CDs8UWj3HrRo7QEB1gaGaC+QQAuRjIhDg9fBcC/HHsrv9/0PACHks101Hbxw56LSTaH2Jg4F4Ane+ey97UpVHUFiC9K8dbzXgUgEhijNTLAieYYf3SZgNnPqxjlkcQ5HDzcQsMBy0EzxrqGCe+L0dsS46ETF3KyXvTRGurn0Ggzx8dqWFLZxdExkbJqW/8c+l9qIphdUzVNVc3jMUZqYrAoJfreFebAgkbe2bidk+lqDvYLASfTafV2xFxwehBB1mtW3Ulsyw7H5LfslnWkVsdYs+pOmrVaanKtY+u35mXAUMkLSKQ/Vy4QRmAt2zet94SoFzSDe5i+XX2gmQoNAlIPMTHOQy8zs+pOI0xfp2KEvYs85uzlZ7tuzVcK8vB66XdJI5tUgkwlfWMGn5dWvU/NPpDdOHigsKPZ70Rq0sgcm7pHW71v45g+mqfXPE2Obt8XdUUHzfdupvu2bFxUQ4aTiSpSoyGiTQFiAlHu5Abce2OUqQuOMjUsDnNj+6qZsjOXQFda4S+/7GW2Hz2HVEuIU20i/q8yOsrWU3NY2NrNYCbDsrB4PP+uby5DoxFqQkkODTbwXywF4C31r/KDw5fxrrkvEgmMsXtI5GDc+9oUOBkmfdkgHz73Gd5avRuA3w4t5AP1T7NvtJ7GLIJw1IYvvvA/mP/hZ1zT3vv15djhNNZ3WnihqZVNsxc7n43VZrBSlqPhARw/VU1w2KKqRwgkmTlj3t1fI9JrOchMENroyeEqPrPzegYHokz7mXDIZ5pwZ2tXNuEYwu/YTIcry/9YLFv5WqmZJpGM2x/4FMvU7176hrP+TRBanXoIQWsfX7vcJVDVz0y+YzmGKVxDF0Iu0Eh2ni7witLWpO2o7VSh6uejKybnqXpd/d9vDeTfeQdfL6H+1Evm66eRfpcE2aQ0LRbKlF2q5qNTXnHBLPm9SOoYXm1Pp2mxGCoEOJEb3HBTwMkCXzOrn8aqBAcPt9D2cMgFHZftpi44TjwpNufk9gYnrZTaz+WXvczn237BN3rfyoNPXgII098lMzpJZUJ01Hbx0Uah1d188DpWNOyjPpjgqYE5JDNCwLVGBqgOJrkstpcFFX0cTQuAxWcPXM9oOsj725/lPdWvELTEy3lwrIKDo00kMhHaQgLl+Om7P0LzDsGfhL4DTikZCTpQi3nK4prXv+Vph5eX+6bSFE2IdFbPtQnYP1D1guAp2Ww7oQKNy49ypLuB2qY4rf8v7AimuoOiOoBzileQgrLYZrLZZvbtWwB3wts8xJ3hICdJL3wKOc1NRZn6JdTVn5tikLGqEOm9eWUuTVaBuCy1Xx2B6SdgxoskNvXl9zmQh8RUP9Pf6TOFWlz10MfGZVrcdN0/TAhfE0mBwk3KVKYylalMZXrz0qTSyExlXFTySn5qbKucoEx+skJUyHShl8MYD3nVQ/LS7PzMrPqJV2ojvR0xmt/fyZJ6AT9/9PC5JHbXOwl5pQYDwn9W1YMrNqx5R9yYDf7hz9zNobEI3zp6Fb99Wfi2QlWjtDedoiac5NopL/GRusNizOEwL45MpyU0SGNwiJdG2gFYWbWX5ZEx7h+aSoWVpiaQyyayPzWF/rEq/rLxeX40NBOABeEjPDcyi7/bcK2T5UPGrPXPClB3MFfTLDQQcNJZqT4+EBD+WdOP86nZv6I+kACgJ13naHqnMlU8PTQHgKF0hIc3LaNx3klOnhTZ/Os3VdL8/k7i3xbzkP4nab4FXAHlUhuTpW0aHxAanNQaZfJkSTKYWjV1A8ZCkyBMlrJWXCHwguczZIoXy7aRGTsc0syHhUziOg9SO9bBJjqf6twhl8xZDyAvODelfz0w3fTO6X2Y3sUzAfZY8dBfjEsj23LdNyaEr4mkSS3ISkLuFTCzlSJsvPwHpvFUMppPoCAayg/pVYxZxNNZnjUtvueOX3FJ9AAAf/T4n3DwQ7c7RTD1KsaQKwQJuIpB9nbEnPazLznM8qaDfH/zKkINIsv9Hyx6lmQmxC87FzFwIsatyzcAsDy6j5bgCL+ML2R6xQkqLRFsnMFifoUwEaaxOJUR5syRTIhtw3O5b+9lLGt9jZdOCARHOJim55UWwn05E+KR1SJ1Vd1BYTLsWLUXgMsbX+WJk+c6WfTlRrz368sJtg7zxQt/zluinaSzr8/xTISYNUqVlaE/E2J2SAjy347Usz81hecGZjp8DD3dTFWPSJNV1ZPLVKLmTRxuCriQoicWBwjFc9WvJUWOBt3VBRACsW1jnM5rYqL/bD8H7lrh+p4kqRu8aiqWKcf058LP5KiaDHUyCq5VdzqmVZmeSh/PhCpU+ykkzNS/i3k3vfpQx9J5MH3uCfRadSdjYyMTntnjsgc/Pi5Btu36v58QviaSJiXYQ0dDeW3YXuhCtR/pHDdpWEULOANKyvRyeL6QhgBMrzn7UTEObnXMeHuUYxdbvBqf6lwPVY0KEAwi2FkWqIyt3+ZsoG0bcyfWlTfcQ1tW45BIN4ADTKe7dwahZptQi+jjaLKWZ4+3kxoNQTJI76iA8X3l5LWk0kGW1nfRn47ygbrtAPSkIzybbOPcimP0pGuotMYAODjazH91n09idz2/7a6l7TEhVPpnBZh2MMOJHG6DaRuhf5YQaHbNKCsaRIqqG2pepq2ij5eG5zMWy2lLwRGbsb5K9o600hQcpD6rBe4bncLxsRourDzIrIo4O1Jic54aGmDUDnJey2t8efB/AHBiRop0tIIpz9iO4JL8LbtlHc1dw8S6cIp8SsF77GLLSYQMwqc44z7ovGOlK9lyeFBoX6G4EHrN2eev5oDFicUWJxaLzyBXOkZW8ZYIUhCCZY08kHgBO3yeH4d07UUFgmzZQdsW9/2mA1187XJPoSJBFq7nWzsMukBWJsBTgbR2+rtjGscJVjckfHbxvmUH2KNMNNm2hV0ieKPU9m8WmtQamU7FaF2FnNbF9OXV/vUCOIqtslsIOpy3EXlVCV4hEHKVV/Ry4qhY24anwq5chy7ggWbSAljwxXW88rmcU1/mT5TayMKbdvHh1icB+GnfRfzi6aUOIjA9KsDswYo0He3d7OyZykfPe4LpFScAOCd0ioFMJd1jDcQzEQ6OiIwf2/va6X54hpMcWI4vzUIS2CEpHbUJzR3CfqmGc6/cDwjtbWfPVBofiDlmPRD5Gi86fz9N4TjvbNzuwO/fWrWPIDZPDs+mJjDM0oiwRR4eq+HBUxcSH4twYKhRXDvZQLhijIFusaaRo2KeqQYxhsyqn8idH5i26jVRE+1QFVULT4l1eTgH2082204MXKI94wg/qXFCNk6v0ibcF8jVaMvWeUs1iHskzbhDyciv1oxTvuu8lGY6AhFv06KaGFk386kIQCAv76QpdZp63YSUNFVpl/z5USFN0AvYof5tuv9K6/oJB3tc/JO/HJdG9sx7/m5C+JpI+p0SZF7ktaF7ovkgz4Ti9XIUY/YrxlxhenmKnZuXANM3AT0IVwqdvo60s9lKM5Y0H6oZ2l19GDa0Zbesc4plzvtWmgPXV/GV93yfJwcXAPDzDZcC5MHVx2ozNM3oY+TxZpIXxRlLCLj+tLY+lk85yDmRPl5LNvDw/vNE+33VOXOgckI+cNcKIr2WY0YEnI09FIf4ohQkxTytlPjcDtuEGkaoiooYsJn1fTRGEpxMVjEtOsDSmk4AEpkwM8O9TAkO0hhMUB8Q5r+XUw28ODKdHx9exltahbYXCYxxU8M27u5Zw5HhWl7qbBNjDVUIM+uhKkJzhxjbV537ImcmGEtUYA2GmHd/LihZmmrTlTaN804CojxMsDvi5KiUAtIO21jVo3Ay7Ag3cGthsj/IJXE+cNcK9t72SddzIoWM9Hk237vZiVdzqheAC/mpPufST5Wn0fhQsQkEXM+f0ref4HHeC0OFbD3XqIMSVRJcexakxfw+n4nCmhf9+NZxCbJn37tuQviaSHrDUYuWZd1hWZat/ex+o/kqU5nKVKYynR30hmtklmXdAbwPuFq5PGbbdm+R9+ey32cLa3ppLKYTlx8V8oV5nQRL6RsMJpHXaYbUEZF6iXk/s6NrLmC0+cv2OiJMja0z+fkkwg4EwGHo80Msa+5i21GBKjxxtJbQ8QonsFhS9ESG5IdOkvl5M3M+sIdnXxSIwLcu28W2rpmEK8YYPFjnZNOQGd/lfE3plZrfLzSpo4M1jokvNBCAmQKFGApluKz9EB+b+igHR5v4rxNLAUhlgmzvbidcIfxxgweFabFmVj8VoTSfmv9rpodO0JMW1xeHe9idmkIskHTmMzU4yEBGnJQPjzWxcUCkpupLVfFqXwvnNhzn1b4Wx5xLMihAHY+IAqMqpduSTG3pZ1btSZ7unOFcr4qmGDgRg2SQ2jZxsG6tGWTPwamEjlc48wzujhFZ1sfgwTpX/F96YwPJi+LM/jp0XhNzmRpNJWO6b1vJzrtuzZkRDRq5YypUYt88M9Rr74fJBKnf47pmyKgB5KExXe+InjZLQVca3w9F61MDyvUsKCbezgTY48L//CTBEjWydDzJc+/72oTwNZH0ZhFk19u2vXSc979u06JK4/F9FWpfyI/lda1UXrzGLQTycLXVgnAlWk4G0KrlW/T2fgJSFmKUaZT6Lk1RWZtkZCBCw1Ni84yeEPB3icSTAkjC+hNT4dwr99MYEZvwocEGDr08jZpZ/SR21zuQ/76ONA07gi7zlqT+WQGSF8Ud/1skOurkgky0Z6iZ1Q/A9zu+S4WVoSUI3z55ET98VZQIkkITgMYUU1tE+yMHmqltG+Dmc5/k/MhhpmfRFAlbCNfGgE0i+64dT1fyXwNLWV39CgC7k8K0WB9McO+Byzm+Y4qTPQTyi4fG9gvex2KQnJGi4akwiam5UAiZCzO+KEVT6wAn9wrf3PVveZpLqg/wT4fewsG9wgHXNEOgPt/W9iqjdtAxzyZfE2Zl6U9TS+0037vZ+R4lIrL35pXi7+yz4RwelBRZriQCWSGh1kbThYYUfH6hL0Zh6FNHzxlfJYPA0t8TXQjn9WXwM3sBS+DMwO+X/ecnCVaVKMgSSbafhYLszYJanG9ZVjcwAmwB/tq27U5TQ8uyIoD67dQAXLfmK/xm25157f20MNMm7AW1LUYjU6+pD7PfC+V3kizFL+aFQtSve/r9dN9AQJRcGW6KuQpiypO3szaatubpr2iPOn4yEPkGE+0h2jbCkXcJv1nfaECkisryIje42HrhizhwBbxv6rPce+ByAI7vmEIQiEVSsPAUp9qEwApVpIGYAyuPZXmJr11OeBCC0RQDCXF1rLua5AUjNDYO8dbWQ0yvFH6mV0enUBsY5hP7ruHwyQZGjgtNaASoPCfOu+a+yKzKXp4fnOHwsmzZa8QCSaaGEvRncq/WQwPLuKbmRUZsYTGoCqT4SONWto60MSU4yBVVQqB9seudxJNhQnOHaKlO0PNKi1jzq2wqWxIkX4sROSqqX4MQwpGXahi8Ik4olCF2h0iaHFy8krGYAOacXNTI1AXHAXhP/TMk7DBfmPsz/r1OVLZ+bP98WuqH+MkrHaRHg04dNbtmjNiuMPE5wj/q1EgDJ23Zhsx6Vmbj16InMg4wpFdJlyUFXHztcmP2keGbV4rvV15Xnnn5vfFA9lkyoXa37Mh/xn2QvZJ/l9DxypOovMOOEPZAQ4JSfkbzp5nG//HDHzeOeTopg4VVYhmXUsu+vFnozaCRXQtUA68A04DPA+cAS2zbHjS0vyPbxkWqaRFKS59TCp0O9GExfZ0WlKNBqBQNMMmeJDvvWOmYlWQ7FVXmZ050jaNUhIYc7Lt/Vi5psNQq+mcFnDg0ALIJcRNTBcJQovPic9IQSVPbFOdvzvtvgojNs8JK8xcbbiK2P+gKBVA1PInaAxhrGWXW9ONc1foql8VEHNm+VCuJTJh/2bWK4LYaFl63B4C3Ne1iceQ1GoMJTqarePDUhQD89PllvHvpdv6wcSstgSTPJYXGMz98nESmgtbgCDJkecQOcHisjgA2YSvNiC2E3osj0/mPgxdz8mQ1NbXDeSbP9qZTVATTHDjWJPjuq6S2bYDUaIiR41UCyIEIuJagjUivRXC10LqWtb5GYzjOgzs7CHaLs2C60iY4YjkaoB1W9oNImvn/POrk0QSBVJVFT2sOWC6NTB541Hi0to0i/2ZVVyCHXPQAVUmt3c887/dMu9qpBWAxhAYYCoL6vRN5Wpxyr+m6zpuejOFMpKi6YP3/HpdG9sLar04IXxNJb7hGZtv2w8q/L1iWtQ04BLwf+I7hlr8Fvqb8XwN0qQ28NJlCAs3TFq7co6KbfEtVaPeZHni/MYt5Wf1IjucXe2bq0zGhAKzocHxVrrYrOlgTWMtmDwSki6SPLYvwcsGwgWN3rWDnXZ90eJaxaCoiLL52efaEH8gW4RSbbdvd29jz7csYHIgyaodYWikygdzds4a2xyxiXSIIuxnRT/8ssZkeu3iFkwuxsXGIcDDNu895nndUv0zPmNC8ekdr+OGrFzM2FmDq219zMtT310dpDCbI2BZVgRSXVItA8a1ts6iw0hwcbeJUIMFgRmiH80IVPDESpSaQcuY8mAkzPSRMknG7gj0jrQC0hAZpqxZ7x7kNx0k1CTfxeTVHuDS2j1eS03g1PtURZE0z+hh6uplkq9CaQlmTY6pGIA6lAOodFLw/saiO4IhFlYIKDY5YBIctxlrSVO0XiZYljRyv4uhfxQk+HGPPTSJnZGy/xXCTxewHhYBqzraV5ka1GCcIf+S0jRk2P3Ari5Xr0ncZUxIMx5TMIK73xZDHEPBMFOz6e/1ad/tNn3XlptRj1Vz+LUMOSGlVyMuQooQUOPfJv3WNb0UHjI3AUw8xkZSxLazfkaTBb7gg08m27VOWZb0KzPP4PAk4nnPLOjsXvkxlKlOZJpJsW/yUes/ZSG86QWZZVjUwF/h+Kfc91H8f763/E+NnxQAt1M9c9xjKSkBh1KPJX2Xs3+NelUeX+aNA0cKieNDs/KqJUJ5I9/zrxQ4IQ+Vb71evgeW09/ElqP3VHLByTv3Meubd/TWXNiZ56r15pVNw0vGzAbH9QdKXJdg70so39l8JwMiDrUSzhjxZ48vNr+1kpe9vjpBuS/KexTt5PtnCjGxW/Kf7ZjpxXEd252KxDrc2Eqyx2T0qtCiJODy+YwqPLgmy/uSF2KMBIp1i7e5oyGDXjNHUOkBjVIBUPjL9CYJkOCd0iu8cv5zWiNDC6kIJpkUHeGvzqyTSEdrCfQ7fYWuMqkCK1sgAdTXCd7ikqYfty4Kkh8NwNOaKB2PLDqLtwpSqBlbPflDwIIufVnUFiM9JE6oapfZtffy/c38CiJI3O6a201o5wLZ3zuT8rKbYtWMOfZemGJxdRbA1wYG7Vjh91xzImY7j2dprdQ+HGG4KOGVjQJgbVe1HJae8i0fMmPwbckjIWNewO27M42+XX8xQpyyma04evjNpZl12yzrIPv9qJn+v0jXyuQX47f/7OHV1Xzb2X6bS6c3gI/sq8HOEObEN+AKwFDjPtu3jRdzvoBZ/70//GXBnAjhdPi2T/bwYQIZuIilojvSB/Op9mnhQ+TO19+wn+9LNu1tYbUNzh2h8IOYq66G3LZQySx1TZvVQX/g9N1VmTYC53H8SZq1vCI6/Q6mdJQVcYiokW9MOms/xr2UFogzsBrGpz3gk7lwbnC2yXXzgio0MpSNOWZbHDp4rBFk2EDlUJfxPi6Yd5dPTH6YyMEZTIMl3+4Sw+P7mVTTsCNLXkSbUMMKUHwse+2cFnKTDMkdi04w++gejjCUqaGod4NwG8ZhPj/bxwcYtdI8J35hMuQXw2lgDGwfms2eghdqwMEhUh5J0J2rZ+2K78EFl5+34tLbscJVsket34Poqx88YHoTBK+J0tHdz87TfML/iFAAZ4LWxGD/vX8biqtccgI2kIweaiRwNOqbnVI3oS5oY5QFCBs3LBNSQS/YrkwqYcovqYR9OW8Pz7pijs1QoOFmOLUl9JuWzJRMxO0HbSiVqJ5eoAhKTh0Gv9/2N8JGdd/+nx+Uje/nGr0wIXxNJbwZBdj9wOdAEHAc2Ap+xbXtfkffnwe9V+K1pc389PqdiBJfJvzUewEmx9+gv0XjmJgWUeqKO7QpTdzBjhByrvkIg73NX7JaW3kjSsYstx5cDOGCBPMEshbsWTyQ3JCmc1OSz8bXLnc3IJYyzglBe23tjlGDrMFfN2cOR4VoOnRL+pNaaQSqDY8yrOc6jh891eI5FUqTSQdqqB5gWHWDrEREDl97Y4KSAipwTx35J7OSpuSPYQxW0PWYx9AHhF1vW+hrdiVqWNx3kgqpOpgbF9fkVCQ6nw8SsUUbtAP/ZLyD/zRWD9I9V0VwxyE+PLOXkcC6WLD4cEcVLn7GdtFsy76KsOqBm39iQESmjpI+s5oDlCNj3L9/G8moBdnklOY0LoweZU3GKRCbIZw9dD4jUXc++OpOm1gFOHK1l/j+POmOplQ4kL+mo7VQRkP7RzjtWOgVIZXJiyApCFR1pqFTh6QvzAGrohzU10wi4YfWgaW2Q89NqhUclqEWNi5T3z/rHr4o2WbCRXBN1jDMBv1/0H7ePS5Dt+oO7JoSviaQ3XJC9XnICoi/9DKGQMBepgbB6njYvGq/AMbX31c6Ujb9YM6GXWbEQ8rBY3gFHc1HNUCDyFBYrtCXpZW/0Ey3gCo5WT+86msxFWR7VzU6u494bow7iLjQQEFnedQ0uqxWoKbeWXL2HPSeamd/Uy3k1R1zDXV2zE4AHT13IORFh5nu2fyZbdpwLkTTWYMgZ06oeZebUEyxr6qJnpJYjcXGoOvTyNP74yt+yY6Cdj7f9GoD6wDApgiQyYVqCcX4xtESsU+xljqWrOT/cz9F0kH2jAkpRYaU5OlbHzsQ5zI8e5UddFwEwmIpworNB5KYcsZjyjOBF5leUgckqUlTmVFSFnVz/9GWDXD5DnB8XV7/G0spOBjKVTAkO8lh8EQAvDLTzdOcMJ12WnP/8+0bovCZG086Mq0DpcFOAVI2I0Zv3CWFKFNW3bRp2BDm1KJfjUaJj9UNSXk5FLyCVFoSta3Vq1n5p5nNAG3r8m3IAU1GYIJ7T7tUxdt51Kwu+KPpp2plxLARSw1vwxXVinbOasRTkGzJnJtfigh/+1bgE2St/+P8mhK+JpEkjyPr7+x0fmSl+SqVitatCVCjOTO3bS2gVc8I0QuMxJ0ctlmfTxrD368v54yt/C8C/brqc+feNeGb1KNS/qnlJ84wsKwLCnDXWV8n8+0Y8k7nK0zKIjUVulGpMW3xOmtBAgNkPJpwNG3IVqyHnI5J5Ig9/KkNDdcJp+yezNnF11V72jNY7sV5LI8d5LDGbhWEh3LYOzxXXKzvZnJjHd15aSc3jMUebCTWMcNWcPaxpeIkXEjN4X90zAOxMtXFN1WsEsaiwBD8jdpqXUlWk7CA7RmZQYYk+YoFktkzNGI3BBHtSIo6swkoTzl57OdlGPJsVpCU0wNf2reH4qWrG+ipz+SFrxmh4KuxoY2pguFwTSamabGB1qwhlkH7R939sA4l0hOaKQRKZMM+cmiXm0zMV+6Ual0kRIHHBiKiztiPO3luChPeJQ2Vq7gjhfZVO9hAQWVAGumshkia2K+wKv1Cz+JvyeKrPif4c6gHUOvzd9I5IyL8UNLLKgcxSImvUNewQBx816bRqonbW+t5cVhOn/tuKDvbeGOXAX+T4OhO5Fs/99/EJslf/59knyN50YI8ylalMZSrT6yeBWiy1jMsEMTPBNKkEmSu63xDo6AWOeD1BycUAPHz7yX4uSZ4QVb71+3VNrJjSLn7X5VhTFxznjxueBuDJBXOBpjykY7FoTVN+x8W357LfX3/uSzy8/zwOXK9keNeqDG9WHOkgTuud18Q4slpqexlq2wZINIQ5cH0VNSKky0E3yrg0J29j1szWUH2Uq6eJbBrSfPh0so3frzrJRsEeT49MZWroFCN2BSk76LCYsoNcXf0yiUURfjB6KdZJocHMnnKCI8O1bA7N58aGbbw6OgWAR04uodJKsT81hd/2Cl9b73CMeDLM4EER1/UHvyfK2LRV9TGn4hQjdoBEpoKesXoAzo8c5sLIKA/Fp7IwfISWoGDy3hOree/07STaIjx29FwOvTwNAGsw5GgIianQm82R0XzvZsj6daQmJdNYLW/q4QMtm/lc23UAHB5pZGp4gP6xKh47ei4VwazWGE1ysiFGKC6KkaZqhIZX9UIlg1fE6bu0gtraODOv7AaguiLJ1MUDVAeTPF8vKmK/9PwsCNtU1iYZi+WQsU07M3Svjjl+M2mKW8k9xLbsyJmsFSSiagGQmvqa9cKtsNnwrEuUo2pultqYakWY/Y17mLdRmBfbWO7UsNvTUcn8+7L14m6MMu9+xadH1MXb4Gxb1ILbsoN5dLByYw6dOzBw1ig7ZwVNKtOiV67FYjdhKM5p7HWfl0nTS3iqzmfAtYkXK1xV06XJv1SMQFt8+zric9J8/5p7+X7vKgCe6JxLcFuNy65vulcntYYU4LzYB66vIjhs8fk/vB8QG/xLJ6aS+XmzK7jU5R9RKx5nN5oj78oFFss6Zc89K8x+sryJEGqWAz5Qs1IwM8G6i3/E9sQsQEDeR+0gLaFBtg3OYc+AMOcNpSL0HK8jEh3lqlmvclmNqFO2NHKYqkCa55PTuP/oZezoEnkSq6IpUqMhpjf2MZSKMKs2m+qqr4X+wSjpo1EnqfGpRcJ/JIp6BnjPB54A4F1126kPpKjAZtAOksgIM2fnWCNLI0cIYjOYCdGTFlKoykqRsMPUB4a58Wcfg0axNuF9lVT15MxdUmiNZS2vMnsKCN/VkqUHmVdznM5EI01hsVaDYxEuqjtEhZUmFkhy52+EgKttGyC9scHxt8kxZQma9qZTJNMhUmkh/GfV9Tl/9w4LBgYebXWBTdRK2IBL0IDws6nIQiMIxFRvTE9FpZr8VFAJBmDMjriTxURFXEoko1r1HHJlbNTSNHIcPXxnQ1aQTbRpcd73/5pgVWVJ96YTI+z94N9OCF8TSZNKIzORV0aNQuQF3ihWYBUaX75YKhhlwRfXiRNjKYx65JEsxecnhdXfbXw7e04IgMHYvmqmG0rPFxJi0k+gwpKHmwJULexj9Tn7OZUWiLvGcJyTexuZtyPu2oz0TAsgnOsS0h2JjjIyIOz+s885BgifSyySYiibuKwqmWJwZphUTYxEe4bm7L7XfmE302ID/PDYct7WuAuA54Zm8osXzseqyFBTO+wUq+zrSNP2mEX/rEoefm0ZG2eJjPvvm/08MyO97Eycw4nhKoK7szD+hih2zRh7BqZiDYboQQjEeZ/YSiaLrJQbtsyG0XnHSpp2ZvjBC6IO20O159NaM8gHztnGqB2kLij8eIvDPbyYbOXCSA+zQxYDGSE85lckqLBG+G7/YpYsPcie42LM+Vd28+LLM+kDQgO5hL9SeBy72CI0VzimZtYNcF3r8zQGh4jVJfnhcREXdkFtF5dF9xG20uwbncJF5wtB/tyzcyFbuDM4YhF5IbdRJtqjHDoqQDfSX9ffGiXybMxV+DM8CPFFozQ8FSbwzl46pwq/VDpqM/vBRC4EI/vcbdaeQQmdH5xts/j2dYQHYbtSI22zjC8zxKmxZQfbN613gz2yuSNlHlEQ72dNx0o2P/BJVt5wj5M7MrZ+K4tnrXP50wDnXV7WtC6X7SQbAnG6QoBKpVwOnNLuORtp0mhkfrkWdTJpNYXuKYYKxZJ5CUe11H18TtoFgCg0XjFxZ1586mVYjrwr5Tjp1Yz3KgJRT8+jx4lJki++hMAPNwXouzSFVSGuS6GhJiTW425U8w/koM1yk6yZ1U9rzSDXtL4MCEQhQO9IjL2vTSHYHRFFOi8Sp++O9m4GUhHaqgY4lE3bdPBwCySDTp9Sa5JziK3fyt7vX8jl8wUs/ZbWx9g6PJdXElM5OlLrlJQBUYwz3Ccy9cs16r5tpRNf5ZCKplNMUQeuryJdaUNjiuVzD/A35/w3AMfTMU6kY1wV7eXQGHSOCd4vifQyaEONBT8ZWuCUitnUP58TqRh7TjQzcCLmBGeH4tn8lAo1zejjD2Y9w2vJBieGDuDKul2cW3GMCivDL4aW8OKgMAtu65pJ8rWYU4FarbRd1SOES80By8n1GBy2HKSkK79ltjJ1KJ4r7Ckh6p3XxAi5FSbaNsZdBT0hhyw0VbGW6EFHYCkamBrPKKuG6yTjFmWMmnwuZ3/jHqZtdFeBAG8Li/OZ9n6eCY1szn3/Z1wa2f6b/u+E8DWRNGkEma9p0StQuASTo97X64Hnuz5XhMneG6MO4kyaJPz68PL9yc/8zJS6pjj0S2Ges74jTvVO4l4ty4arfIv2WffqmBNLJTOuHz9VDYeqnDgndYNyBS5L0uDykuLtUSe4uPoSkYPwopYurqjfzfNxkYE+EhABxJ3DomzJ1l8uIb0wzlVz9oh1emUhwYo0l8zo5OCAaHPkQDOx/UHii1K0ZbNQSEpMFeazyy97mZNJoUl+evrDTA/FeTrZxpde/h80Vgmtqes5YWKUEHgpnKXvxpXJIiuwndpdCjlxXhfFWTTtKADfmvOfnEyHqAmM8dpYjI6w0Mi60mkWVsR4NpXi5WQbb40KJ+Gf7r2R2dUnefZ4uxN4DTi13lyJlxelmD+rhwPHmrhqzh7aK0WYQVu4j0sqD7JpeB4/6rqIQz0iv2N4XyXphXHSR8V3JKHzssyORPLJg4xMCp2YKhCMkDVDDgSc6tzJViFcZfkeNXu+s5aK0FBLyEhznloORj0kyGdJ9bmZrAxOuE62DzUAP4+yz738DkEc+vT2UqiZaqmdEUH2b+MUZH909gmySW9aLFOZylSm30myrZJRi5ylSYMnjUammxahcDxZKWQ6weUhIj0K+vlpVKqJT2o0EqhQbGaD8ZpGpZlmuClA8/s7OXyywSmoqJpP1HIYKrILRK0sEHFUdTXDnNzbyK/efQ+NAXFSfyRxDp977p2EQhmSwxWO6VKNB3MFiRvAK3Lc/lkCKXfsYvGyLVp+gHAwTWvlANt724kEhUa2rKmLl05No61qgJdOTOXkSYGMlJnu48mwUyJFpsiSZlE1OLu3I8bw1YP84bnP8L66ZwE4PFZHW0gcVP/n8x92fGoyHkua26QZLdJr5WldMm+kyyyG+P5ldou9N0aZeZ6IYfvIzCc5la5iVXQvjycWsLRSlOpbUDHE08lmagMjNAYTHBwVWuaTgwv4ya9WkK60mbYRV5YNGSiu+plkJYA1C3ZzZFisyyUNh3i6b6bI5PHiHCf9V3yOSAUmzc5q1hDpM1IrRMtnp/OOnD+pqgdOrRqh6oVKp96ZvN7XIUzraqA25OICZZoq0DQrLaeizPqiZ6nXQVeyjaswKPlWGr3grHxmpIlSza6jmtvl/HVryZmII5v93c8QKFEjyyRGOPDHX54QviaSJo1G9lD/fbkUVR5mtZKBGkUEMXuhGtX/1X5NQZtyU6k7mGF4MBdUWQg4ovIwHlCLFCRHvr4cfjSDKCCxYv2zRFLe3o6Y8HdcLEAAaiqkVEOGUIMwF/3Bomd5eXAaSy4TWPejabGR7xpuoyqa4k/mb+bvNlybC3jVNgQ5P1mAsbcjRt9NlwFC2Aw3CVNn5zUxglkL0kvPzyJyTpwdY2201A/RdaIegN9ve5HOcCOX1e1naCzC5dNEtooHd2Y3u5NhQiNCGA43WQw3xRzfjkT2Hf5UhpHjaaZVJ+gaaeDxCgGdPzjSzLnRHi6LHmB+Uy/PdohnLrY/SHphnKFlKZLdtaKGGML/I/1kUaUIpfMdKL6dunaxHjJLyR/PEJvwu2PHeCYZ5PHEAgB2Js8R62/3UGmNMpCpZE+qlYeOLhVrvnU2kV6LuoO2C0UnKb52ueMXEnD5YVprBqmvSDA4JoA0PalapkUHePa48I1JEIR4fnOHkGElZ6EUYKpw3vzAp1jTJcbP+cgsghVpKq/oJbG3kfTCLC8zKmh4KsyemyqJHHWn2hLpzOL+qGItWbDul3T5krNtt3/rVtbsiItAZ8X8O+sfv8r8+0bYc1MloYEAe7WCs/H2qMu35pg31TIuW3YIoMr6tW8Y4ON3hSaNRqZn9lCpENhivPFkpSAXPbUxE/BES63jx5veV8G2WU0nvna5I5BCcUheFCc9msvIMOOOzfBYO8saRKm3H20Xef/On9vFnuMtXDXrVX716IUwU/iILpnRydOdM/iTJZt5R/WLTrHI7xy/nFAgTXUwyUMPKTFd5BLMqsCQU4sy1O8KMDjbdjK1qymWJKAABJAgvVDwvWbBbgeskMoEeVvjLk6lqxi1gzx2TAiAoVSEk1tbSUdtqhaeAmBwIErVC5Ukm21HwwN47sB0ghVpxvoqmTUvx/Sypi4aQgneWr2bT+5ay4nOBtf6WtWjzDvnGEvqhTY1P3qUR08sYsemeTn/WTZNku5nlNd6O2L0XZpixUIhgI/Ea2mKJjjY38CSph7HF/h7DS/QEhzk8FgT/3HkUhGfhQCs5NXLIldLSyb4BeG7Si+ME3k2xgXv3sWHWjcC8FDfhYxlgmzYcgH1u3IQ/vAguUS/Cu8yZZOeHFr6rg5cn8sPKb+3upphGqMJ9hwUqVcangobv3eXb8sjw4fJD260Xhjqg8ksMuqhQq6Vc6hUxlRT36ka4YHrq9h72yddfXv556+87LM8/tTEaD5yT5z1r58dl0Z28MN3TghfE0mTRpBdwXX8xn6wpHsLxVpJGo/5zqson9cY+lilBDR78e4nmGWyXYDG5UeJJ8Mkdtc7bYLDFpFlfXxq4a/ZmTiHfXEBAnnvlGf5eW8Hr/a1MPJ4swPpTlfaXH7Zy/x+0/NcFOnmM13vBOD3ml5i1A5y5+bfJ9IZdqUg0lFoIKDhY7UZiOTQddZgiMZ5J528gtPEXuuAR+KLUlTWJolFhYnsstZDLIm9xp7hVnpGahkaFVrGolohkBoq4vznoWWij2yfjfNOcnJvoysWq2mnMGedWiXSL4FIrTV7ygnePe157n7m7ZANiLbDNis6XnXme0nlQQCeHplFY3CITz/7XicjvpPMWIJAtKTGoKQ3AmeTDA5bJFvTrOh4FYA/nLKVqaEBfta/jB+8cKlTmkYmepZmLTU+S/Yrn43Z//63VL1QSeKCES6cfZiOWnFwaQv38YPDl9HTX0vjAzFXYl9TVngnhko7VKlgFzVfYXxRitqmOInhsAMckVS/K2DMp6lX+pb9eqWwMqEKVaCGbOv6DtQx1TkoyFlVWLtMlNn0VZLy1kM5sJwJsMes7/zN+ATZn3xpQviaSJpUgkz6yLw0r0KkvwzjESql+q1Us49fQmC1r9cTLjDv7q8R6RUmtMgygVBLjYa4rP0Qe+45z9lspE/iTz/xM+5+5u3ct0oU6/7V4Pn84IVLnaBbFcacqoG3/8E2TqZibD8qzF/3LFnP33ddzchftTpZG8CNIpO+lbEYWEsG+V+LNvHb3nMdDWP5Ja8wNBph15FWV2Bx9ITwl0V6LRLtGYJZc+FYyygAb18iYPmzqwSC8n21z3NwtI5nhmdzeET4k7YdnUljNMGBY02kR4OOwJJaS2JqNnFy9nuKt0fpvnaMaW19HOluILZLCLLatx2l53gdy+ce4G2Nuzg/IgRCa3CE9774YTI/b3b5fJLNNrNv32L8HtUyOQCd18SY8YjYJI9dbNF+ocia8YHp2ziUbOY/dl3kyrUY7gs42eb1TVoG6aqlcOJrl9N9lY1VPeoI5ssve5nuRC1DqQhHDjSLz4D6TZWORqb6TtXNWn2O1YOKfLbii1JMa+sjngwzs76PF/cJ86VMQizi9wKOmVfmyDRWWpZkSizswYvqs5LxZtJHJq/LPIt5sWhKJQaTZmcUqLhzh8bWbz0jPrKZ/zI+QXbof519gmzS+MjKVKYylalMCv0ORURPGkGmgj0kmbQav5gyVyoZaQbw8G15aWsFNTBNm/Kqgqv3uWbVnUaEVjHzUk0yf/DZjeyNt7C9u51YRJjRBk7E+O3L5zJ//VZQzFBHVkf5+gPvwm5N8y/H3gpAd6KWeR98zqnF5Jy4mwKO36U7UcviFmHG+9ye6+g5XkfwE2k4ZBPbKLWDqKguPDNBcLe4Un1JLzXhJK/Gp7LneAuXXyY0qlQmyEg6RHB3jJoeXNncQWiPiQtSTPmZ0CaOXVwBMxOsqtvD1NApHuq7UKxLcAH12WwZjx0U4I1whfA3jSUqsrW1cn1LbUUF5DTviNP2cJT+Wa1EYrmg8eEHW5l2IsPOD0zlnc07CFhiR3hoaDEXtXSxYVW1o+017xCgFZl6S30mlt2yju3yOcx+z7K8SWxFB1OIknpG5FT8zp+s4vipaupqhjmRqCA4ICwSMj1VLvNETvvavskdhM+KDvpnBYjth0S7hV0j1uPQYAMza/p44rV51LYNMDgg+oieyAgtZssO51mBbGBxVltRs2rILBvDTQGnanToeAXNc+O0ZatOv/U8YSo9maxi15FWhptiLjSjo1VqpVZMpkw5txg4WTXk2jr3dOUyyGze9Fl4IGcZkb93Khqxy0SpXpefZceSv2VsWRtuUlG61635ChNN9jjg9yXD9d8kNGlMiyrYA4oDbrgeSANsvtD98n85np8Zs5RSK4XGLPa6bv/f86cVrL/q2/x66Dx+1nUBfUPCAf/R857gWz/6H7zyuVudPiScWJoMJcmNG3D5X/pnBUi0C6BG36UppxxI5fVHaY7GOXSqgcTuepcjfywG51653wFYpNJBGiMJZkRPMq/yKN/tFBvxoZ4mUSJEwqS1TAwSFCAFqaxxdeHbd/HJtl8Rs4RZ7OmRmbw1eoD/HLyAHx8WPrJlzV30pap44aeLGIvlhIYeEiBJzvfYxaL+15HV4npwxGKsZZRZ04/zzwt+yNMj0wUv6Sp+1HURJxM5sENyuwCIVPXgDrPwqCDuQuRt2eFA2UNxXGs+a7owofb017KsrYunn1wozJfqZquFU8g5SeCPDE6ev+A1uh+e4fjOJD337FyqunK+Llf1aWUOesHK7tUx0peJLygWTfJX5/6SQ6lm1sRe5h97xSFpQVUPP31tqfN9SxCQLJmik/7dONcVwaYGT3sFN3fesdKpG+aQEj4gcytCLsNInmlxRYdjAlb79grVORM+shn/9LlxmRY7P/LFCeFrImnSaGRQum/MuGkUke3DdArUxy+GvPxpXv2r97naa0JS5SPWNexs9H926QYSmTAvDLTTN1Tl5CwctYOkGjKugpix9VtZs34t0bXLad4x7PKpyM1QdeBXXtFLSzhJV2s9kd25Ol21yTDLpxzk0KkG0pW2qwL1/Fk9XNJwiKG04GNKeMDJEL833iLSRyF8J5LUjCdyLXZuygltgOhGOPKuEVKZEC8n2zg+JiRxS2iQPaP1vK/mBfqn5QTLtqMziS8SwtdTI86uuQuttqIDOyw2imBfgLFkkMFUhHXHruKPmjYBMBCs5M9n/YZEJsK2QZHO6nB9Ay/uayc5AwZnVzGlPV/DUL9nIAcEWdHhFrbZjTh0vIJkm1in/7VoE3PCx9jaNpu937+QaVlNleyhRvWZSa0tFBc+ymmze53Pgqv7WDtjF7/sXORcs2vGqDsYcgEtANasX5vjE5QMKSK7RbLZpi4Lxrl82j42D87n+vrneD45nXc3iBi9LfH5JNMhghVpTi3KkOrKhXlI/6pT84vsu2pI96W+PypgRgpYNY9j781CiKnFeNXvQsLp25QxVE1NzUIj+1FzPhZ6lyeczhI9xbKsnwJXAI/atv2+ku+fLBpZsahFL9i9rzZV4DPZR6ExvZCQ6jVT314ndT8epDP+5A1xx3z2N+f9N5XWKNsTs3jg+1c6bfXKzHqfaj463bQy++si/dNjv+ngqit3UF+R4NRoFWsaXgLga/vW0ByN85Fzfsv+1BQOjoiUqrMqe1la2cl/93dwalQIlSc65zI2FmCsr5LKloSDQowPR2h8IMaR1SIJr54GSJKaubzzmhjJ1jTzF7zmQOGvqn3ZKZwp6fhYLUdS9fzkB5c7aD9JqtNeNS2q48r2e28JYo8GiHSGiSzr432znwegIjDGgsgRlkZ6+MngBQC8lmygOphk/Z5lBLfl1F0Zh2VE3yk8uSoMKFWz99wkhOr55x3iprbNLA73sCG+iL/bcC0gqkbLgGs1p6WMFaw5YBF4pxBkMog8Eh2loTohUo0BU34cdQ4vMrZMJSdxtKI1d14Tc6UKi4WSTAkPMJoJ8WTvXN7SvM9pu2toKlv3zXbWEnJB5jKHpfwuJOhEnQtgTCEl06HpeUnzBIyivZq0f13blDGQMq+jChhR3RX6u30mKkRP/8fPE4iWqJENj3D4z74wIXz5kWVZVwA1wB+NR5AFCjcpU5nKVKYynXVkj/PnDSDbth8HBsd7/6QxLT7Uf19J7fVTkh+03c9kWYqmZgKG6P2p5j1TuhwvUIfeRwxhHvnIM3/E0hqR0mh5ZTe7U/U83H0e8Tlpp3z73hujTGtfbswCAbhPmVmTWuc1MVINGQ7snw8IyPtvf7GU6kt6+f6S77F5WJjRIsExPj39YXrSdays2stVMYHs+D8H382cc47xk1+tcODkDdUJ+oaqGIukuaz9EHOzsPm+sSp+Nesy6nfhNmetutNl6tusnISremDGHduIr11O/DZRG+zwaBPzwz08MbSQd9Vtd+a3Z1jUx8oBUXCd8uNrl7sCjGWmjlQNHHuvuDa1vp9UOsgJaplRM+iYSyN2kK1D81h//BJe7Wtx+phV14f9ktDGpG/PlVgY8oEE2fWPSf9Ntn20fTnx9ihWtlRbOJjmkkg3QQuWVnZy7Sox14d3Labtg88B5LLCb9nB4PUr2HvbJ5n9jXsIPy005mk7RWjDSG0FPUpqsf5ZuQS5ywZxa+oOb+64sFRDhqn1Q9RXCP/oW2peYTAT5fhYDW9p3seyqoMAPDZwHr0jMRobh+gfjNK4XISHHItOIdKbDYRXMoksu2UdzRLQoZgY5bqsCax1ABfSZCjbqu+nqkVKTVuCVFQ/lySpicW6cnNcecM9NMvCnlpRWZ3WBNbCpUvgqYfyPju9ZGV/Sr2nxDss63LgNuAiYBrwbtt2m8csy/rzbJupwA7gL2zbfqrkwTxo0ggyLzJF94NZOOUBQQwPcbF+sFKEnfp/TLHzy43MJdwwC12XAGqPEm+PsmbVndTeHaMlmxuwAouwleb4qWrm3zdC8z1CwO08PpXY/Vk/ioeJUR1r1j9+FSIioDW9UQAXgjGRguijc59gMBPmyVPC1zWzpo8MAaYG+xnJhPh14jyHzccGziPdlnSAELFIiuRwBVZFhqGxCLuGRMR270iMxAUjhDdVutcha+ZRTX9yDs1blO9iizDpvXpeC1e1vkoyE2JzYh4A93deTCodJDR3iM5ramjamclbf3096g7mypfIIOcjq6MEW4cJVY1y1ZRXWF0lkHgJO8w/dL2NeTXHWTRdIDn3JVroTtSSnJGi6eHcK+iVbV1+v/H2qMtHFMumgwIBiLDDwi95Xs0R9ozWMzU0yNPDs4ln005VvVDpPM9Ohei1y5nyjM2sf/wqbRsthkWSe5Evsm2EpsYh0S4qADOJ12K0bRzOE+4qqYUxh5sCBEdsmqNxlsbE87Y4fJx9o/XUBIapjIzyxNBCAJKZEM2VcSqDYyxp6uH8GiEp9je38PCmZYT7RHC69PkNNwVy76ci7CXCUTU7O1k7NOTjmsBaYuRSbamp42Lg+MSc9tnvQZpn1Tg5L3Ol6QB75WXjA36VRGcOfh9DCKd/BX6if2hZ1g3A14CbgW3AXwKPWJa1wLbtY+MaUR9jMvnIXm9AtBeVFFRdpN/LhJyUwbbWYIj6XQEHteWCGRvQj7pfQpaPOHB9Fe9c8xSLq14D4PhYDbuHprHpt4sJDltOSRV5wtbXTU26qiYLltku7KEKJ5ls3cEMR96V4raLf8XU0Ck++eSNAFgVGa5fvIMKK82oHeTh/UKQfe6C/+bHxy6ie6jWSfZ7qKeJqS39vHf6dqoCKR4+tkRcP9XAQDZ/4d7bPmn2CXr4PlfecI+rZlZq7gicDBM5R0w+OVxBY+MQJzobnP4BpwKw3PxUX4jsf+/Xc2sydcFxmqNxrmt9ngXhI+wfnQLAnIpjnMpUcTJdTU0gp/GtP34Ju+9b5K7HBkZUoZyHTG0lN0+ZnDjSawkwxZITADRGE1QGx7ik4RD7Ei1s6xJ12qQGOOMOd+Cv9B9JIA6I5MBW9SiR6ChjYwEn+8a0jXhmDVE1ELXopEz/JTOrfH7KUzyXrGDb8Fyuqd7JY3EhyJZH9/Gto1fRGI4TH4vQGhEHsKpgkkQ6wn/88i0Ehy1XDkapRanPr5qGzfFh3hgV/lVw+b5keSC1oCYo2nFW8BUKlDYioeVnegLiwFrG7NGJ95F9647x+chuuQOgHbepL2nbdrKIsW00jcyyrG3A07Ztfyz7fwA4DHzDtu3/p7S7AvjYeHxkk0Yje6j/Pgd+Px6oux+C0Le9hnIsiJQ0QPflKXy4KYBVkWHt5VtZ33ghbKp03WeE/q/ooD+bNV3NZ1f3oWFagkNsP9FOQ0iYdB7uPo/qcJKaA5Yrce3mBz4FD+RrfqcWZWjO8iY3hMOfyjC1boDoP03jyOqcE73zmhiXz9/LRZUH+dMXPkibomk8vukyBq+I0950isvaDwHwfHwG1aEkbdUDzKgSpr9kOsS1bS/z4mA7hwYbHNTi+qu+zcOzL+CB71/p0r684upcKMOuYfpn5eD5ydYKarMFOQGODtZworPBEchqfal4e9SJR0qtdo8ZX7uceZ/Y6gizVDrIvJrjpOwQXzl8LdUV4p1/S8MeXoqfw9TwAPsSYj4X1h7iLQ172HLpXBKdYYabRN+pGgH4kIlm1Xmp5tQjNwqhYteIQqXJmWkWTTvKTW3i0PH0kDDr7hqayvbudqePZGvaydAhTYttO+Ku8AV5cDlw1woi+ytJNkeY/WCCDZuy439C8DXcFCCWrYos10NdG2kuTdVAzQGLPXNbOHRKaO9Hk7VEAmPUVyR4bmQGFZbQJKUQe+nUNObXHmda+JR4VgZnsPXITJGlvzvizCd6IiMOGmuXu9CEzvdGDpQzbWPuOXFlNukaJtaV07SkRcSZV7YvObc2RaNTNU+JeNysCHOTJUhev9K6njc5dWn/fwG4o9ROLMsKI0yOfyuv2badsSzr18CK18OgSpNGkAF5PqVSIK8mk6Ppf/lQmgKaTWN6Pczq5849HSuZ9rMwP6nogJNhJzmuPqZ+b7hD5E2USWm7rx3j5N5GIufEGdtXzUNLxMt/4qgIGA/NtmneMczRvxJOFRnAulnpv/OOldjhtJMWSSYH/qslG/jqS2tIroZ597vz0x0abOA7gcsZPFhHMqsFNe3MED2RIVAzzO+3vejA67cfPYdYJMXxU9XsDAkT4sjxKv4zuZTrZr3IpoOzmdYmfCQxa5Ql0cN8tz3jytxeSNt1AndX5wQFCBPmyWEh9AcP1hHpywVzq3Bt1VylJ66V2ogsLHmis4Hq9iRHUvW8tflVvvncFQC88MIiat8mcln+wdxnAHhn9U4eS8zj/LldvEg7VT3CVCYPBWtW3elUJpbzkBp39+oYdo343qa19TGr9iTTo32cE+ljb7IVgKF0hG1HZ9L/UpOrWkEEqNoRhBUdTmoxOZ5Oe2/7pBh3MODwAMKcqedrdOgB8R2o5s/OO8Q8DsyuZiSbOmzT8GxWzTrA0WQtj3af69z+jvaXnaKo23vb+cXTSwGcCgv2UAWRXsvRjvXYMFcpnqymKJGs2791ay5Q21DyRWq9eukgUw5GqZWxZYcjMOW7qB9A1qy603gIfaj/PhlHNnFkW6XXF8u1z9PIxslFMxAEjmrXjwIL5T9ZwdYBxCzL6gLW2ra9hSJpcgmyMpWpTGUqEwC2LX5KvSdLg2cSfm/b9tWv5/5JJchUpFmxpj5JJo3JFAdSKNasUKYNEwhEv2fZLeuE76RLaEG66Uwv8td3aYpQ1Sj9cXE+PPih27N+ghdFKqkDAokWyWa7n3GHKIKYHs2gk6Md3rGS2rYBoE5kXU8I/+MD3Rdz1axXeXh4saiblU1pRFKYh+orEtCYommj0DJkMczI9xr596bfo+9SoU1YgyFiCwQqcWwsqzEcDfJ7y3fx/Kl2qqIpmqNCI3losIN/2v4W5n1CaEFO/TJlHfLWPmv2iq9d7mToDw5bWNWjtFUP8Oyrwm8UGhG+Qic+SdfqNW3FyZayooNY1zDDTYKX5Iw0yUyIoXSEo8laghViPZLNNpHgGNU1SUazZWaeHJ7NqXQVV7fsYtfW2U4VAu7NgRDCg+4YucHZNs33Cu0yVCU0m6unvUKFlaZrpIHl1Xv5brdIM7Kotof+wShjtRn6ZwUdX+hYTCnBosxH9b2q4B4Z0ItiQlSDwdXnRc9gIb+LZbeso3t1jEgvpCvF/MeSQZ44eh7BEYvQ3CHn+/9F13n0D0YJhTLONYBQKEP010KdTtXkNGvdnygBPqpGrs5zc2Y9a7rudCWvlrwu+OI6Zqg+v/VbXXN2+ll1J6yOCZ+gYk2Rmpe6JoCTJsvkhphwenPkWuwF0kCrdr0V6MlvPj6aVIJMkirE/BCHfgHKGzLrPYMZ1ftNPi+v9sUI1TWBtWz3QiXKDVsr8gcVjCUqmJ01f62RaXQCa10mwzWr7uTA9VUiJc8dm5WqvZm8+c94JE5vTwPDTeJvGWy798V2urtmEI6J7PnS1yRp1A7ylxc9yta5wk/z9JML6Z5jE9sfJDwI8z8szGu9N6+EBfD2ebv51d4sam1Giqd6Z/L+9mfpb4o6pVZ+/g9vg2wqKFkCBcihSrU8ec5Gkc0jOOUZKbBtjjSEeWnffKwGcW3KMzaxrkQekMb5W0Nxqt9L920rnQ2xD+H7+Ub7Bv4rMY1Xm4Q/rAu4ZtrLvDDQzn8eWAoI0+aRA81O8U2ZFkr6nqInMqRqoPnerc44U54RuRPji1J8uuNRAMLWGO+rPsjTyWqOp2u5umUXAAsj3TxZP5eTu3O+LxCmyzV3uFGoDtpThbFn/192yzrI1ouTqD41j6GJdLSn6o9KXCAOMZF9laSjtqhSMBZwkJ9DH0gx1ldJVdsAECKdzeaffC1GctUIwe6IYz53kXbQk8CYYaUuGtK0SC7NFOAU/Xzlc7ey5o7NblNi1rysH2Zk3TWX8FKrWHiF8nis2YTR6zMtnh4WbDtlWdazwNuAB8EBe7wN+IfTNc6kEmSvNwbMy4flNZZfHFopPBZDXqe47tUxIp3CF6VrE3ljbNnB3k3rndQ+5165H4Cunjl5sTgy24P0Sbx1mcjU0X3rbPbcVElt2wCLW3r4+xn/DcC/nOrgWKqW+dGjvBQ/h6c7ZwCiTpmMV2u+d7Nz4k3VQOrRVn4xp9lhr7ZtgGmxAaZXnGBNrJd/G85Cy68dEwl9V3RkNdXsZqPEA6nzVoW+BDWA0A6nbcxwYnHOv6c66/X+XElj1WvZrBHLblnn+J+sigybDs7mkaYWpodOUBMWLoU/WPQsV1e/TN9ojKeHxZoMDkSxUhY1BywSU6HmQNDhZXC2TWJqgKadGfZ8W1TIju0XAjw+J03oeAXPD4p+ltZ08omutzvAmNomoXq11gzSN1QlKnjHA26/nxab5mTHMFgjtn/rVhZ8cR3bv/UpdzYRw9qDIQwEdyaYeR8UYx64a4Wod7crTMvbj3NksRC4M67bxeDXlzN4sI5pG+HkDWI+QhurzPnEtHgxmSpNzftoEjCxLTucw0de6EsWYq8+W65agsqz5YoT02LG9DUwIY3XBNby41PfYaLJssVPqfeUPI5lVQPzlEuzLctaCpy0bbsTAb3/N8uyngGeQsDvY8B3Sx/Ng4fJAr/v7+83Z7/X0juZYOzjQjkWeY8XbN4LLq5/5tWnbH/Bzz/H4pYeDq1bkAfZ9r0/W6wRcBLL6rWbpNO++7aVjnluyjO2A/5IH43SOE8gDt/W9ioNFXEujB7k8GgT3zm4CoBZtSfZsnsuALFdYQfAADhxURLUUrfkBPcu/ncOjzbw5VffQebnQshJYIGucTlIsWxyYz19FOAO8s6aYmXCX/m5nK+K2FSTwuraKuQCs+UGLwuCvn/5Nt5Wu5NHBxYDueDfx085fm1mVx3n8EgjU8MD/PDVi50UYumNDYzFcEyBcs0Bp4ZcckaKplbhuogPRxjbV81Yy6hTywvASlnMu3+YzmtiVPXkTHFtiqauPmu9N690gT/k/L0SGHtZIYzmeeWAdOAuAVKb/WDCFcvVfZXge/59I06gPeBKTpxstp3QC9X8B+SnklI1dUMxTsmvyr+J5Jxc/SuxaIDrYCAPTvpagvv5OmPw+7/74vjg93/5uZL4ysLmf2P46N9s2/5Qts3HyAVEPw983LbtbSUx58fDZBZkkgrFHXm1LcasKE/8TnyRIS+iX841U59eoQAmHpfdso4//8uf8OVHrufAX3wqv51HnkZ945btXTkFlRgquRnWHcy4Kv06GedXjfCV5f/J1GA/CTvM4VERWdsa6md/agrffvlygttqHEHW2xEjMRWnwjNAqGqUjvZuUmlRtuXAMdHH7Bt3uDUJNTO9WoRSQ5yB2CSlCU+GHajmST1WyHNj08aUwlKtnDw42yZdaTPzvCPObXfN+zEpO8j8igSJ7Lv2iQPvozGS4JbWx+gca+S2J98PQMNTYZFsOZJmxcJ9HBwQCL6e43VO7sGqHhyfWqoh4+RPlLkSAWeOg7NtxmozjkYsSc+1qMZJ6eZsU3YKLyGgCw997Ry0YRZ96RT+VARSqiZX4VqGBci4LTVmzRlTO9QALtSkyoOuQeXNV33+780vSuoiTZDJvrtXx1x5HU3vGZyhXItnSJC9Gaica7FMZSpTmSYjSR9ZqT+CnrIs6+Vsaqk3PU16jcxUeryQtqW3Nf3vd18x/UryQzkWcw3ESTZ6ImPUsIoCmBhMMCcWB0jNzaUDkuaf2P4gbXdvduJupI/owrfv4svtP+czXe/kLQ17nCz3AD95pYP00Sg1s/oZ6BbfUdtjFrGuYfbemDNPSsTa1DrhK3v6SWGOEwG5Bh+EQTsD4TdMtGe48KJ9pNJBJxA3sbs+C+7QytJAflC1roloWdFlXJJKco2IpJ3aYOc19HBdw3PEMxFOpkUG+UPJZn6/9nkag0lOZcL8c7Zo6YlUjHBgjKHRCPNqjjspnb60/R0smnaUrv+Y42gzktR6ZLFdYee6WptNUlVXwMlW4jK1GbRd1VTmqpmG/zPrqb2pmpoaVKxlyHAVsVTjAZWcmq53UuPXxYtWb9A1RpZkFhw1Y74kpxyLRw5SdR0hpyk6+RqzpmcT+vFM1COb/rUvjU8j++TfTAhfE0mTBuxxXd1NrjIuzgOvvYBrAmuNzm2d9JeiWIHjZ3YBjC+eqc88BKUPv44Z5QF3H8UIXdm/vGfe3V8DYKw2TWV0FAgTW7+V+bIrCbtedSfdf1rBp1f8EoDfi+3meLqSp59cyM6FUxk4kd1sk0Fi+4OkLxskub3BQQueWBwgtn4HwetXcHKvMKFNXXCc6nCS+bXH2XZ0pmMqgxxaTl0XNY3QyhvugewGMhaDe97xAyqsNC+NtNMYERWVt42G4JmYKwPK7C4FPCA3NQxAD2UTlj6Q2PqtjikqVQPz7xPlY9LRAEc6zxHTXx7iwupDzKzo5fyIiAmtr97Pk8NTWFDRSyKT5r1NTwPwUN+FHB2ppXc4xrToAJv654v5JCp49TdzSC3KkKoR1ZMBiKSZ/8+jdF4TwxoMMSaXvDVNuiVB9Nc1BFuHCWbRi/FFKQ5cBMFrVpKO2s789ZRY6jPRrPxtIv0Z0kESsk0ehD0bvuBaY2Wd42uX50qwZKHusm0emlftFyWllx7crNWSA0XYaAeZZbesY7usW/ZA7ro0ibKiw5XCTRXYcl6OWTGbNUfl+0xUiH6TwO/PCE0aQaZmv/eL+yoZLegjbIr5zHWC1AAEzj2K3d45BRfJm2OXv3tzDllm4Mf0v0nDm60L2vfAmvUGB/+WHYSuX+Eg6ADmho/SsWovAM9mNa+mGX2M7M/NZtpG8Tv5oV6WbYejnadIjYrHsDkaJxxMs/G1OaQ3NlCnwOz1DAqAE8sDuRx4IHxHJ9PVrIzu5+cnl7Hp4GwAah6Pcexi2wEbAM6GJitWy7iwVA3Uted8Mqp/RvpFo2uXO762wdmWU3cruDvmADbiyTAzK3oJW2l6xoQA3W+HOSd0im3JGgYyUe4/KtCJMrbNqshw/FQ16dGg87+E6AdX91GZXa9YNMneW6oJdovdpyoblZNsFVlSRjrSTKsfovpykYPxf898hOeGZ/FvoeXUZOOy9t4YpX5XwEmQK9dF96/qBzS5SXshd/3AFKqFRAfxqAAeU7ybfgCUFZwXfHGdU3B0TWAtwzevdAmnzQ98ipXc4xxiVW1aHoYkEtVFaiFNcjXj2LIDOlbmv9tKsuLhpoDDt3pQWHnDPfxyw6epq/ty3tqcVvodEmSTxrTolTRYp6LNbeOEyZdyvx/gRAWSOKg9Q/uVN9zDx778I77wwxudF1ktdVIqzyahZ9qY4muX8+EvPUg8I9JfVVhpplec4PBoE0dS9U7+vB0D7Tz37FzqdwVITM3FTFnVo1w4+zADqYhT+HJKeIBjqVqeODKXyPca81GEknQzUdbc52R0n5Pmz97yGG0Vp/jS9nfAISFApIZ3apEwx0mqvP4obdUDhANjPPcrUQ1ZJuNNtGeYtlGgEkGgB8ODiCD04xVCKAIHPgGRZ2PEF6WIdIYd5N3M847w/YX/DsBo9lUbzIToSdewL9XKV7b8noNClJppsHWY9NEoU7MB4ye3tjrr9vaLXmRx9WuAKNC5/onl2GGbtsesPB4TU6H6kl4+Pk8AyhaGjzBiV/ChTX8MJ4UZUjc3OlqSJjCMpUkMRUD153Px7escU7TTVwFB56AENWuKCqxS+9JNlC7hIkkF82h8q5qVixQTqAT1SCBKb0fMFQriaLV69QKPChpnxLR4953jMy3e9tkJ4WsiadIIsv7+fidpcCEfmBeSCLxfyNcr2NQ+vPrRQwLkye7EYhFXpL5MgIPsGovBtFWv0fWcqL40+/YtJfGp+pZkFnAVRmzie+UN92D/yXE+OXcDAFOCg/x2aCF/3PA0Xzv+Vrb97SUAHHvvMJFnRVLjvo40VjbINdgqNoDZU044fS+pP8Kjh88lvbHBqWQMeMLgVV76ZwUc09q5V+7nf09/hAAZPvjIzU57udmrGdRHv3iKmTV9RAJjzK46Tt+o6OTJo3OJJ8Mi637DCKGQWHMJd58/q4c9r5zjJOGd2tIvtKijUWhMOYLi/nf9A8+OzGJVdC8phIZ1cLSJUTvE5557JxyqItKbM6EmLhih6oVKZy6Aw+uemyppmtHHE0t/AMBgZpQbd/8hPf21ND4Q49h7s0LoUJUINk4GadgRZPhq4TC7ds7LTvUBWZlaTRSsa0fOd6+HsGhIx/GQ17tgQj2atB7AWCVAJ9XPteCL60Tgs+77VISN7pdzhJyiudcdzOSqTRjg/UYhrQnPsUsW8PhTX4ayIDst9KZALVqW9eeWZR20LGvEsqxtlmVd+kbzVKYylalMZzPJgOhSf85GesM1smzRtftwF11bCxRVdM2EWtRPe4VynHmZ0AppTX70ejU7NS6m6WMHefHlmcy/b4Shzw/R84pIfxTuCzBt1Wssa+rip88vI3RcmFZlTa1CcXCyZlR8TtoBZEx/34sF+ZNzWLYdB1k3P3yUk+kqtsXn8dNvXemg5Waed4SmaIJnXxQpq+YvEGax/z3zER4dWMzRZK1Td2r9E8uZuuA4Iw+25pmWJE+m07T8W2bzb6xK8KnZv6I2MMIfPfIRp0RLslnEeYX7Ak4BzSPvympPjSkunH2Yg/0C4Tirro/zao7w/vqn2TY82zGVfn7TdYSqRqmrGaZ/MErkWaE6JS8SWlN6NIg9GmDFwn0AfLLtV7QEkmSAw2NCC6q0Rtmdmsb//Y+1jgkScGLCpNlyLJstvuEpUQlhrGWUW5dvcKps/7T/QvYlWhgai5BKB3nxZeFjm//RbU5WkIYdQVfcmV0zJvquFePOv2/EHYfngWD0qiyRhxQ0oWu1eDQX8ELNgmGIB3S+d5NpWYkNU1GrKmjHKy2UjnyU96uxbjJgXy15JM2Hso6Zbh1puzuX+m3GIwJhqmq9cuwzEUc2467xaWSdt599GtmbQZAVVXTN537HR/Ybd3VtoDi4eyHyA0yU0r4U/5zJ3OKU9lBezu7bVpK8KM5YXyVtjwkT1ZHVMO8TW32FqLou797Vyz9//V15voc8gAdus+3i29ex8Lo9AMyoOsnPN1xKcNhyAnUB0pcNsnhqD+9qeZ7vdq7knxf8EIA7u6/l0GAD7z7neRZGugEIYPOD4yvZ+sslNO3M5JmN5LgOqCULm5YCf+gD/QD8zXn/zYzQSVqDI3y++x1sP5pFEG5voGlnRsDkI0IwRTrDJFvTfOGqn7AwfITWoCgZ8uvEPH4/to+TGYvXxmqdKsbzKo+yd6SVRdFujo/VsHNI9B0KpLmsZj87E+dwe8sWusbEd9E51sDRsTreWrWP55MCPVkfSHAqU8XTQ3P40dbLHHNruC9AckYKkkFq2wZYfY5IIfZyn5BEqX+axse+/CPmVojzXcCy+edjb+XV/hZ6+msZ2yfg/elK8U5P25grYwLCtyQLaaqABBDglp13iZRUIDZhUzkk/bnUgRt+f6v3ueDyWvJn1Ryoju/1PEvkqMkUrlPnHSsdU61KJkEG5AW+j8XEgUB+V9agAN6E+wIOwEeW/JHJBAZn2yJ7jhwrIypET7RpsSzIztTgouhaAnifVlH034B627avM9wTQZRWklQDdKmCrBCIolQqpNlIej0+g1L5keOZsi903rGSGZd30v3wDOKLUk6RyxOLA46PwG9DKjQXdQNZ82fipf38lKf47NEV/PzVJQR3u9MM/fDPv8bzyen87PhSrm0WGt+jJxfREE7w162PcjDrl9o/OoW/33slmZ83OxkeIFchW9cKZBotmSGk7VqhHV415RX+V/0ODo5VsDkxjydOippXqXSQ3uEYzdE4jREB0jg02MClzYf4Py1beWU0xGtj9QC8JXqMnrRFzErzjd63ckn1AQAqrRQjdja2brTeWZOZ4V4Who/SM1bDiF3BrAoRG3cqXUnCDtMRPsUro0LQ7Em10hgcYmmkh58PLaY/i2Z8uPs8eo7XUVM7zB/MfYZ3VIu1OpauZsSuYH9qCnPCx5y+pwZtjqfh8cS5fG3H2xjrE5uWlbKcdFWx/UEHrt/2mEX/rIADSIGs/03xQaqFRT2BH4pmpdb7coWOaN+Vep8OujA9c6qP2CvzvgT5OFW2lQwipryMKhJSfYZ0LQuEMJJ9H1mNAw4anG2TbktSUyvWJjEs1lGGOITiudRiNQcsmu/dzJ5vX8b8j25zCfcfn/rOhIM9Zt51J4HKEgXZyAiHhCB7BcgA37Rt+5unk7+JoDcafl9U0TWN/hr4vOkDdTP3i/HS26unfdNL5bepn06B6UdeAtOU+mrNqjuJ72ynbf1mF+JKvd91j1JqwuSo7r5tpauwpLy/ryPN4WFhirvnRAdLY51srZ/FSE+Mpp3i3mMX27z/e5/k3Cv38/H2X9M9Jto3hBO83DeVR6rnURUQJsF7dl/NQHctsRpc5eTXdJmzjIMAkIQGAlhLhrhqyisA1AWHOThWQUsgyZrYLkfjmx7q50Q6Sk+6jlkVAmTydN1s5oaP0p3OkLKD1ASERhbPZOgea2BqcJD4WMTRgnanprE0cphXR6dQFUhxc50wld7bfw5TgoOcExqg0srwWhatkSHA9FA/h8YiLr73p6YQCyTFTzbB8Kzak0SCYxw83MKx6bWcyoiNfDBTyYWRHqaGBjg82sCelDAtnwzGGchUckXVq/QvifLMqVkAvPTr+Y7mWXcwQ91BofENNwVINttYgyHnoLH3xijTsmEGK2+4h2QW+RjbqJjmZJweuaBf+Qxs1t4Tl6ABo3CTbeXneW118322YOfKG+4RpViUeDFXSItWeifeHnUKbMbWb3Uy3XdeE8uNKwOat+zIwvXFmnfftpLwoDA9zzvnGEdnZSGxw2E+s/QRnjx1LkNjEcIBkSfzYH0jkeAYyXSII9mySYOzAwzetQLIuNZwc1Yjm3B6fdnvLz2bNLI3WpCNh/4WkU1ZUg1aWe48X4oHmYRVsQLIz1dWjDZTyBdXTJ+ewmdFBycWBziyejnzPrGV/qwv7JXP3Wrsz2v8DZn1zPvRnaRHRxyfi9w44muXEzkaYOs+EaN1wbIu5lQc4y/m/IbPzb6BxFQhPKc8k+HYxVBd4S4w+4sXzifSGebLDdc7VZaTrWkiR4Mkm22GBwPueLjsuLnSM9maUbNEQuP5LcepC4pN9oqqV4nbFewZrWcwU+nkfXxxZDr1wQStoX5OpoUWtCb2CqO2RaWVYWoowcm0EDiDdpDLK4f59XAD72162tHUrqo6wPPJFkbtEBdVHuTRYXHibQkN8NpYA1WBFLNDFnFbCMQ5oSCPDTfxVHwue+MteWv81tgrVFpiMzwUa2Z6tI+De6eyd7CFgzGxIS4MH+G3w7OpCQzTEhzk/Kzg2zMWpNIa5Xg6RktokI5a8RrsXDKV5CVJrL2NrqTMNQckNN9y/GZVPeKwUXPAIlWDU/LmwPVVTjJplXo7YjRv8Tbf5Wk+8tkyBErnUTbY2QudaspcE1+7HLRwE6eEkZInUQ0tCMVx5RR1kIlbdjjlasZi4qexcYjK4BiLW0SQ3pfbf869J1bzhbZf8H973u74d5fX72fn0Dm8eHIalS1C2x+JRIh0hp3qBjILzuLb1zHFfyVOD/0OxZG90YKs5KJrtm0nUcpuW9bprZ9TpjKVqUxlOrvozQL2eMq27b/I/h8AOoF/KAXsoceRSTI6m4u8VsxnpZJJI5N0uvx3awJr2fOvFxPpDNO0U9j4gbzs+IX6kQUKnbQ85E6yl3z4eU6kYuzoErFr7U2n+NLcBzmeruG73avZ/18CpZi+bJCxfdUsWn6Aj7U/6mhHrw5P5b9/uNKF8nrlc7cy7+6vOWAFCRiRAbV55qmsg77zmhjTVr3G/QsFkOS7/UtpCQ0ys6KXWRX9TkaNnnQd/3T4cj4y/QkuyZobW4JhRuw0zyVrOJWpYmFYWLm3Dc9mQfgIGQJ8ctdaljSJc9X7mp/mqfhcllUdpMJKMzUkTuSzQqOM2BkOjsYIW2lHy6oKpOkeq6YlGOfxhPDVfW3H26irGebyafu4qvZlZ03qgwm++ML/ENWRD1XxnrcLgMAl1ftZGD5KEJvnk+0sDgveG4NjjNowLVhJhgz7x4QvbE+qhfXHL2Hr0wsI9wWcjB/RExknaDo4LH6rwJydd93q0upNGpSj2eiBvnr9ruyztOyWda6AftnWlTuzSIRvMSArdXz5/IIwJzbtzLhKE4GIo0vViGdsz7cvcyFcx2ozXHT+fk4MV/GRmU8C8JZoJ2kbDo3VUB8YZtOwKMM1NXSK/9/em4fHcdR545+eGc1oZnQftiTLshzfVxTncGzZSZzDCQmHw4Ixuy+bDfACIbzs/kI2BDYBQggsAYx3lyXJwnJsgAVjAjGXSZyEHL5ix3EU23F8SpZlHdat0cxoRjPTvz+qq6a6uqqnR7HsSJnP8/ixpru6+lvdXfWt730wOh2Hh6vQESbe0y3HqwBfEp7AKAqfD5ocSIYL4zjwo38BxtNG9o2vj81G9i/3jQtd44m3AyNbD+B/AHwK6aJrHwIwX9d10XYmu96S2QOwMjPxmAz8RKEBwarJ5nRSnYugUScu/Pwkpnax8EVJzPm0ueRPJmbNG/I7VgGfvP5ZvD5Ui9d/RzJeHHrY8Hy7uRV90QDunvMMAOCbh2/CnPIelHvDePrgQuZg0rGKeHQtf9dBXFp0CtMN29Tu4dn49f7LScVozkgfqQILKXj+B1cy+ioe22nN+GAY6PWPd+PBOVsQSpFJW+4O47WROvyxcwmOn5mCz1z6PAAg4Irjpf45eG9FEwpdZIHrSxbgEt9pdCYLMSevH/tihDEfjk5DfyKAAncMm48txaIqwg0WFnag2juAntFCXFPwJkZ0Ms7V+SPoTxF14pHRApQY/R8dJUqkK3zt+GLbe8nY986DXpiAr9WLpF9ntdGo6ilemoJvWtqzLuiP4W/rX8FF3rM4GJ2OtUX7AQA7orOxJngEbuiodufjF6FaAECZexgvheaZvEgpSg67TI401Fmm/FCKBYsD6d+mdF4wu87T74aHeJy3Y6m8FHlIPWv5xNA2m1CZMwkDH04AsMTLtEYbdXKhjhqB+QMI+uKoL+rDxUVtWBU4CgDwakmcTRaiyDWCMncEb8aJMumvgwvw572XwFM6gkSErEM0HIaqbfln/sI3Pz7uzh71Xx8bI2u5L8fIxkbEWyi6Rl/ako9/A6//9xcByD9sepzirUppIuw8JWX3OxegxuPY7X0Yeb4i7faL9AJy/E43SnaQj5kyAdHZg3c7pmme7vvEr9CY34ojo6V4NVqPn/5mDQCwNFjHf3YpftD4OKa4hwEA3+28EWXeMJ7+5ZWI1KZMRRHprte9qh9fWPAUAOL998Vf3Eb6E+KV3v/jZxFJefGfL5J7znl8hIUf8MUmA/MHsLz6FP6+Ygfq88L4g+Eiv8h3Bp898GGEhvzw+Ufx7Ut+AwBY4u1GpduLUT2FbVHCYEZ1D/7Q04Bdb85CUXkYM0r6AQChuA/VwSG0DJWRemDDZFGaM+8M8t0JVPuHcElhK0Z1soOfnteLvmQBrgmcQKXLjYEUkchCuhv5Wgq/HLgcP2kihSUDr5P3kQgSGxUfp9S7yIW6p8JovjWAZA3RoPv8o7i67gTmBjuxtvAAkzAHUgEsz+/F7hEi0Z2MkzGVuCN4rPlqDD1LFtlILel/9q+iFrd7mjastMmNeGE6az6VHppvDWDKKzprTzcU1FOQfkO895+lvpngnUiRyZYtbhrFGDP+PJ+FHjDnTwQkGUNk8XJIM7hIbQpls/tYpe+vzvo9AGAolY8i1wjiuhsvDs/H7t56AMDxM1NQWBRFaMjPPBpDQ37MfiTJNmi8239i5yvjHkdW/9AYGdn9E4+RXWgbGQBA1/X/BPCfb6WP/L70YsA7bsgmiiyuxbK4ZxHzJetTdS/x2rfC4IKbd6P9nkYk9lYgXpsyBWIuvXMj0BCE90R6oexpCKL/E5dbvL+abw2gYeUxtA8XYaC7GADw5Vffiy8t/TM2vHkDCn5ejCObjBidp9I72KZL61DpIStfPOXGH7YtAyp0uEc0uFcRhlDw82KDWheiox5sH5oDAAgnfPCEhWDXFQ1ovSmIY9GpuKKgGbdc8RoA4NinYwivW45EEFiwvBk3TzkIgKhzAGC6J4wRzjvrKyfehznlPWiKEunqD31LAQB7fEOY4etBOOXDJfnEVT/gimN5yUnszpuJskAEV5SeAgBcGTyOl8Ozsb+9FoHX85lrf5E3ht5oAAdOLMS+qbWYW9oNAPhd+BLcd9Gf8OfhhVhbcAhlLsL4tgzNxdqCQ3iuay7ceUT1F6vQmSNF860B5hhDNgnLEa71Y8orOtqvI33EADx3cg52+2fgCd9S3DHzRQBAo78FI8ZG1KslWOmcrScXIuiPIVKbgntEY4maj3/YD/cIkbIG64PsWyGBv2kmBhD1F5PIAAQ3p130Z3/7u/D3wpRQN9oQNH1TjuadjIlJipyy+Sxxrlp650ZUrGiwppwzPB1ZvlKOBt5Ra+mdG+HvJenfar69E94GModiIxpGnq/ACIh6/PYdHwVAUpHVFAxh39EZyC+KIXYm7ZIUO5EPlKaQNDYqs7eHyZxrIAkH+HCCLYOPU4ls/JBz9sghhxxyyGEiYywpp3Ipqi4QeGePd33ihwDMGQH4TAGmekTIzmYmHsukipTGqDlMb5WJJtFmcOzHlwMA8ouIGsT9ciHLAMLsSjBcp43UO8G2KJr/ifRZ+HwQ0RtC+OfF2/Cdg0SdN72sHx+t3YkfnLoKz1//HTae9nsaEb6IqKIGFqSwZsXrAICjg5UYfGIaSwzsHklnYqcqtNBM3eTI4Q3BlEGc0jiwIIXFl7SwoOUdLyxConIUReVh3DH3JXTESwAANxQeQr42ijOJEszK68F/9VxD7ulK4MmXrsCMhR1YWNqJi/xEato3OAMd4SLcPfNp7AnPYn3EdTdeic7EL09cjrvnE5vfocg07O+vRfPe6bjiqjfx/1VvAwA8FVqCl3pmoStUiBkl/QjFibv+VVNO4JNlu/FGvBT5WgLTDUm1zOXBQCqBXw4tNalnt6U2M2mAqu3o3/z/AMm8/zc37kJXrAjxlBtH+4kb/20zX8Yz3Qvw+elb8bOeleiNE+lg34GLSDLjPi/0wgQr8tnWWwL3m0GSSd/IbOLpzsOUV3SWdNmT1n4hESRVANxRjTmMUFsPLU5qSgWlUCGKSYfZdwy51iRbdb6dCYG52T9mzcAPgGXLoUHUNMwkeNLNVOKVN55By2nyzIOHvQhflISndATJLj+zZY4M+YCYG54hF/vG3SMaCYpuSmdSAc6fjWzmg2NTLTZ/+T5gggVETxpGtnrZffB4jJcmZksXqgiLRmM7T62xBjy/FWaZLeY9uBHlh1IsRdNQexGpwCzYCWjNLhpovJT4DOBEuBJNO2YzpwOAVDtesvAU2oeLUPbuo4zG+b99EIuqOjF0Tw2abw2wfIBayAO9MIGarR6WrR8gNp9b3kfMnXP8XfjZKbJQdHYXw3uCvC9ZyiB+kWxfFcQnP/onLPefQL6WgMvYNr46UodLfKfh0nQci1fiF13EBnXwmTlI+kluwvrp3chzk0X7uilHMMPbiyvyT+OkkZUjX0ugZbSC5FDsTjsL0Yz0+at78M35v4XXyLW4qW8Z3uivQudgEWLRPCyfRTJ+HOquwvXTj+KW4iakoKHTiDsrcw9jVHfj0dOr0fpinWW8PQ1Bllpp0b0bWfkVgJRgAYDF5Z34SOVOzPcO4LVYJbYOXEzee6ATL/bNRftwEboHCliG/tKCCDqaK8iiWpOO3/vMpc9jhrcHX2pKJ8wpLYigs7sY7nYfZj4ZwbFPpB0V3FENsakk4JzHzCcjaTUZtwmh4PMeinMOkOdn5I9TWNpL8jCaVJGSzP0yT1yWKQZpVaOsuGh43XKcvVxDsibGvtWk39iMlcXhbvcxpkW9Q1mWEYB5RtZsT28kAWJ/TCRGxj1F1cyvfmNsjOwr4+NNOZ6YPKrFPQcR/tBVAEjk/BrXOpPtC0hPDLFCtJ2TBvvtIPEw7cvOgG3R+79Fr8Ztqc048uW70Lh+A0JD6V3fzk134+KPfBlDvXnsnokHGjFY70K7IcEtxSusfcPK4zjZPIclN23ZRCa4j9tJAkDZpiBOls9B5CZg5r07mZE9Wu5CaPUo2q9zwzOkMw+8S288jL8peQUDqQD6kgX4cB255+h0N84uLoLPlcCWpUsAAEO9pNJxyWEijdCJH7l4BAt9Z3CJV8PumB+vjRCGMKq7ccJVgXJ3GPsj9SwUwBcG4rNiKCqKIhT3oa+PpIb64exf4YXoTNy8805WPuZ0XylGhnwIHvYyyREgNctm/yqKYwuKMDA3gCLDC/HYUCX6IgEE/TFcV38U+3tqGe1bRxfi2by5KAtE0BchDhmx/aWIlxJbldt4htt23M+cIyqQrnhcAyJBBDoJMxtNkCuGEz6EUvksldenK58HADw1vIgU44y5oRWMshRVHUM+wJdEYP6Qyflg3+AMBErjWDdnPwvO7hkJ4tKZp/Fq3yw0/xPgwahBZR7L+5goSqG0iVIPZveZ8+mXTYHF/OZDdLLg55ydp6NK22HqU8H4xHRYJvurITHulEmMu5rSGT44D1p/bwq+Hg3Fr3gRJf40iFRpSFSOonRHPiJV6byW1LWffPekL14rAqRt1dt23I9rtVst4zvneAfZyCaNRMZnv6egcSSq5KemD1qsuWQjUalUiIA648e5kLzs+mhcvwEz7iIpmva+NJ84C9ycQPnUIZQ9RJgRTWBae2k7TnWWs5pZNLOGmCi2/Z5GRC4eQfXvvSTRLgD4krjl4gN4+tlLTRJctNyF6A0h/MP83fjBs9czBwPvJzvwvbm/wkAyH0+HlmCBn8RAlbtDeDVaj8X5bSx34AOn34c7qv+KET0Pv+m5Agd7iWhSUzCED1btQ5VnAFXuEGZ6iLS0K1aAvwxejN1n69E9UIDa8gEAQMeOacTz75+A4sIo1k4nOQv/9+jlWFrThr2tdZjyRNrwTjM7tD7QyLwysaKBebDFKnRgBlFzut8MYvm7DuJjU17CDE8IL0RJZpOftDbiVGc5ysqGMfJ8BXOc4FWHNMOGrEI1fT/7H7mLODA0hZnq1+NJYVFVJ15tno7Z087i+BninfjJpS/hv166Dp7SEVY8lIJ6GvY3pNWI+UUxlBZEsKSsA/u6CQOuL+7HwWfmIFYXN2XFpzkaqaqMfiPlh1LMs5Iu9vQ5ygq6qjJ12GXw4K9T/eaPy2LYVKp//jx/T1FSM/UlZt7nirmaCnIa4SB0rjCtiHDP8Lrl5yWO7KKvjE0iO/nVnER2wbB2zbfg2UsWcvqh7VRMIBFi7Bh/TMbQMsViiccoTdLzWdjNlPdd+RCCu5pw9HYScEsLay69cyP2PfJ1rHm3QUNDI3w9GgafmIbZkoq44hjrf/ow/v7iPfhl3mX41GLS/paCA3g+Mg8v9Gg4ezlMRSFj0Ty8PlQLb78Lg/XGwaen4bYn7sZFHzmGB6b/nsVdvRCehx8dbERDbTuTpJKjbmz2LsOD1dtwsugUriwm2d874iUY1d14OTwba4v2Y1eMSFglrihaI2XoHw7Aty+IjiBhPEm/jmO35cP3phujS+PY2k6KSY50B7D7zDxUzetmXnu9Rjb01gca4QmnCyT2LnKxKtFTXtERfJKOMoxXwouxf9U0fHzOThYXt7C0Ey2nK1HojaGvNoVEP80qT2xPdU+FUUHX2l1NaH54BWNovB1nzWM7EXmgEX3vjWKlEYQ91TeE0rwwmvJq0PpiHWYbzPa/Hr2OhQOU1Ufw4stknIE2F85eDiQqScLowXqyYQkvAPoOFuLpqRXwdREJq2m+H74wgFYvAp3AwALyPmMVOoIn3Sx5bn8DYYbtU4HgSRJgHJuahN+ouIAVDQi2RU3u9vz3KTIb+pxV8yGbTZ8svkwVciOb/2tc6yxrBd1g0PEwVSrAxhEvNBfUpP+XlpP3uXPTXVhavjG9OTG6Dm7ejeGPXep4fGPGO0gimzSMLIcccsghBw5jKZQ5QRnZpFEtimVcpMX7OM8qEdl4Tql0+ZkcPEzZBjgVhZN7ymjl1ZmtNwXhW0pit9xbS1lszKGH7zKpRtpXBXH5Bw7ixWOzMfuRZPrewq526Z0bkby5H8ntpShuSTF1yWVLTuLgM3NQ98BOFG2vRF2AqAXztCT29MzAjMJ+7GiZaVLdYUUDhr8yjMfm/wIBF7nnF1pvxb4DF+FjK1/ENQWkUOTe6Ez8sX0JllWcwqjuxhQv0WzU5A2gPq8HNZ5hPNJzNfoM77yDvVWYW9qNnpEgjh2ZxpK1lhZE0D8cQOJEAQLzBzC1kOj5ukKFxI7Y52WqMk+Y2DJo4C8dp6/LzTz2PGGYUnTRZxu7LIzKEhIQHo55EdtfisU3HGMxRpSWAm+MqAM5VS51DNi56W7mVQukM23EpiZxzdLDAICrSkhWiWf7FmDvS/OZXcY3LQxvXgLvqjuM0rww3hwm9c6GjUz7b26ZYwpOj1WkPRCphOUpHcGUJ4htq/WmoMlrkYJ6L1LMfDKCY7cRldWcx0k2E1nxTQrT/DOQjfcwoFYLZqNCzKQx4WmXOpqAOCGJziL0PG/7pH0yu6FQqDShj457QPRF938D7ixVi8mREZx8KKdavKDgA2t3brqbBUWajMmysidjzOAhvUbIFk6vCa9bbgoYBdQpdzJBRXt6weBy2z18l+na8II49ndNw31X/BmbcBMAoOsLcax5/i7TxPevW47gN70AyMo253FyfUftLGARGefQPcCL95OyLGunH0DbqzVom1GCwueD6F1E2gfbyPPoPFKJo7OmYO8wycH4avN0AEB/Im3bqckbwLfn/AYjKQ8+f/SDuGoqqbJc7I5ihieEvbEaHByoxrEj0wAA9bM7MTzqw7GWKpTX9aO3ldDSGc1DWdkwBme4kOdJ4lgLsbV5uvOgF6XAp5mmtix3VEPvIg2eIbJgx0tTqN4OBDeTwGX6jGd/+7sASDkUnAqgg6sB5jYWe1+rF9OvJmrB032lQAFw84JDODZEHCyKvDG0Dxehvb2UPG9OPRUE0LVlAeJDfiwpTBd1OBWrwN9U7kPVmiE8/UsjdVdbIUK1KfwFCxAf9WCkmzxLz5CLOCm0pAC4uEBnDfmrezB4sJwV8yx8PojBeiBaHkSgE6ZQjdBMHTOfjOD4nW6W2cQz5CK2u0gSpXu86e/KSGk2+5+M0ju8c5QkFRVg72RlceRQqPYz9ZvR61jw6qV099zRyMwMjes3IGgwYX4Oh9ctNzFCuiGxC9mh58+Ls8c7CJNHIpO43wPOci5K3XoV1/LH7WxeooR37FFSCZglwqWVniVpdN6qU4gKjes3sPLsM+46gt175wEgEsKH3v8inn1olbUqs1BGvn1VEO5V/Zj6Ta85jggkQ8jH3/0Mft92Mfp2k/RInjCJO/rUQ0/g992X4NV9JH7rvpuexKMnrkZvV9pBR8tL4T9W/BIHR2pR7I6iZ5Tky/pM2asIaHn4du8SPP7GMiS7DE/KsjgW17XjYGsN9OE8ZveJl6aAsjhZfH1JVkSS0hO5eIS5U1PnBb4gIgAmidFwBd6O1fpAI5LzSVVuvrozQLweB1aOsH704TzkV0Ywp7Ibf1u9BwBQ6R7Cj7uuwv72Wox0B5hHYGhmupxK7LIwigvTz3bt9AP4aOleDKTc+PXAFQCAPz56NUsEPPPJCJpvJYwsma8zz0/qmAEQuxaQTkkFEO/IQCfQvyzOkkxT0HHTYpIASZdVVTyEcn8EvdEATr1BpEDdq6PmOY0l5VV5KAKwxEFS2M0rJ5DGboo2MuF7toQH8BoTSitXhZyPRaXSOQCWGYR3eKEbWP48xXmRyO4bo0T29YknkU0aRibzWqQYa0yX0lMqg4OGWPyx+dYAAvMHcP30o/jz78lumi4YOzfdzdLo0B1gNnASmC0uKq0PNGLxDcfQMkgkmLJ3H8WxH1+Omq0eqZcVj/Z7GlngLE24yo/52G358Ay5mEcjVS02/xPw/Sv+F1v6iZH75pLX8R+t16N9ax3LBegeITE7H7l4D1YVHEHccAwpco1ghieEu1vfj6Yds5kHYcAfx1B7kZmBgTAV+nz5NEutNwWhLSbZ+Pn4n+T8MJJdJH0TdV6hKrlIbYpVB6aIF5Lz7qlRliCWSic0p97xDxNmW3KYqArLlqfzX39g+n4MJgLoHQ0inPDh5bYZ5Fn5Yxg8WA7PLKKu9OaRfI1fWvgnjOoeLPGdQYkria913AgA2LH5EsQqdCZ90ZCHI18mzgXxQvKOTJWWhYWaJpimsU4UYk5GKqkd/7AfH1m9HcNG3bY/HF0MAEh2+RkzE2PLpMHQQk5Gejwb71/V36q2jB6Ft6SlUjq3yeTVv9QT2qINETam1PuUHueDon2/fmncGdmsfxkbIzvxjYnHyCanalHIMiCbLCoX+kwfOOtfcf9tO+63SCrJmhg+OPM1/KRpBVM/UclozcqHmDdTxvFJJqtM969UrRiTKdAJ7Ds6A8HDXqPN11H/04dR/U8n8MQmbszc+GlMFwDE6uKIhzzoaQiactn1NATh6yI7/ODmXabnNRMN+Myt/xeffe+fAQBbBy7GsZYqeC4Lw2uUiU/ODwOjbvxs33Lsrq/HaNKQVOI+XDn1FOJJNzyzhhH0E+mgr68AWsEo4nGNZZOnoM9/CvxMEomXplDyTKEl/mcwHGTMlMI9orEMJv0NScYstcVET6cP+dBQ246he4jHZfsqL2EavWSx8jKvRXLf7qYpjEn+8cYl6IsEMLUwhOG4j5RtATC8twLJWSMI5CWwdOoZXFpE8j7O93YhqCVxJhHEc+F6hAwbWKwiLcEN1qfLtcx7cCM8HBMzBfrSRZVXZxpzpXH9BhPjCtf6WeYVGopQchj4OVZhzYrXsajgDFbWk4DweJ0b8ZQHr8ZnoeRwkAV1lx9KMemFd1Wn9+Nha8eSMD7es1BmDxP75vuT/ZYFbVPwGUza72k0SVt0PGKeyQqDxm2pzSbb2bbUZlzb0g/s2YIczg0mFSPLIYcccsjBwDvI/X7SqBZXL7uPxZHZ7eyyiQHLpp1pN8jZ3GiaG2pzYTv/sjj0URfm/HA03QmXWms8QGns+9Nc3D3nGURSRIJ56K9r095nHC1U388XKATSdcP4EiS0vD3JpO5iu2/RnkC9Autnd2JucTc+O/VZ/DFEUi71G5krNr+4HCWHXRhYQPqu3k7qmrmnRlFbPsBSTh07Ms1SfgQgUtChh+9iRR2P/zvZOetenaVbojYffdQFT3cefD0awgvi0EJkbxdoczFvveLFvbi6mjie9MWDePEYKaYYeD0fCUNQpdk4aKAwHX/zwysw895daH54BZPIEkGwbB9TXtFZ4dNAG6khV1QzhOXVp/CZKc8BAFyajoFkPk4atc0oHmu+Gt1NU0z2PAAsRVjvIhezfwHE2YUFYxvSDPXCA2CSGnruaGQFJ3lbELUnFl3fhc9e9FcsN6oIvBarwl/6L8a2I/OhD+ehqIZopZLbS1kcXbYeuqpgabt2ANLaGEnpFll6OqlNTdWHcY4PBgdgLjbKeTjSnJkmdeuuJiSumDfuKapmf2FsqsXj3/wXYILlWpw0EtmWbZ9nFaLFFFQMEo9CCpU7vfQ4bzAWmA9Vg5jyrF0eQNKvI9CpoWheNwCgwBtD+9Y6YNcrWTGuTIxUpEWmZglHfVgTaMNrMWJT1ApGWVYJvm1w825gU9rATcfu700hXuhi7uNA2rMruKIB0fIgKylDVTB0Ms/5NHlezQ+vwNxru9GXDGC2j9iP6oJ9eCq0BCiLo6Ipif2PGPaJ7RuIrak/iM7FKWY78nW54e9NoaKJLBLUBuHvNeis9aP1gUb4phEu581LADVAqKWY1QTjM3B4Q14kbyYhDJGREpYdJRz1MZf/WYFuvDC8AMGTbqbaA4y6XnVxhGv9hHn+jNgC3e1g3x1fF6x9VRDFLbRis87OX7bkJOJJN95V+joGUmQ8cd2NgVQAeVoSjfmtOJUgTjAF3hi6Qe5bvjU9lQOdQPvNCSDmxi3vewWdI+Q9X7ysDT+ouQremxpZW08YqP+v76DmOQ3tNyfgW5Q+V/dUGFjRQGyCVVzRz6WDCMe8WJ7fit4UUXOWu8P4xJQXsLrkTXzv5LXobiJMd0oLCVVQud7zEBmKylFLVP/ZzV3Tb2oeWNFg6c8UpgOYnD9oYmEAbBz7HyFp4ahdMtgGpnKkjkHEeYdcxm8YAGBoaAjFxV+3PIO3EZblbGQXAGuLb0tXiBZ2UKK0pHLUUE0E0eakqnDLX0P1/z0NQbijxFbQsUqH3k4cLDzdeZi5PWxx4ZUVvlTRyN/TqfQZXrcc+kEX7qu7ATMDhKlWVQ5i1yNfVHph0okJpG0b1P7CKgu0RZnNoOKxdA5GmsGi9aYgouVB+GvJcV+PhqcPLsQLrZfgng//FgDgyutFfyJguHon2XMO7mpC9I5Gw55VCBb9ZkhD1A5ErXh8/se6p8I4Pot8F17D9hSv7ETLvDIAgPajSpy9XENFUxTR8iCmfpNIqc23pp9BIuFiUtiLIP97Q0AiqDHJK7xuOaKdXgTbyDv1nkin/WpfRb4BKpG1rwqiZnsYrTcFMfNenun50DJYirXTD6DSHcLpBEnwd3xkKl7qmYWbpr6BnQAr5lmRH0YzqKNJOllt9I5GaHkpLJ7VhjsrXkQkRdp//+x1WDPvTTRPK2Njy3cnEIr70OKrxJJZbZh+MWHkx4YqkX9tAgdfq0fZ7B4MhghTXV7XikJPDLX5/TgxWoKBFPGULHFFcHmejpbRBHzuBEt11bvIjUAnLN58MgaicsgQGZbMNiZKUxQyhiVLRSdizcqHWLaX4pYUW1NoNYlF926Et9zF4uvoOz326JUshMPXo7ENXE9DkFWhLm5JwdfSL73vOcfEVrg5xqRRLYplXFTOHBRjjSXjJ410cgru9+33NErLXlDVhCkXpETCk91Xagy3u0ZgvMzD0Mh0XlQexuvvfdBiwKaqKT5fIIC00Z4L6OaZHV+uxdvvgrY4hKA/ht6uIlZSBABOvVEN94jGMuhfs/Aojg5UortpCo7f8zmL96dYzbf1piBLIwWkpav+ZXFoeSkSgFwWZxWy+xuSKK/rx+LyTrzwBknn5TNSM1G3euowQV3OvSfyES8lCYTpPWmANN+e5Rw03idl8B2rwEraUOmNqZp2NbESPADJhXh13Qm8q/R15GlJjOjk/QwmA1jia8NQKh+hVD5OjxIG970/3AJ3VGPqTOpgwcIPRl245eIDKHATNeqJcCXah4tQ4I3ho7XkHQ4kAyhxRzAr7yziuhuvjtQDAOb72hFO+RBK+fGbzssYjY3lJ0gxUv8JnEmUYI6XvM++ZACV7jAOxavwtTfejfgo2SOPDPlYJn0aBkDngZ1WI1s1v8y5w66iNP83jRnjvzda8qj1pqBJhd6xCkzt7e13IT6LqOTd7T4WbE5V4tQjFqcCcEc15kk7WO/CrvvGv4zL7Hu/AbcvS9VibATHH855LV4wrC2+DTu5zB787k32ATtysxfdazlYVBGKnSV1UV+z8iGTnpy6M5ukR5U3pIJuSpdy0gv5Hde41rHJ3XNHI2q2kol1yb0niWoQ5lpug/WN6F8WR/H0bvTuIEHINKkuZVz7d5if7exvfxeFzRrm30aydUz396PLUGEedScRS6Y/ucL6QRT8vBjBzSQjfvuKBvTdFMTxL5MwBEupECEry7wHNxJbV08+wgvi8Bou8LR0y9LFbRhO+uBblGDXtEbKcHSg0lSypaIpjPZ7CFOKE60dAvMHEB/1wLs0inhLMYvRShQlEWhyo/nhFShsTjP1NCP3Y41rHaLG75LDhLEGD3tNzA4gUkrpHhe7Z3GLB8EvxlDpDuFAbDpW+o8DAF5LTUeNZwQHwrWY6hlEnlFSpnhxL/qOlyFc6zephXvuaESkKh+BTuDZ1stI/TGQLB7FhVE0ny3HL93LAAAFeTEUemJoD5bgc6XN8GrEFujSdAyl/LjEdxobBm5g2VGeOzsPMwv6cGl+C/qSBWhPECbpgo7uZBCjugfvqjuMX+8mYSaeIRdb4On7pPZUU9yWAP6c1NUdglexsGGzqNONDZrlnisaUNEUZp65dF6y+QnCmPzb05dEqoh6+Ngn8pDvN2zcs0aROFGAiz5ynIW1DIb8KC6Mon5lOwmAn0r9k5NY9uXxNzu9kwprThpGlkMOOeSQA4d3kNfipGJk4k4NgCU2RBmLlaH4n8yuJraXlovhjMa8pxPLuCDsSFV2MTuVouU3lVxk2UoMtRdvwL/I343tHxlEcLNZ8vSGgGsuPoC1pa/insgH050Yu1iTjQzELjizLYrmWwPoGSEWqwUFnVhe/ir+0n8xugcKWNzRcMKHY7EKonq7nBTE9PUQ9dOaB8g4opyUQ3fxLMgUQB1IAHZ4AVElhlaT4ytKO3FD8SEcjE7HutK9yNeIRHYgNg2NhccQqfThMVwNACj4agHCtX4UG04J1Kh/vLYYvmlhzCnvwaFRD6ZvIM+q+dYA4oVETejvTbF3Qqs9D9a7MGgEjQPE8cLTnWfyqsSuJhz/d+KZGS9MZxTRr+9Ga6QMnYXFWOQ7g7NJkuU/4IrhtVglpnoGcXq0HINJItmMJtwoOexCtNxwtuG+JU+YSA6eMJCknpoFbtQUDKGmYAhew/PzUHcVgr44YikPfuyOoMxNgrFDKT/aR0twODoNZYEIukJEbAy1FOP0tFI0D5ehIj+M9xop/Rd525GnpVDjGcbe4ZmMDupR2d+QzpRPHYNYthTI54BF4yHYwFRxY3zMmqmywGbShg9MZrkTVz6EiqawKV6SfmezfxXF8TuJnTHwej5iFTpGHxxAedzHnmNNwRBmzerGwGgAC2s7AABdsSJ4XEkUuGPwuhLwzSbfYcvpSlT/+8s4gvFFTiKbgNgy+DjL7CGWgrA4ayg8omRtswHveGGx74CoraiHXbAN0qq0snQ5/Fjs1IwMXHodGQMObt5NimvGyOTc1U/SRoXXLbdkZdi6YynCV/oQ9BEXbt4WBnAqGC5jhPumRtQEiHo9z0Um77ryPXhv2X5W3fi60sN4LVCH3/Uuhbvfa+qT2t74ANo1m9cxBkqDcyO1KZQ2udDfAFy98ChLrpunJVHoGsGK4DEAQMsocW44PjIVM3w9KHMPIxwj9ywwiirSMAO6yJUcdiFZn8ChziokThTg+Idp+Xr5I+fL2XtDaVf49ut0ElS9LA4/9Sxc0QC9MIF4oReR2hTKZpPEyxX+MOoCffjm0Xdh7fQD+GQpUbmG9EG0jBbjlehM/ObUUvQdJ+Px9rsQALHnxQtdrDQN7fOW2jdwPFyJ4VHiWVjtH8KyopNoj5dib7+RTcQXRzzpxtGBStT5+3DKCM9fFjyB5/oX4MVjs1FWNszGOWNhB66behQL/GdQ5R5kIQEuTUco5cVz4QV4sWMWtAKickuWjqC6fACJHdNAvLnTJU8qHttpsrNSG634DfImgjWudVJnLn7OVTSFWdJwy/cJYqPig7H5gOv4qkb2DgHipNV6UxDuPNJP8soQ3AcLUe6PIJb0oMJPjv9jzTOs4CutuZenJXFl8Dj+s+16nBooZXZDLS+FUw8uA748zgHROYlsYoJnSHbOHrYxKXwONge2M1FPL54H0h5bInMLtkXRc0ejWbKyiSUTvbPs3JX5MbDfxvnWBxpRP/0MWo4T74B40o3l1adwEBdbGF/j+g14wbuAZZZPGI4chfWDiI960FpFdup1D+xEEITRJf06yrxkgt9Q8AbmeJJ4dGAJ3hyuRtzwoPvKjrUonzrEsosAxIFCudHgihlSJhG+SCd5DYfzMJzwYc8QSUi8qOAMTsUqsDTQgr3RKnTESwCQHfJvmi9BfNSDWJTYyJL3NCJWoTMvNCrVJUfduHnaSRwbqsRpAL6XyThjFTq8IWpLc5neaccqwNsPlnMPAOZ8+mUSQ9bqxdnLjVXiA4DnVB4SQUAvTLBK0KcGStFYfgK31L6BT5a+ggo3scuNJsNY4h1ECi14yrsQvV7SjydM7DdUsgsvIJuNovIw7p7zDBrzW3GsoASnRglzutLfjIFkPgaSAayd+hoAYEZeD3aF5+BEpBKxlIelntoTnoXhhA8zqnqR507ik9NfBABc4WvHqUQhAq44To+W4ho/kbBPJQqxMzIbZ+NFqCkYQjhK+hkZ8qHTU4Tk/DCinYa0YzAZBjG/IcxprcSsGBbvRi5uC4CpogDd9Bx6+C72HfHSMUvbZdSIoyt5IqihB2kNCs3vmSyLQ5+axMFn5pjSjv2iZwWCnhjCCR+e6iNpu/piATzXNRd57iQiUS88HsMJ5EQ+fK2KHVEOY8Kk8Vq84v0PYbSKTHx/b8oU+8SDrwTr1EvKaWAm357vm+4y+TQ2AKwBl0YKKUqfmKhUdR+V2lFFKy37Qh03irZXomWwFCPPV7DEpmxnbHgK0jRP1CHi4vcfxq43Z7G0UPFZI8xzK+lPey2uu3o3Dg9VwetO4tXm6Sx+K1JreAJyCVkp+EVLpJv3XDx+pxuFRVGEWoqhFyZwzUIikQ0nfCj3hvGB8r14ovcKbDsyHwDxLAOIuouCetI13xpAYbPGPP9idXHkF8Xws8t/jGeGF2I0RfZ8P/nrNcTQf1s+5jw+wlRRfHAsAJOXZ/8yUuCSVdnm4CkdwY2ziWPM+rI92NS3DOvL9hgeimkV2NpgJ756dhmuKDiJbf1kobyksBU/OtmID87Yj9+cWsoqYc/O78J1/tM4lfChzB3DazGS2He1vxMDKR150HHa0H2WuEdYEuJnOuYhbqQFGwz5MXNKL/LdCXxy2gu4Jn+AtImWY4mvCy9EZjFVJwC8FqrDgb7qdHykgZrtRIJOXhlC2SZyT95zl08wDGSen6Z8iELiAfHZ8962NIGyJwyEL0qixlBz8omRC5s15nEYaCNVA/qXxeEJjMK3j9Aeq9DhmTWMke4A6md3MuclnzuBtt4S1JYPIBQn31nf8TLMWNiBPHeSVfUGjO+wP4YT/zq+FaLnfm5sXotHvzvxvBYnDSMbHBxkAdGqeCw7d13AmSej3Xmpzp6rSbRtx/0slgRIZ1ZnDIuvW5QhI4GMDpm7upKZ8eM37HdM1QNYYm14GsO1fgzWuxC5eAQ+w2trZMiH4GEvwgviuGbhUZYId6Q7gOBJN4qu7yKT/VWSm5DPdELzEtY9RdydqZsyX9eJd/OnzIbW1fJ1uaEtDqG0gEiNS8o6sLL4GAaSAfyxcwmOH6gFAJYRntZpA9K2rWAb8ULzBMh4blu4B6O6G68N1OLmKQdZFpSj4Soc6KtmuRPp7p6PJ+Oz5QMkG747L137LRHJA2JulNf1YzDkxxcueQoAMNUziCXebpxOBDHfm1avvRYrwoieh/2RegBAsYeMc3XgCI6OTsEUdwgupFBi6D07E4Uoco1g30g91gSPoNDg2ztHpmJ6Xj+8SCIOwrAGkn50J4twOFqD3b31rORNdU0/+ocDKC2I4EcLfoaQMf4DsVrMyOtBChpeDs/Gc10kjKFzsAgj3QFW4YE+F74UCsvjyFcnF9TfNBuLTMUIwDIv6LFtqc1MCqM13Wi2FR5ilYNEUYrVnqO/GXxJeAKjmDmll5TjAbC0pg17W+uQ7PKjsH6QNR1qL4JWMErKBx0kzL320nac6ixHVeUgugcKkDBK/gRPupGMjeDIv48vI5t319gY2ZGNE4+RTSrVYg455JBDDgZyNrKJh7VrvsUGw+/wZBkCxL+dBmDKoLK/if23PtCIRfduRNH1RK/e3TQFaCHnZTXA+B09H9MilpoQPTTtaGS2Ook02r8sDn/vcqvzicReRYsLtiOI2GVE0phT34ljqMKHlr4CnyuB9jLieHP8DKlfFo55sXx6C6qvIpu8vS/NB6CR4pVtZHxUTUd37kFOOqT5HokKL6228wyRoG3XFTHcMZPYcWo8/fiPthswkvTgWEsV8qeR/iP9hQBI1QG6e/cbz//4vy9HzVZgxl0kjmpF8BjmewfwtdiN6BktZAVA93XXYnF5JwquiKH5bDmKjArRrVWNiE1NQosTL0xfD6EvcvEICouiJCbNSK21dsE+3FB4CA+1vBs1BUM4GiViQyAYR0h3o8gVw8lRLw7Eatk4wykfXuqZhZrAEGYZGVkOxWswK+8s3oxXYyAZwC0FbwAACaROpTOAnDKy5R+JVeOZwUW4tvgw2keJhHGR9yye6luMg71V6O0qYvF1HSDnuxMu/P3B23F9DVHbTvORZ9sTDaJ7oADJUXIP74l81BxKZ8rnv9nG9Rtw9nINU17hpB0+RozTJFRI4irpHO65oxEVu6zXhtctZ/cAgGQ+KcEzsIAEhlPooy7EQx7ohQk2Ts8QUTf6lg4gub2UfVueWcMYGfKhtnwAfdEAltaQIqcXF7UhXuvBwgUdKPZEmKNUk2EDC0d9rMxQLOkB+rzoziPep7SCgjcEDFafB46RY2QTDx0rgpi+l/zN50IUPf4oZExNdOKwY3BOHEd41D0VxvE73ajxkgDSoZ50jj2qtmMOIbuaELqVJJsFYMoNF671myrUUthlBaEQbQ8Ui+7diL+/7EW8NH0WwJ0SHVgoGtdvAGr9LLsFAByL5LGsHS+dncUKLl562Ql8ofbPSOkaftV/JTrChMEl84lNglfDUTtFaCZ5LgML/IyOINLJimndMVqktL8hiVumnkKhi6ii6vMGcay7klRM9iUxp5LQdXi+CwOlflT8Kspsfkm/jsR1V0KLA2c/EEX7m2Rh+kLNVrSMBlGb348Zvh50xokjSTjqw9GBShR4Y/jbBftQ7R0AALRMrWBBwIH5A1g69QwAIOiJYXp+H2Z4e9E+WgIAqPSEMMMTwv/O/TWej1bhqnzirn0gXowqt46XopUIpfzMeeXpgwuh5aVw84JDuKH4ELOd5Wtx1HhGsDsawOrAEbSMFgMgDIwWJ30zXoH/aL0eANC+tQ75q3vw9PH5JgYUqyNFNX1IP1vE3NAKRuF+M4hBfwCbj6e/Nd+0MKZvcKHDqD1H0bvIhWBb2mmHfTfrlmPmvbvS392m9PclU/2vWfmQOb+n4aRBVY4saJ+mMDPU3TTDC6AxRxqPodKl9r5TA6XI8yQx3FrB3r83BAy0FKPq+i6MPEkKwvYXkYKnCy/uRNdIES4rJiV15vk6MG9qB14KzUNrtIzZFFfWNyPoieG5lrkwoSyOZJcf1duB9usILbGpwMw79qAZ44u36H6/R9O0XNLg8w3vsPk3XXjF3Iq8hKZK7cS3pe0yOYaIGTZkUo8+nIfwo2SXXbPZnB0eIC7mPXc0InJTI3w9MDl78Nm4+WJ/zJmE28na2gUlmRRqvr0Tu2+ux3VTj+J3d1xrfn6SZ8QzTWpbqK7px4zCfrzUNQud3SQGCwBur9qOkZQHRa4Y7q18ET/xXgIA+MEb1cTzz1igAABGxvWZT0Zw7LZ8VsX42CfySMopjEAfdaHGcGMfrAcSlaMonzqE8ry0BNCX9GF6WT9qak9hSWEb5vkIozhYXov/6r8OPQ1B1F1NsrY3ny1HdckwOpor4PGk8K2rfgUAmJ3nwm+Gp+CagjexNzoTp8NEQhnpDgAFJK5qc99SfHHJXwAAHyh5BVetOQKvlsCBkeks+8al+S14OToL0z29jNGO6m6cTgSx0DuC9tFSfD9CnCNuLDyAN+JBBF0x/KJrBcoNz8/L5p7Cq83TsfXwImAB8KmKFwAAQykfRnQNl+S34rXYdHQbyYSvChxFX7IAcd2Du175EHCKSJNTWlKI/qEChQCXTSSFXqQrQ1NpOF4IFLdoAFLoeF+cVdQm6bAKgV07UdqQ1hqYUjxxGy/ASNsl2I237bjf6vxEvzEhlRq1fwVB5sKatrRnMZDOa8ongAaAs/481F5KNjH57gRGkh5my6J1AX09GktpNvLkVBR/gGxAkpEAimdH8EZ/Fcr9EewbJDbfP4aXoHOwCNfVk3RqPnc6a8yLLy/EmhWvM+ei7qYp8M0aht6fj45VKcb03VENvR+/EvjR29r9Ppc0+EJB5W4vnlfFeTlRQyolNSMtjkq1CBBXbMZIeIcOgbmUHyJOIMQdGJi5Wa42pAxu56a72S5XNibTb85phFc5th/RMbOgD/m3EtVnuHc5c4pY41pncQ6hTiy1l5KYmYWlnZgX6MTB3ir4/KMYGSLqrFDKj1HdjXxXAhE9gV+eILkFq7cTRtTTECTqIgN0N08rHFNcPec4pvqG8Ov96dyEiSDJT7h2+gHMzu9iHnSX+jrxkWkvoz6vBwFXHJUuIgXna6P4TV0/UEcS7gLA4rkdmOIdwtkpRTgeqmQOFVfkd6LMPYzvnL4JpwZKmYRVP7sT5f4I2lGEod4gHmsmgdWfveivmObpR8AVR4k7wphKkSuGeb4OQ11IPNcW+trxzPBCNHgP4tWhGUxVeHJ0CroThfj+MzfCNy3MVJGhlmIU1g9iRkk/Xu6aAeAaAEB/PIDZwW4sDbSgzD3MGGXANYqtPUtMXqIEOpfQmWZtjyK4mXyH7fc0Mq9VOkfaVwUx+5Ekwkbm/p6GIOKF6RyiFGxDJaimTY5IXOkYUxFcATxDo30Hwc1P7jhWNJBN3IoGBNvAruu5oxFTXkmhu2caAGAwRBw/SjuBeKGbOXzEKnTUbPWgYxVRr8efJu0jF49gqDeI6pp+NLXVsED+6uAQqoNDZFMBoq4ESNB7oEfDtl0XM+elWF0cie4AUbkKDkB5fWYv1xzeGiYVI8shhxxyyIHgnZTZY1K539PMHoA6xuqtOHbwsCsHY2mbIaaLj4URY2zocVPdL67suhgUzcOR673Rf8f74lg+qxkLCkg691/89lqSFb4pbFYBCeEBdJe5+pMvoy8exP6uacjzJJkL8swrTuPT059HoWsEP+66CruaiA2BZrsIHvaynX203GVyEjj+YWILck+NYuPlv8YUdwgHYrXY1E6ksmNHpiF40o3KG8+gOjjE7BiRpA8VeSG8FqrD6pI3TSq9Lb2X4lSoFB+tI8+2xtMPr5bEodg0lLgjGEgSNVzPaCF+03wJQi3FKDnsYsUpaULi42em4NZFTWgsJNlDIikf8rQkpnn6sdgbQUQnqsVQyoWwnoeRlAcpQwoqc0dwIDYNv+xYhoOtNUbZGlIXTh91IXjYaykUSrN13Df3z0zyfLz5SgyG/KgsGUZ9UR8KPUTyXFZ0EgApmOopHcGUJ4zky4a0ZJKcJMHIFCwrPBd+MVjvYu+Ld4+nkr5FKuO+lUyqd4s9NkPSYFnBSyCdXb99VZCFWfBB08HNu1m9wOKWFCtEGmxL205jU5PwlI4gYdh+q4NEy3a0vxJ9fcR5w3si3+S2HzzpRs32MEsw7Y5qJFbTeAbUnlz3VBiJxMi4F9Zc8Jmxud8f/n7O/f6CYW3xbfirkf0eyFxR1qSDd8iQ+GvFa+wYJw+Wm9AwZvPZN3hb2NI7N7KJyWcqEIOjpUxSkZqKz4sIiDnt3Pibyn1wG2mEypZ3GcURg1bbGhe3Q+0Rz56eixkl/Qj64ujsLkbh/AEAwGjSjUdPr0ZXqJCk6PHReCq3UR17lHkrUiZGx1+9nealDOK5uQtxVeERXBM4gVeLiL2iaEkMr8ZnofvpaWirqEHPFaSfpaVtCLhjCHpiePD1dzOPs5ahtHH+UISokAIFMRyPTcVHivejM+nDiBH4/NfRhVhU2Yk3t5aSnIVGfFlbbwmSo27ooy4cD1Xi78rIoh1JeVHmjmC6W8OphIa5eWQB6UzqeCE8D58sPow/RogDzJlEKU7Fy3HgjRkInnQzxjBYTypOxyp01GyPsEU1XpqCe2oUc0u78czgIkzPJymtPjhjP57qWIhY0oOekSCG3USd255fih+/stLo22+qHoBdTcTph8s7yDM4umFaeudGVjySz+FY3JJKVwDnvjOqOhysdxGvVvrdK5gYP1fod2mxZ0u8c02p2+h9aNyoxGa29E4St1mBtFp0Z2oz5j240XjmhIlFy10Ibm5CuVEvL9rphr+XxEueClXjVBnZPOjDeQiedLNnMVhPNieJIqKODLf4WfVx94l8Uz5JGnwPAL1LgsAejC/eQV6Lk0oi4+uRjRXZZPEQ8yHSY3aTVrTBWXaaNvWT+FQ9svOmgGwuZ6MsQwafODVaTlyVP3PD01hf9DoA4LehRXimewFODZTCvbXUXIJEEmy+9M6NSN7cj8ibJShe3IvF5USyC3piKM8L4+evL0Pg9XxELiZBuyU78tHfkMScx0cYLYP1LkRqU6jeDlYinh53r+rH8upT6IgW4cAbhJFVzyQ+7tqPKtF+c4Klu6ISGvWQPNVJFqGqykGMPDkVAyvTgdyLqgidH5iyD7PyzmIoRRjQ5t5leLF1FhInDNdp5hFHbHNJvw53VMPca4n0c0XpKeS5Epjt68LcvLN4LTYdALGHeZHEoXgN5niJ/bHKHcNT4dnY2rME+47OYP3S7B+e0hEk+vNRVEM2xJGol6RIKovj1kXp7+NvSl7Bgdh0BF0xHIpMY+VyhhM+7DtwEUqb3IgXgtm9gLQ0JvMUtIDLusJKz9T6TYxMtPOKlZDpPXhk0hSostjwiQ7E4xatgUGTKZE3RyMPXsPBb9hokm9eU0ClLepRTGmZ9+BGE6MCjGKb397JinFSDUPJYRdKHn0Bz2MLMI4S2cI7xyaRvfHIxJPIJg0jW4216QrRkJcwz0bysoOt56KQAV8lPYk5HWlbyqx4xsQb1qmrMQBTTJidlMb3U/NtsgAdv9PNVFotn/pnQs/Xe/HPM55i14VTPlS6Q7htx8cx+xEiSckWKorG9Rtw9gNRJCJ5KJ9K5sAX5v4Fh6PT8PjW1SbX+sJmzaRGBMgiMfOK0+gKFRp1ygjT7rmjEaHVYdSWDyCW9KCzm7iZ08KZgdfzEb4oaXIFTxSloMU1oCyOxXXt7PjB1+pJwUNDJXTFVW8invLgm3VPYu/IdJbB46WBuTg6UIn+4QDmVHajJ0qkow9M349ftlyO0YQboSE/S6hLUzoBQF80gKurSTzaLcVNqM8jSX9X5RMmft2B9Xhf7et4fagWLUNlhuRrZIIwio2uvOYQS4IMAM/2LSDPzRPD6hKS0mpW3lm8FJmLeb4O7I/UoyKP6CN/3XYZOgeL0imhuM2PKfUYhcEgRAcO9n0J0jivNeBTc0kZgk2hWOlxG5U93ejJ5p64yRPHyWfE58NWqBMGTZUlU6GH1y03pbpiRXJpnkajPS20SrOZiGPiNwvnQ7W48NNjZGSPTjxGNmlUi4DcS/FcBjvL7mNqI5Gm+HYiU5XF0QS5QqAU3hDSKZS6A5jySnrzQcfILwDiuKXu931eBI04LLpAhB9djgc+/j4AxAtvkbcdrYlSLK5rxwhIfE1w826mlhInfhCAe1EjMD/MbGSPFxDVijtKGNf+Rzj1j7Cb9/Vo6IsGsLz6FLatuhjeReTaQCdJ69QSqSQZ+w31pGcqYZqRi0fgO5HPqvWWlQ1jNOFGWSCCvkgAZT4SoDrVN4TqFUM40FeNziOVAIDXf7cA89cew5bQEtxUcAhPDRNvtHjKjSVlHfj64mewLVKLRV7CDE+MVuCBeX+AV0vg2aFFOBEm/Qz5I6jID+NQdxUWVXbiigLi5ebVkpjq8uC1VAA/GSKBzzdUH2HemzNK+tFpqKLaeksIYy6KwudKIOAidrk53i7Mq+rAgdh0vNQ/h9nxXF4d1wSPoDNRhGJPBN9++j0AAN2rwzPkQu8izSwl8DYk7lhPQxD+2uWshI0JNMUarwkwvt0KmBP1AmnvRVOsl1joUlHsVtRIyFK+yZjNth33mzx3aRFbi/qfY1ZMKlvRQFSovSRIPkrV3LS0zIoGk0QWrvWbArH5Iql1T4VN0h4rObSryTK28K2XWJ91DmPGpGJkOeSQQw45EOS8Fs/XzTWtBcAM4fAXdV3/ZhZ9WFSLbNemUEOo1Bd2gcRj0evLwBwuOFsTf06WJZ/q6s9ersEd1UxJdak6ki8TI3NEoTTSNnz2ewBst37sE+QZfmjpK5jr70R7vBRbTi+B76ekBpZq582Prf3mBPKLiJRBkwabCksa4JMUA0S16I5qSM4Ps8S6AFDznJbOXL4gDi1E9l/uEQ21l7ajL0IkFBrrdVXJUUz1DOLgSC0qPSGmlusIF+H9015DY+A4tg6Rumg3FR7AI13XYUlhGxryW9GeIIHPeVoS7aMlmOHtwajuwU0B0vdgKondI3U4FS/H60O1zA5X6I3hYGsNZk87iy/X/wH1RoD2ydFC1HiG0Z4oQNxIGXUsXoWWkQpsPngpU48CAPq8pJinkYmkII88Q68rCZ8rgVDCh45wEWYU9gMA/q5yF8IpH07Gp+CFnrk4cMIItt/qMSejFpIv9xiB5wBxWDh7uQbMiMC3L8gKgtY9kE7cyye7ZipuQf0tqsV5qOzDMsicpkT7mGjHtrM78/1mAj8/+ETfAEwJiXlHF9Ebkkq4QDo5skhzeN1y/OWHn0BxcTEwjqrFRZ8am2rx0H9NPNXi24GR/QjAD7nDIV3XJToOZR+W7Pfj4W4/Vqi8GcU2AJhRGEhPJABM/379e/bh2T9ellYX8RkQRMO8cY56bQFEv8/b1URDPs9YZ/7iX7Fu8asozQvjp79Zw5ieKuicX2z4yRypMkqlCLYGWoiSt2PQsbTeFER8FslRCBAGdSpUijx3Es17pzOvsBlVvWh7tQbFi3vhdSdRYKT/qgkM4T3lr8GNFDoTJfiPQyRbyc0XvYF/qngBe2M1+OsgYW4frdiOSlcMW4YX4e+KDmMgRebDb4YuwXNn5yHfncAVpadYrkUAqM/vwTPdC4jrvBEQi5gbniEXEpXEiWROPXEiuariBGbnd+F7J6/F7xY9DgB4aaQao7oHT5y9DPuOzmClcAKdgOu9Pagv7sdQ3IdRw8PyVGc59FEXtLwU+x8gzivvq30dT3UsBAB0G8G8ACmfQt8BtdnwVawpQ+pYBaAsDn04D54hl8mppbiFswfxmej5b41jkj0NQYt9SAaTg4YDhym7flRq/kxOV6IXsGxjtujejaxCBQNPN8yev1StKAaF8+0orr3y/nG3kS361Dfg9mbJyOITk5G9HVSLIV3XO99qJ6L7PYXKA+qtMLdsrney+6TgFwGTDQlAwRU9uKH4EJ6ePx8w/DGY0VqIp6GG+DWuddgv2BTWtD1kmYw8KOOb/dir+NM9jaRuGGdnYRNe4unG+tzVhP07rB6VvCciYK07RiXlRfduRLzPCxiM7NIiEh9W5+/D0hvb2PUvdc0CZkTQ11eAwqIo5pYQSebFY7Oxv2saZpT0w+tOIugnDG7ryYVYZEhWa0tfBQDsjc7Ey4MXYW35q2hJ5DFnj9+3XYyO9lIUlYdx4EQtyyPZsWMafEv7EWophrefSIkAcb2e+WnSZ/OvGtC8l3gtHqusYnkLb/76PQBIWZfCoiipuh1zs/yGyflRJPsKMPJ8BcIXJVE/m0yLGVW9qA4O4Wh/JQq9MXQOEimwvqgPvzxxedqr0ci+Ub0d7DkWt6TYe64AgBUN6F0UZBsKvTCO+qpetByvQjJfRyKYZmQA8bzzhoCdm8xOTLI4tP075A5W4qJvsTkLGgSZRCb7W2r7BUzfpUoKZAxrEzemtqipvTcEJtmyb1WIl+M3hZTZ83TR4xdiQ/1OUi2+HRjZFzRN+xKAVgD/C2CjruuJDNdYsGXwccsxlUpjLB8UPzFVEpbtxyrJcahSe2JXE2EUbWm1xeLyNzCikwUrbCRFj5a7pO7Tjes3YP+muwEjmJWCTcgVDcxYDZhj0/j8dnxgKp/YmLaT5bCktMiYJI1LomMKWlqQfmuMHX97oSHVzfJifkEHTo+U4dOVz+PHvasAAA/M+T3+MngxOkeK0DJUhqk+soGcPe0sRpNuVPuH0BEtQt/xMtb/Q0PvwZJZbaj2k7ZPH1wIT3cernzfSYRSfpYjsXuAuN2HWoqhAYx5BDpJgllvvwvx0hQCnYQhRPq8pDr2zf3wjKYwYkhmS2a14fDumXB3pXfGs//+VbTf0witJYVgvYulS5ryhB8dq0jhR1+XG301RAoMDflRPjPCMtD/JUKkyf3ttfDmJZDoz0fpYRfbCC1q24jG9RtQY7zXpeVpqTw0U4evhzBTAJgz7Sy6QoWYM+8MjrVUITlCVMuJylEMhklgdkVT2OqezxWBZe/Opc5vyp93ogLkj7NvUXCEkh0DjBi4HWZ1Hn8vk4ejcb0s/GD/I3cBdHPJOZKw+20yM3Ze0qN9y6pNrHGtw5aBH6G4+OuWe55T5OLIztPNNe1zAF4F0AegEcC/AviJruufs7nGB8DHHSoE0MZn9rBT5yld5x3q8Z1k9LC7B4Vp4Zfp/I2FAgDar9PxqaueQ7E7itdCdXjhz5cAgMnGpWKKvMcZVV2KIQKm+wr9WVQ0NmVkVGNlEN24BVAaqBs4lRoiVYBvaT/mlPegoaiNuZkDQJVnALuHZ2NN0UHMNzLR7x4hxTuLXFH8y5vvx9/WvwIALAfij/50A6sSHasjNjfdq+OapYdZQdCgP4beriIg5kZpk9tUoJEG0IZm6qwQY35lBNPL+rG4pAO3lrzK4tEWebtxT+v78WrzdHY9yV1I4rH2P3IXk4Jpf/WzO5HnTqIvShhZmT+C4bgPSyva8Pkpz+JH/WRT8dufX43wRYTxUjsiBbVxAWCVqWk4gj6cxzw/aQFNWhRT95K2phg0cRMmqLT590ch2mtlsWQmdbTQh6WSus1cVqm5RWnQrg+ZfY+XtnjbsDhXMo2dXsdvBq/Vbh33OLIl/3dsqsUD/z3xVIuuzE2yg6Zp39Q0Tc/wbz4A6Lr+XV3Xn9d1/XVd1x8DcDeAzxrMSoUvAhjk/rXZtM0hhxxyyGGSYzxUixsA/DRDm5OK4y+D0FQP4Iiizb8C+C73uxACM+NViE51047VjhJJQtUXhV3QskgfLVcBpHfS1TN7cKm/BdM9g2gZqUBsqhGczOnuxYBQFv/DGen3C6pGi6Ql7DTF0jRAFgZ5SUorpeeY0ZaeTwSJE0LJYXI6NjWJWHsRXh3y45C/imWFXzXtJB47cxVWTTuJET0P+RrZlxW5orjUN4iWRB7um/tnLPGRjBobz16HT1W8gMq1IZav8XRfKWIhD8rr+nF0oJKRdHX1CVwyuxX/euBdAAqZLYwPGAYMKQdAaUEEx89MwaenP4/XRurQM0qz34+goagN+4YvQnkd8TZsX1XBxrlm5UPYbzzTpXduRP+yJDoHizCnshuXVZLP+kBfNQq8MezvqcU3UjeiJI/ExVEVZN1TYbSvCjInoPZVQVIOqAoG3eR78U0LIxbNIzkdjWD47oECJLv8KD3sQqSKqE4B4hi0/5G7sWZ72CJZ8O/WVEuPk4RM8WCS7wiQ28IYRLuvZK6I81wVd2bpG4IdbeVD2LnjfhYfSdtTqZNXn/LB1CrwsWRMg7Gigc3FNa512DL4OPVaHD+8NdXihKpH9rbK7KFp2v8B8DiACl3X+x1eI00anA2ydaFX9aHyoJK1kU1g0auK5nFzryJqtXJvGEcHK9Gxg3inUdUiS+4quOzTbAW86zDLnycpXChL/6Oyb/DHLMcF9WsmlQ4FXTBm/uJf8dGGXTgRIYzlhf0LUFQzhNCQH1fPOY79XWT8Q+1F8HW5CWP3JfH3lxFG/p6i11DjGUG+5sLm0Fxclt8CABhI+VHiiqLQFcdrRvXlS3xt6E4GcTZZiFHdwxIMH4lVo9ITQpVnAD/oWI19B0iRy+BJNxJBsuD3L4ujqJwwj7X1B3Bj4QGcTpTjVLwcvzm1FACwuLwT7ZEiHGupYlWJAWKD8gRGkRx1o6pyEADQ0VyBW654DdvPXIQZJf3M/f5ofyW87iRjOtRdP/B6Pgtibr0pyJhtzXbC2ACSbJgWIC26vgtzS7rx4rHZrL4YAFMgrywhtVL9xzMH4fuRbVpU55wcV313tJ2Tb1WmzudVpHZmCN5eLM0BadOHBSsa8MTWfxx39/uLPzY21eLrP554qsULxsg0TVsB4EoAfwUQArACwEYAW3Vd/4cs+rEwMtUuT5wYGe1hGXZ4dsffKvj0P72LXIhNTSK/MoLEiQLm4l26x8vap+tMpdNY0YwEfFJemv9NHLfqWdjawbJgWLy9AZDs4JFeDLq2LMATS/8bL0RIteZn+xZg9955QFkcM6p6EYoTzXNvVxFK93gRqSJeneEoOf7FJX9BwBXDqXgFGvJb8Up0JgBgcT6RcEZ1NyrdxM5W5Iqh1qNjMJVEKOVBmVEo8Y14KcIpH6Z5BvBceAGeOzsPANAVKkSeJ4neriLkF8VQWkCkoyVlHfj7ih1Y6B3BptAcvNQ/BwBJVByOeTHUG2SJhwP+OCJvlgAAihf3Mrqvqz+KcMKHS4tOoTFwHC+EyT3/2L4EfZEAQkN+BF7PZzF5fMqlwXoXiwELdIK52fNu+PRY+KIkap4jkqSYtcKSIV9gYhStDzSysArAxgZlE8+pgtIJRJEMmz9PIXrl2s13nkmJ4+Gv58eksjPzx1RaiG2pzRgaGhp/RvbRMTKyn0w8RnYhvRZjAD4M4AEQ541mEEb2XZtrbMF73PGQ/ZYmSYU94+P/FlWRSrVZJpq5CchPUj4P4c5NxJU6UkCK9wXmk3OhmXkobNasY9rVBKxbjkgV0DwzgEKSLQnhWj+KW1JSVQz/vzhmGc3bUpsdq49kf7Nj/IJjPAf31lJ8ruQDeLj+twCAo/4q7PLqwKgLc4u7EUqQhf9Qwo2BBR6UHHbB99MylBnSxDduWofqlWfQcroSvlYvCq4gyYXfLK/GqVApqoNDKPUSBlTgjuErU/bgjUQ+OpPFeH2QVGseTvpQ6ongpcQ8FLhjGDaYZ3zUg0jUCy3kQRVX3mNl8TFM94QxmAIGk35cVXqMvIo334Xqmn4UbC3GYD3ZeEQuIxLZNQtJleHCYtJHlXcIo3luLPefQL6WYJWtd/lnIc+dxFB7ESK1KcCQsNrvaUTN9jCi5S7UfDu9keld5EJFUxSAH9jVBL+R0Z2qa2s+/TJr6+9NSRdlmvJJtvg3rt+AI1++C/hy5vkiBvfzcMScjH4t2gPA5ASiYhp0nKq1gR5b41onpcOibrdz8hDWBpUjyRrXOjwx8CPpmM8pcl6LEwfZqBazqSE2nn2wvhRei4DZ5sVPhp47Glni3WRNjCXzbV8VZGomqibqWx+G++VCtoMfWJCCe0TDzCcjFjWQ6C0m29HKaLf7rbqWbyMGgdOSNTS3JACUTx3C8N4KxOriqK7px9/PeBkA0DJSgT/9b7rqLpNUmsI4dls+PEMuxujp+AESZzX8EaLOKwtEUB0cwsVFbRhNefC/R4ntLOiPob64H15XArOD3ag2PCIPhqfB50rgD0cXw+NJ4R/mk3d0XfAwziYLMaLnYe/wRRhOpv2Vtp+5CKGWYpNHYGimjkTlKMqnDqHQCOSeUdiPOn8fumJF6I0H0TJIsowMhvxIjrrhbvcBMyKs30R/Pqnr1kC+gTmPE5f6bTvuZypbPviZYuemu1mmjprtYWk1A1WWGFYPT7B7OlFBO5XKZB6PPF0ZvYYzJO82tXXATMVNokxFyd9DbMvTQZHQR8fda7HhH8YmkTX9z8STyM6512IOOeSQQw45nE+8HQKizwnWFt9mzrXoRDWm+G1pz8XL2LazsRHJztupJ3duupsFRANpIzwfz1T9ey8Asjs+tMOcjipeCMTOBKEviKN4q/GaD7sQL5TH9sjUhXQnapedwbIjN9qL51U7aT6byZqVD6Fx/QZ0vC8OfTgfwcMkRVPZx46i99FSlO7xov+GAF4LEfVfSV4E4QXpKtN8kGvNcxoG6zVTHSj3iIZEUQqx2/sRCZFjS6eeQZ2/D3laEmcTRZheRnyMjh2ZhuGuCsRnjWC/vxb/vvRXAICOeAlm+HrwrJ9UuqZZ7H/jWYr64n6sKD2BX+++Ep5SIh0VF0Yx1F6Emu1A7yI3G6uvR0My34PeWCnmNqTLtbx0dhb6IgHmyAIA8OvwRjXEpibhezOIWJ1RrXp2J9qGSMycr8vNamUtvXMjKtqiOHZbPnxdsKQ6W+NahxrLmxBgfAei2nenJAsHDzHNk0xysZsTgFUK5L1aVbYupVZDOC+uDXx/prg4QUqzeG5CrU4X1wrZejMBvBYnFCYNI9sy+DjLtQgo3HUVaZkyqTwyOTTI+pFNNpWRWdafRT1iZCBYdO9GlB8iX1u03IWdm9LlYCo4Y/fxD/tRWD+IPE8S7dcRFVVpE3Efz1TAU6RBfGYy2wXrSxG8KtpKeGbHPBdr/aSwZF4Sd1z9PB4bugkA8cosbSLODT1oxLYFJOFvYf0gfK1exCp0BL/N1aIyHF0SQeLNRytND9ZraFh5EleXHcXjzVcCAF5um4G/W7oLc/L68RfXfEzzEUbWFw1gcKjcqHWWh3958/0ASHByb1EQiyo7EU95WKCzPupCb2spmkprSLDxKcJUBhEwJpnOvArjhcT13jctjJHuAF7/HcnUEbssjIA/jtj+UmBqkrnCVzy2C+33NKLu0y+j545GxKYSBtf2ag2S+aRkS9Kvo3gxqYfmbUjiWEMF4Eui/JCWdvZBA/F05YLtTTW1AMu75r36ZKDvjjIvvswPvV5E6wONpvOiKnHpnRvNCaVpGRhJdhy7+/DHZY5J4nnTnOC+Y5HBsf8FGzErKyPpU2SeQ0Pjr7XTdB1alqajbNu/XTCpbGR80mAVw8nk0ahqa3fsrZ4ztXNgA+Az6FsK/IEs5IP1LtTc3IrWF+tYtnzmoWakgKLu/Ycevktp47KjWbTjqapS8ztpy/OUMOzmWwP4+LufwetDxEV+6I47NwAARkVJREFUb2sdfPuCLMtE601kYfaEiV2MFjs0wSgUmbwyhH9evA0AsKXrEoTiPiws7cSnKl4AAHyz/WbsfWk+Pv7uZ/Cewtfxs74VAIDfPr0CiaIUfF1ueMJgHoHlh1KE2Q65kMzX4e0nzzBemoLu1RE86UasQkcyn8yrksOk+vbsX0VN3oN8xeWzl6fteDPv3YXmXzUg2eVnbvMA2YD0LnKh/FCKZfDwhNOu9rEKjpG5k8xTkkqrANIVEhRZVcT3IrXxcMxFpdWQ/e3EozWTtkNsw9Mkq/igsm3Jxu70m7UbT6YK7jzOh9fiJR/5+phsZK/9/L5xoWs8MWkY2epl9+GvL5u9o+w+QsDeS0+lihjLgm+iSXCmyGSEZm25BajnDrKjpQHO7fc0spx4QDpzfutNQZQfMqvc+Mq3ds9GLJuhVCXyC4OxoNCyMvyYLQsNL+1xiyN1+259oJEFfgdPuplTggiqyrIwVYOuY49eifdfSVJUXRJsxalYBZqGanF9OYm2vipwDH8MXYz/euk65FdGWAmVo3+9iElEAFgoBHVC0fJSQJ8X7hHChJI1MVPFaopIbQrNn73blB2d31DwO/ueOxqlSZX5asditWKAOHR4Q2lnFpTF4fOPQj9IgrJNxTUpJG7zlvemYD4yON2k0XtbHCOgDrZXpUXLpKLkofo+nNAtPhf+fiZPYQEy1Tw9fj5SVC39P2NjZPt/kWNk5x18PTKa/d4ps7FV7TnwxuKPq/rh24mTM1N8jYwGSx9AmgFwthA+AwG/8PH1lBgUzM0OoreXanfs1MuMgo9za7+HMGy+Bha9BwWVSHnbDF+frachyGpvJa8MYU5lNw68MQM3XnYAAKkaHUt5sP0baQYBkGDnOR97hUmulAaabSW/MoKq4iG0HCdGSyq5UQmRB8uKzqnO+DgvfhGktcL4jYlpkeQYHx83yHuttq8KshIsPQ1BUyiHWNoFkDOnsdiZVdfZbRyzkXjsIM5DcWMm2u6y6pdTxVoYmjAHpfZBgdltS20+L2Vclv7dGBnZ/048RjZpbGQ55JBDDjmkkSvjMsngxDkDsBpkZcfFY6LEptpJOj1md09xp0pVjjLdP90ZLrp3I4uv6l3kQt1TYaZG4lVX0XIXqyEmgsUOAUxqk9EGgDmesPPUUA/rM2XgVIs1u9LHqITBpL42Q4oV1ZRtD5GxGKU2WF2pFQ0s+wUd56mPJHDZkpOIpcin/8my3fhax41G9e10rkGaNSXYFkW0PMj6qHlOw9nLNXhrSAaQohqyaY11laalK66wqL83xVS9dGceuSkIwJDyBOm54rGdJLaOo1t8RvRvqm6kqmbqnVlyGIYdzW+Sxqjal5c8LRDyXsq8Vuk4VPNFhFSrQdXm4jexosGq5oZcK6HyPuTHIZYfMt1LvL/MO1nUMPD3lzmQbJKMX9BarHGdpzIu7yBMSkbG66Z5ZNKLZ2JWTu/tqF0Gnb8TPT4/MYD0pKV1yrCiAVjFqZY4DVWwLZpeEDfvxuA9jZY6TQCAXU0I8uXbd5k9tPjx8OpF5pAiqf5LaeWZI72u+dYAEkUp1DynmQzn4gJCEa71I2gwV3ZPg7bmWwNI3HYl8itJEHHihIaZ3/RiCDXYdxtRuXzNlcDqkjdxoKEaQ89OZc9q2477sRREvUfVgAAQq9ARmD+AGSX9CMV9iEQJw0uWcurEXU2oQAOjL1ruQu+iICugqXuTiE0FBgpGUY200w3LuiKp/cU/J/5ZMqYnqIp77mjEzk13pz0AjfZBgLikG6pFiwqOejOK71WhimbvhzK8lWo7tcoBJBt7lZ2zkAnGBmqnYkMqVdeLtjuJjTi8bjm7Z7jWb1apy+zGHI1836s+9/2MY33LeAe5308aG9ng4CA+cPN/AJDEoWQBlb1A1VZlX8uG+WVzvcwJRHQcYW3EeBZjctLsIDOfJAt8601BBDqFfI1cCXisaGBJaAGkY7bEPHySVFumBUESp8OPh9qzYhWENsY8qXQiJqYVFhuRsTau34D2mxN4/yX7AQB5WhIvdc1C55FK5qQBkHRRWoikuqJxevFZI0acHnD2co09q+ZbA7ju2iZ8oHwvAlocnUkSC/TdE2vQeaQSgTYXIrUp6IVGbdiYGzdedgAzA93MC3NBQSd+03wJhtqLiCPLt9M5Exnzoc4gUCy6wvdgYiISRsM/P5k9VdxUONEWZOsEZWdHU13Dj5HSp5LsxetUThoWusRvFFZnLKl0yDNtiYen3fjOh9fiZevHZiPbt2ni2cgmDSNbjbXwNJLgVNVkzNbDUAbVxHHqQZVpgqv6s0ujI+uHFdVsS7t9xwsJEyJqNM1UsqPjfXF4T+SnPdwUC5zMoE3vSRdgVUFDVSwPj547GhG9IYREwkUyvYO4sANmBwXWB7cI0YDwSBWQ9BMXeL0wwTLUzyjpx8HX6llgNAB4hlzw9WiIXRY2ZaLv7C6Gzz+KxAlSKXrmFacBAO+pOoC/KzqMUCqFJDT0GamoHmp9Dw68MQOeIRcSRSlTQPQttW+g2BPBZ0uOAQCejhbguaGFeLFjFks/BZCCmzIPRt6ZRVSfWTYNsMZAifFZMrXdGtc60/sWEzlbKoTbOGnQPlWwW+gzbeDs5oD4zfH3cOpcpdqYUsjU+Pw503U2oQ7nhZF9aIyM7NcTj5FNStViDjnkkEMOE9d5I1tMKomMut8DCjUMH48i+VvcaZ0rtWEmFYWTvu12pJYdohADZoGhKqTOFDQLSKilmAXhHnrYsKEI9jDqHm9RFYLbrYr2FOOevPqLPm9TGXlDimy/TsenrnqOlU4JP0pUcqI6U1QPUftOxypgxsIOFHpjaPvlRSypbnldP8JRnymRMgBWBmZuaTeWl6Rrvj7TvQA3VB7GHzuXoCtEfPifvexHeDPux0AqgNOj5RjViTT1g5+8G8UtJFi6tMmN5M0kQ0hZIIKrppxAa7QMSwpJGZnHDlyFlfXNrC4YX0eMfzY8MkkCovrNFDNI2zn5dvg+JVKMXQkTZUC8Is2ZDOI3Ib2PKG1JpEFxvqhsaUoNi01aOlF1L7ueb2uxe+5qwhMDPxp/iWzdQ/DkZSeRJUZHsG/z/eNC13hi0jCywcFBvOsTPwSQ2UPJTg2SrfrxXKgrM/Wt6l81Dn4hEb3U+BpW9Hi8kMRYjXQHUNpEFmY+AwhVbQEk+JbadCyQMFDe5map92RMbsqAaFxVuNaP9V/dikiK2Kj+66XrWP0sywJnOKJEqtKBv8duy4dWMIrCIqImC7UQOxZVUdK4MiBdeDJ5ZQjvm3UAc/1E35qnJRFO+XAwPA3PtcxlORgXl3SgPr8HPaOF+HPbQgweLAdAcicmgiTDh7efpIwCgMD8AXZ/Cm+/C7E6EqfGg6/4LT7XTJW5eUYuBv7KbDcqW7ATB6Ns5ovMnqbqz65vlfOWbEPF00PVzVSlarm/wJgtKlQblaTMdmcXvM3Tdl5UizlGNnGQVRmXMTIp1TWZdoqZ+s5kHGZtnQQVS3bHlvxwXGaIiqZ0VeDeRS7ES1MoOexidhmLPYbCYBz+3pSpxhLABSLzY5OkoOJBK1kDwPF/X47ZvyKZM5bMamMFNFtOV6J0jxf+3pSZLi6TCJAOPO5pCGJg5QgKi6II+uLo7CaMRB/Og2eIMDNfD2GMkdoUqreDOYVM8ZK5O5ryYG//DBx4YwbgS0ILGVr4sjj0URc83Xnw9WimEikswBlgJWiCh73sGAUtV0Ofj+jUIlv4M2kYRIibHFW//DujbfjrxVpaNJibZ5ZOkYkWGf2qa8VjPCySFaxewk7mnMqBQ7oh4JyXMtnHAZwXiezyD46Nkb3ymxwjO+9Q5VrkwSc2VX6QGdQfdlKPHTLtSO3aU9hNPN4Yr3LC4Ccbv4iyZL0AcwrhUzHxu1yaZSN8UZLUvRJVl4KLuIl2g8b2exrZwh8tJx6Csbo4fK1E8vKEiTMKrWI8Z94ZAMCxlirmVcjHRTFwkiNAJBvKnKvmdaOmgMzHfQcuIgl9Y25oBaMAAO+JfMRLU8zbkKJsdh9xxBAcTgCgv4E8A7oRAMwSp8goeIlWfLbSxVBUdYvempJvkX8Hsmv5/ildMlp4SFWLY9y82TEmBknMFn8flSrebm44Kdpp6kfmeeuQAa9xkXAI6pQky0VK+z4fEtnlHxgjI3ti4jGySePssbb4NpONDEh/6PRjWrPZ/AFmw5Qs57nATdk9VdfbeVbxxzNOesm9TAsiJxEx7GrCTo6xBPnOjOBhmpk82Gb2fmRSxXYi8URuaiTnJN5sKlCPSQAobAa0xSEsqezG4cBU0uDNIJNq2hFEVw3RAZZPHUJZfQTHCqvg7+WYR1vUZAPhc1AuuncjtMVhdDRXoK+L9O8DkPQTL8VILaGDJlQOtoVZaicyzjLgcg3Vr+iIlrtMaacqPv2ydLMhey+0HI+4MZB+IxwDaly/wRIDpbqWfTMS25VdcUd6T1PAOw9JHBW/MRFV2KpchmK5E/rdUOavivd0Cno/Xp29c9PdpmB8Szo13nbIzz9FlWgRou2LXlfx2E4Wo8eHsIhMdW3xbVmNcSzQUuRfttdMROQKa+aQQw45TEboY/xHsEfTtDc0TfvM+SV6bJg0qsXVy+5DrJ7U3VLFuvCQ2ZScxKiYrpGpWSSZLOyM4zLvqLeqtrSV1MTAWQpFTBIbn5hNgnMGoZCpUfj78MdP351CLJqHsrJhpvo7+teL4AmDBRRTu9SMhR2oDg6R+l/7ZjE1H03nBJhLo/Q0BEnA9727cOzRKxE8SRxYIrWk1IoW16B7yXfv63Kj/FDKZN+iNNOsGVLnCEkwuFilQAlZsmWo37+tAwEfWM71I/s2bD0OMzhjyLQHTiRSp98y35+dlsNOMpWVbJHRpVIhZqJBBifjlK0t50O1uGzt2FSLe7bkVIsXDFu2fV7q7KFiWKrFVgbZxJR9uHYqRdlvp2pI1fX8AmOnjrHcQ3DLZvn1FIswz6yUE9xQZ1oYPm/z4Tzr9IMuVC3vws01b6BthGxA2jqJR2HJYRf6lwFV87oBAHnuJIZHfaj2D+Gj176Ax0dWAwDiht3u0MN3YemdGxEk3u3w96ZQ0WSoynxJFLcQNWJxCwBoJptVsC3MnC1oADkFzXRiUY251pG2QlZ02YKrsiPStk6+GdW3aWujUhTLlKnVZN+Q3QaQbmRk16rGBFgdL+zGo2K0Kjueyr4m+636hu3GnGneihsP0zgzbWzGC7pO/mV7zQTEpJHIeK/FTEZiEU53o6xPRY0hu/6cTIZsrpdeJ1koVLtZMX5r2477TXn5xNplDIo4LpEG2eSlJUoAYi+LlrsQWh2Gx0MU8yNDPpTu8RJninln0LyXVF/GjAhqywewsLQTq4qOsdit/zh+Lcoe8rNSJcz93Cg4Kpasoam4aDkbwFxnTASzHwmFS2WOGqpvTeZ0YaslkNmMuPcjll+RSVvS+wOmvIxiW2Yny5AVRxy36GBikQIlc0jsxyLlibklOSlK9mzEsjayci2L7t3I4h9lz8hiU7ZxubeTcC0bHkX5mPNRj2zZ+742Nons918aF7rGE5OWkWX6CFXHM6lcLEZsSe0tu/uocsbZ0ZItk3Taj8zTUKXSko7fAXPmFzJestu56W7Me3Ajyg+lzHXAGpIoqhnCjJJ+HO4gThqJ/nzC2M6W47MXP4+1BYcAAN86ez2e/eNljDlRnL1cw5RXdFMxSkAoVCmL1+LGLwaCZxNMqxp/tpsTU/C4g82Tk2+LpbrKIqeg3bicjkeVniwbKYjCjmHx9xKTS8sqZKvmCB/jKEsNBqg9G03tJEVEz5fX4pXvHRsje/kPOUZ23uEkjkxlh+DhVI9v6VsRp8Lf24kNQva3iuZs7A+iPSCbXbOMWcvokPWRaYGgTCJc62fZ3xOcG+U1t7yGoCcGAPjdy5cTu1ZhAvlFMRacfKylCqV7vBhYQGLBKGghzJ2b7jaVseGrMouu89tS5grJKnsS/2ycQnxP4n1EycP22dnkC+Tb88VFxYBfcWFmanaFq71yU2Z3TogXVG0E7DZCqntks8Hji49myvJBzwGQZjSRjUO2sRO/cVmmloQ+Ou4S2ZXvGSMj++PEY2STxkaWQw455JBDGu+kwpqTUiJT6tOdSjAceP08oDZUnys4oVHWViXByWx82d7bIjXwqhs+e4jEO1El1fDqRpPKry2K9lVBRGpTmLGwAwBQ7o/g1X2zEGgjnoXNtwYAAMl8Hd5+Is0d+fJdJnUQVSva2Wfo2CiNi+7daPJcdCpF8OOR3cfuPTi2fYoOOoBaC2A41TgpYaIag2iXUqo0HXgK2mWtt5PKnKgf+fO83S5TPkhLP4oCmnZaEJUZwlb9axw7H6rF5bc8OCaJbPefvzwudI0nJo1ExgdEqxZy2YdJ27EPWcKwMi3+fN8Z7VJcnzL6xqri5PsRFwexT1VaIjuVqGmR5go8sj4EWwufQYK3R4m07Nx0N5aWb2S/g5ub4G1oRM2vojj2iUoAQAuAoMHEehqCmPkkYTbUyYPVSjPoosU8xaB1tiHhbSScuqnGQU498XymRdekbpKoeGXfp+UenI2MPlMTbcLf/EZCpF1ktuIzkc0dMRTDbrxShs4HJkvuIeubnwsyZim7N+tfxjRXNJg2Xpk8C2VzQvwtm9syxswcPqh3sGsdElfMk9J+LpGTyCYQsrGRjZVJ2EG2CxTP2zJCB3kUpfeDZNGUOAeo7qeyKYh9qzYDmSQdKd0iE+FsM2IfNNkrAOaRKGYPoTW7GFOWpGji63rJmDf/XFS1o0zMUGLTkrUTxy7bqat2/arnl0kykTlBSN+pIi4NMKdzY9ervm2F44QTusWNkt11/Lfj5B4Z7Xc8MozNqXRo6luMJZWkvzsfEtmKd41NItv1l5xE9raC08zVdt5UmRiNU7WHeJyeEz9wFYNR7RBNoLvNMSweslgpFeiCqVIJye7J1DriwiAZ/xrXOlQIOQKDm3dj9uXfJd6IRt/7H7mLtN9sZghsB2+k3ZKpgsRdPr/oULoAa6oo/ltoXL+B0ULHJnvvthIvJ6nJnpvYh4wZUtAQAlHCt4zbJq5JTOeW7fdtuo+D8SgZuSTWTTqXVjRYJO9tqc0mqVWELc2yHJiKcVg2CUISa1mfOYwPJo1EdsX7H8Ke394nbaOSmuykDKc7Zb6vseyoxYlht0s1jcUBXZnUXZna2jI+keEr2tLfMhVjpp0zPc4n3pWVcREDmS3MMUMgLutPImFkem+iBCPt1+bZ2rUVF9JspAO+nep6/pgyC77gyp4pw7vs3mwTMwbPRSfj4ulVXmMTbpBJcpNu8BSJnNk5wJaBnY84ssabxiaR7XwqJ5HlkEMOOeTwdkBKJ/+yvWYCYtIwsmd++ln2t0qN0bh+g1JykKl/nOrd6XGZ2kGlEmS2hww0qO4lG6vFRqaQxKgkwUsRTK0nkV5k96O7bCaR8Ko9Tm1LsXPT3abqA7zdQ7ab5SWpnTvux5q2hxAtd1l30GIWf5ilQ5NaLcM77GkIYv+ONH28+k+UJmj/7N6bBNuT8BzFe6rUuCpJjKdHdZ1snCYHB+N6mWS7U3Jfk7pO+B5kGgwpJGpTJ7CTzFTaAVkfqmtM7VTvl8vyr7w3fc8ZpE7LtcsWA3u2KGk6JzAnAXZ+zQTEpFEt8vXI7FSI2UCqD7dxJQask8KJGiMbOpy2B9R6flu1pSQ7BH88m5ptgNWxQEaDqK6xuHyr1Di8HUWhTlR5o6nUyjxdYmkS1RjFcWZ6JuL5bNTISlWYIl2SiimaIHGkUKklbWlQqKClGy3F2GS/Rbpl6mzA7Owi0m9KyaagU2xjV2JGfI7KjYTimzwfhTVX3vBVeDxZqhYTI9jxzFfGha7xxKSRyG64/XvYI9NXc7DbYfNtgLShnCLTLpDfucp2trI+nJ5n7SRpiuh1SnocMEBeypLdj+9fXJhU3m+MDokzB39fMYchjSWTbiJgdiIQ3yFdyBrXb8BOmzgikbnJnFcAsxQpjiHbagmyDY2dVCNuHsTrZPTyUPbLSRAymlWSo2peiOOVbTIYbKotZBqP7Brbb1zYDMm0D2KfFjsnl9xZyWSNcYo2RtaG65+X1s9HPbJc0uAJBKlEZkC2y1ap/xwzE8XunUJU2Y0VTnbeqvZjkfxUu1QLMrhBq1LyiM9M9hwtLs+CZ6H4bPmduCkFkc3iI7unSZJxUN5DJmVkrKRsk2swkwrM7tu0lQRFZsJtFDKlxQKQMb5MNq9UGolspDinx5068TiB+M0AztYP6XMTINtonheJ7PoHxiaRPfvAuNA1npg0EhkgV79k2mHy7Z1KUnaTOQgAm6xtxb/Fe4j3UTEi5aRVlOZQlbq39Jth582OK9SmDBJPLdlzlD0/kRGJ9xKfLe1DmdRV8u4tDJaP9bGjWWAK4m7bshPn7gmA7O65hZdJdpJvyHKtolbcth33q70IFSpiabJkLlDXdJ1iQ2ILoXJ0Jqi0ACKkc1ERbpLN/VUbFFkbsX8m4QOmDZxpLnGhAdSerEpYfa7xTgqInlSMLIcccsghBwPvIGePScXITB5EChUEOy7spi27Lm6Hzqu0ZCoWAMrCkvyOTGpDkl0jjstup8ip+sRdq1OVjUyCtbTjd+3CMf63LKtINmpOadC04tnx9JtAPc0kalDV2GUOCHQHbVFFKmwyPKRtOBtRJqlBlDyUqjshEJtdS9WIkj4tdkLeM08iUcv6t3y3QlCyeE8nKlT+/jIbm0yboppTtJ2oQpbNNTtpTKVypY5AfP/S8XP35B2HhobGX2un6Tq0LE1H2bZ/u2DcGJmmafcBeDeASwDEdV0vkbSpA/AogGsBDAP4HwBf1HU9MZZ7Ogm4ZBNLstCashFwE12VfNV0LccM17hIFV0A2M8Fk44Vykkv8+6T0JVpEZaqtsRsCQ7sELxRW2YDUi1yFKKTRjYMkFfzZFLlyr4HcWPCqzJl6k/axm7BFe/Jp90yPfMMJUJ40GrW7DqOyVHG27h+A0A98DhVrKxIqMgg6T1ZEU8bBm2nhrNT9anU67y6TmZPFGH3bVmOGc9JFnrgNLsKf8+g0JZu4MRNIX0XKhrHFSnjX7bXTECMm7OHpmlfBTAAoBbAx0VGpmmaG8BrADoB3AOgGsDjAH6o6/q/ZHEfi7OH3USRGWhVO10m6SjSzDjJNSdCZnNwtFPlrrdbqCldtmm3bBZ4u4VBRYeqDwBjDoVwmtrHTlqVvWdVH5myvsg8CO3ya1LY7fb5flh7Tmsgo0H8RnsagiwN16J7CaM89LC5ijRDJnpluTDFTVIWBWFV489ki1JKnqINSojbs7PfSr/NDM/EyTjtvjG7OXU+ci1efdWXx+Ts8eJLD44LXeOJcfda1DTtdgD/JmFkNwP4I4AaXde7jGN3AHgYQKWu63GH/RcBGFyNtSz7vVNIPz6bVDY8ZJONtnPK0JxMgreKbPqxqGNtmHSmxdlusov9yRitrI10A5Ll+DKNxa6NHe2yazLdP9PiK71ewWx4iVR08Gh9gGgH6p4Kk2sksYCiVMerwWTfvoU2fuMnMpEsEmPbqf5k4DeaTjY8drkmZUyHmhXYc2mLkpRohlpRFhsnXitjqufDa/HqVWNkZNsnHiNzZW4yblgB4ABlYgaeAlAEYJHqIk3TfJqmFdF/AArHmc4ccsghhxzexriQEtkPAMzQdf0m7lgAQBjALbqub1X09wCAr4jHTYU1+awOioJ5fDu7zBNZ7fjHmN1BRpuT49nSoaJHtaM9F2O3o8FWAlMEW9upk5zSrlKL8lDRZiuxjbGUj1NkVOfyyWoFyY3S7FTaZeCyrQBQq/Js7Foy9Ww278dO6uVVn+FaPwCYYwoVUqqTv+0cqZzQbTnPrTfXXnk/nt/zdWA8JbKVXxqbRLbja+NC13giK0amado3AdybodkCXdff5K65HeeWkfkA+LhDhQDaZPXI7CZ+tuCznGdjf3Fyb4stxGF/qn5Vqje7dtnQmy3WuKxGdhMNDoKQndCUjdOErc2KayOrS5XpWtVim+k90GekVHkrFlXZuFU2Ics3wWW3t8vColrgpc/Bxt4sPhcn74G/v9OEA9Jn7GCjobLv8cfF96RqKx7j6Tkf2e+vaRwbI3th58RjZNl6LW4A8NMMbU467KsTwDLh2FTunBS6rscAxOhvTdPYOdMHZEzupXduREVT2jZA26kmqgjali8TwruiZ1q0eKgWZHGBo3042gVm8ES00MctMpkYhFObT6ZrnDJvkQ7Zwm9ne8kmlZPTHbYqsbMMqk2C3XO1LKKb0m14acOU3UTCwOzsWLJFWhw/60Pm+cqnBZMsypb+RBuUxCaVcZPEh8dw3oA7N90ttWOL/dE1QPw+nKSnk42Tf4Z8IVfZN5dp06Oy951z5FJUncMbZHb2qNZ1/axx7JMAvg1gisGwnPQvrRBttzu2m4yyKrumNg5cgzMujhnaqPrOpA6TtbVVRwlqF0thQQfqQidSiN1u2Al4eu2SFquuc0Kr7Jvg3dUzeSdSqBYuyoQAmOOPJDt9u7FYxiSRdlSbBHZs5UNpNZzCqcNOmuDvbVLh2dTnyuRFK94TkFerzkaqY3RBzfTEuaDKHaqSsnhkej98H+dDtbj6yvvHJJE9//JD40LXeGI83e/rAJQBeB+Ie/1Vxqnjuq4Pc+737QA+D6AKwM8A/PdY3e9F1SJgvytSqRMAZL9oGouDKXu2cJ3dji9T3yo7nmwcdgwv08Ju9ywsdDmQSJ2MMRNDkDFFwKpCHCucvgfxGpFOIP0dUAle5U7vhA7LRsMhY6bXyrLhZ7yn+C5kVdQlnn+2Uiac2eecYCztTVCoRWXPgX/myvRSNnY/9pwknqbnw/1+9bL7xsbIxonBjifG02vxQQD7AXwVQIHx934AlwOArutJAO8BkASwC8DPQeLIvjyONOWQQw455JAZezRNe0PTtM9caEKcYNJkvxfjyGx3hQ7VXFTVaDLs2lybreojk7SokqRMbbMsJ5JJXSJClXE+kyoxWxXQW2lj97ycPMOx9Mu3sTtOz9n2YeM9yyCrGcY5aqhi/sSyNyrpMJPa1dRfBm9gu+v5Yyq6s1GpZ9ImiOecaFYAe4chVkFAaLf0zo0sOJ1dYzwnfh6tWfkQntj6j+MvkV0xRols78STyCZNrsUtg4+zv53Yjvh2Kt22dGJxGbdV9ZHEvmVwwsScqj9UkOXhU052IZciPSfabFT3y6hKdJACyE49JbNN0PPi/2tc62wXNRkNsjayezpdEGVQMg36TSm8+0yLoGxcMmcKusER+5NUBmDqWqEfPnWTZa4oXOhFFbvKlgTIGbft978yXR/PMk5J/zK6Lc9JmMdOMrXQY9SeTn9X0PuIqdJWPkSqnHOb4fNRj+ydlGtx0khkpjgyxcebyebDw84ekY1UJ+uXp8XunpmOA85tIXw/Y5GYnNq+7GxHb9WmlY19JJOdhke2UqqT43aMVJXxQeyH9hFet9xSqVq8h8qDTnb/TFoCnm5eK6Gij96fZ2BO+mbPwVj4+YwZqueh3OxkyLJjN2aZE46Kdtnmih4X2zSu38Bi2sR5ej4ye1x72RfHJJH9dd+/jgtd44lJxcje9YkfAkBGhwu7RcoplCoaYUcqtnfab7bnnLbPuIhl6UjB7zJVC5GpvcyLTJKs2ek7eysSkt31dhsZkSYKO6nRiYRpCmgWkM03IfsmWb9ComnxudLExhWP7VTe+1x9ozIJVOZUIT4rJ5sIpwzJrr3dhkM8tujejaj59k5T38oN1IqG86JavPbSL8LjzpKRJUfw11cnHiObNKpFQM3AZDYIXi3Awy641BF2NWGnjfrLdK8Mi14m6UA1eVVZMez6ykSjDLzqiT2vTenrZP3KVLGZApjtnqHdcUfI0uaZiSYnNGa6RmTwloBlBcNTMk9JaRTVu67gzquYB6XN5KWr8my10xhI3NJZf5udMSNRLSlrZzdmWT/0WHDzbqzZbJXgG9dvYNnv6XU1XP9s48CVNYJwPqdaPLeYVIwshxxyyCEHAzrGEBA9LpSMOyYNI1tbfBvzWrTssGxiXgDzznus+QLHAuVuV6L+EA3Lsr7Y3zbxb1SKyqRGdKKyU+3AnUCUIAGwHbpTFZIdfU7VX5kkV6cQJVA79VImCZP1I2alcGjbcvKMVO9X/OZkz4AeEzUPKhshg6K2mUyroJoHIlg73lmFc2jJpMpmddck47fcw8DO1GZTBhb2XDgHG0qH9J3tagKWLQb2bFGOK4fsMKlsZLQeGWDvLSVDpkmj0q3L7menFlTZVJzQolJFquhlk1awOzkxVPPtLLTZ5EY0LSySNqytjcrpXNgC30q7TG1l71O6oNlcI/uOVM/eSa5CmSpXZcdzCmnJEyEMQKWKV9Fiucdb3AyK96P3lL6DDN+cXR/K8k68/RHy5ysyS+D81CO7ruFeeNy+jO15JJIxPNf08LjQNa7QdX1C/wMp+6IPDg7qFDdoH9RVuKHxa/oN2gdt29B2sr7ocXqO/2e5j9CWv0Z6Tzu6Jffhacw0Htl9pHTzY5KMNRO9Yt98H6q2suOy61TjtDwXyTNy2peKRr693bNw8oxUfdvRzT9P2TtStXcyPvHZMboU70B1nd0Y7e6baeyqa1Xf7ooPfcdyb9OzUozXch/Fs5XRqXyGwrjoNauxVgdR5BXp47QmXrfkXv3GS76c1b/rltw7bnSN579JI5E5CYgGMquiTB5kitRAdhhraRG+jR2dtrSLTi2K4E67e5q8xjgPt0y7aTspklf7yFSdKvWe6l6ZkG1bni6nkjltk0nNa6dCVdKgyPsnk+TspGmRRjtpXhmcbLwf0UWdvtdM6uWehiD2P3JX9lK2w7RotnQ4UMU60dLI2onPnk+cIGvLhzCscZ0f9/vrF39+TBLZswe/NS50jScmjY1MBvpROf3wAeuClmmxsNgYbJiGU9WKcvJlyHEnU5uINivZ5OT7MHmN0bEIto1MQagmCPFN/MQX89bZbRrszqlsQqoEz3b2I2qLzESH6PXqZJEWaZE9AzsaZcxWGfRubB4sxwWwOWLz3dJ4KJEWsT+LjQiAv3a5ZTwqOFG5Sk0GKq9XagvmrxWCqlUmAPF+fJ+yZxXcvBtr2h5C+z2N0jGJFQSGhs4Dj9DfOdnvJzUjyyGHHHJ4xyLHyCYetgw+7lgtJzPYqnZidn2NxXg9FtWhk36VyJClnD8m27EDZi9IUzofwcGBz/TNdu78s5Zkn2hcv8FERzbqYL4fRoN4T8k4Vf2vca1jtb6oV5rsWWV6Xjxk0jz9zdR0gtSc8fvlz0uCpy33t8nlaHEMET1I7bwlOUmdSpiihGiq48e1Vb0LXkK0aBMURU5ljhpiv9QDM5P2w/SdSyResQqAk2+zcf0GU4qqbanN5yWO7J2ESWMjU5VxkUHloaSqestUNbCqh8RJpbpWWuaB61fsW0m7xJYhU3+qdPV258U29H6ijYS/t3htpg2ARS3mwPXf7jmPxXZmZ2vKZGcSxy1lkrJ3ZOPJKPZBk8+K91M9F9X7z3R9JvDMzc77FLD35st2A8Zn1ABg9ZR0qOZXfuNiiIiNx6FT2M03Cp7+82IjW3D32GxkhzeMC13jiUkjka1d8y149h4B4NyAyx+T7eoppMxHmKBOFgvpMRsjtWqRyCQ98gzSxIQl9KpoZv0ZdhZWlXhzmjYZg6E0q6QQEw12Y1cwDvG5OJGcZQxclLBk34XdOxQ3IexeikU/m/jE/Y/cBQju2jJ6eLob129AUKRHkgjYQq/IDAV3ciebEhlE6c9u4yQeD27ejUZsAAw7pJj2zOlGRiaNNq7fgKAkLVZw826pFG/JMykUyqS20qCCFr4/PuPHeZHIUgC0MVwzATGpJDIaR+aEqdjtyuk1TtVbfB8i+B2t3Y4/G2S6LtNOXaZ6sZXSskj4qypI6nSsdvTxbcS+nS6SKkZpeTdZFBPNdI04FjvaZeN39O2J+SptPEUtpXkk2gjTgm0nTSo2W7a0Ovg+LTFcktIxsv54mBizQGOmuc1rUhgNgPLZmlSSDryEz4dEdsPcz41JInvm6HfHha5xxYX2/z9XMROrsVanEONgHMWN2cREOelDFXtjF7emilES7ymLN+JjipzQL97Prp1TGrOO6XJAo5N+Vc/LCTK9B9NxWRwV98zZbz6eSPjmVnzoO9IYLyf08L+zjQkzPSuDxkzvWXbfFR/6TlbzgG8jpcXmOzf1IcTL8W3Fe9nSwr0f25gxSYye6n6XfPq7pvlumoeS+c7Ho9Hzq5fdN+5xZDfMuUt/1/wvZPXvhjl3Tcg4skmjWswhhxxyyIFDSge0LDVuqYmpoZtUjIw5JBi/LdnCzwHsbDeqNjJnApnNq3H9hrTXnA0c298UKiqRFpN9kFOZ2NlAVI4K/HknxzMZyPmxrHGts3X8UNEo9i2+Hxkt9FqL44ENrXZ2TNU5SzuVBy2nIuPVWDQDvThWdo2NilGEzP4IwOLBycdnZasW5+/FxiKx55psezb3k9n3TGpOrh8at+dEBap6j1jRgIqmcPo4179SxSkp2klSVH3dloa3jHeQ+/2ksZHZZfbgjwE2OnHIFzOxHZs0GTI0OOrHgTHd6cI9lvFk257ZwBTjz4Yx8X0CVocImb3SqS0sE0227xUYU1YXRrPEE5U/ble2RmWTkvWfbc24TEyfh4XRKOrEie2dQmlPltjI+GvEd8RfZ4JQd00M/XBKtyrLiuXvLMs/nY9cizdc9E9js5Gd/PdxoWs8MWkksi2Dj8t3kxycSAf8Mbs+pJ5pNgxHlQLIbpEe627Xzvitai9mgqDjl/XFt6FS8M5Nd6d31sIipNp9ZxxfhvpZqnO8od7pdyC+Vz6+jfUJ+3dMz/PvmtFix0wFxmRagGH/jYhOCTytfN924DUB0o2HmCSYr1LAeanKGL9sM8L/VklY0jFm6N8OMibGj0eWDFnMUgLAUjlClAKliZbh8Hs/5xiDRDZB67hMGolM5rVIkY0aJKvFX9HOtphgBrpEic9uPLL7ArBIE3a7X74P2W5TtnDY7cplKkcnkqCKDtl936okoGIG0lyDkvFkdT9BerDrw4lkqXofluOKqgf0dybJMxNDspOaTJCEqljaC4xcpiqU0WXH7FXfoYkuo29aJDTYFnX0nui92+9pZFWhVdeo1oLzIpHN/Cw8riwlslQMzzR/b1zoGk9MSkYGpD9cUz47B66x2UK1YMuYBP+bHnPKXJ2o4mTXZAo6BjDmKskZ1VFZ0AggvTOGevEyXW8TxG5Hn9gHDfjmbWF2myEV8zCNSXLvTH3b0ZkNGtdvQLTchYrHdso3LA4TNTPaRIlPEuys3FyNURJRqfBkbVQZP6T92pgELLRL3P5Z3kkuNAGQqx4tYQ7ce7hWuxXPYwswnoxsxv8bGyM79Z/jQtd4YtKoFnPIIYcccuCgp8i/bK+ZgJhUjEylb1eq/Wx2U+JvpdpCYvOxs5/I+ra7nwiRfrtAVJrjje9ffDZ0/NmqBFkb7hnyO1AnQaEyu4ls7Jl29Kpn5USFR+lkdNvs/AEo8+vxWdWdvFvV3+IxETQLhd0Yg5t3E5uXUD6F/S3YQmU00nvtNN6xRUXK2ax4WpbeuVEp4chKwajGyR9XahZ4D0fBnqpUBSsynfDvFwBRNVLVLGeztHgV816LQuorURrj38OWwcepanH8kPNanDjgvRY9Wh47bmcbEiFTw9naCGwydWSz6ErVkZK0Qm9VNXMu4ITB2alWnfYt9qPqX9UHTyP/2wkNdvaNTDQ7gcpek+0zUtmO+P4cbcJ4WiTqZTs7LT1vV4VZvLfqOajeu0o9z49Tdh2QZviy+UltYgBhNmtWPmSqmya9ZwaP02w3Wwl9dPxVi9M/PTbV4ulHx4Wu8cTkkciWLca2l7lYG5q1WkhRw4MtCNzuXLWoyiaNnQSo+sD5fqQxQxkYpN0CyN/TTrLLhhnINgQqJmOCWMPMRgJzyvzs2lmkbgndUnuP8H5N9zMcAVRu4DJanEgZmexJ0gWdd4GXSOQA5LkfM2gH6LMSvTS3pTabNnUqO5sdk2QQ6FLND7tv1m5zI/s7KHiKis+WeVsqPGxF2pU2Rb4CgPg+FGPGigZg5yuWNuccKZqkI9trJh4mDSPbsu3z7O81Lq7woU3WbCeeharF14n6UOxbvEbmEiy6Mzu5p4p+GQMSk/2qaM/EkO2u5ccmnpfRqGRIDqRAKS303jSkwGYzI95HdtzSfxbPxe56tqAK8VB235ypH1Via46RZ6TVuPfOTXezhND8vbalNsudgWwqfos5CmWLO3+dqHK03WiJfXOMVezbspHhmHZQ5iIvC5HJpLaU9CPOV34jAJD3xnktjh/eQarFScPIcsghhxxy4KBjDIxsXCgZd0xqGxmQWe/OQ2Yjy7Rbz6Smk9kBZDTa9aXqW+yj5w5SZn2/YOS3o008rjrGBz4rVWMOsvy/FUlGBaWk6iD7ikqdJ/abSUKye8+ZsrY7PTbWZ5dJ/Uclw2xUqOwY53ChkgKzkab5e5livRz0IbUdKrKAOFEFA+nacNlI62Ib9jy48ZwX9/uqT8Lj8mZ1bSIVxzOdPxgXusYTk0Yi2zL4uCmOjIJWhgUcqMckNjLZdZkWZpne3s4W4xSZGJBMvSKD6pxqDEDaA4u3PcqM+paihbB/Tio1mokGah9yaN9ix20WZtn9VHBi92JtOe9F/nqVCpEfJx2LzA5jai962yreBd8n3xdPt11MYiYGb7dBcMooxH5l6b1orTVqMqBem7xqdltqM3PgcKo6F4/JjtPacJbnxOW5BMzfvXKzxLU5L16LqRSyLjCWyrnfv23AT0Dec0l0ArBjWvxkdeLyDKQDIKXSgaAnd7JLt1sc2DgVjg0y2O0QVW0sC78kASpPm+q+qgXDTppyshjyiwSjTcIsxTGpmKcMdv2J9IrfFutD8rxUDEF89nbB4bLxALDmGqT0ih6xmQKjMxRlFZEpSN3UVsKwZdfyjAsA1mzmxsqlAgty9MlCa8QQCZEWmYMS7a+nIWg6h11NLDSBp6Nx/QYILaXv8bzgHWQjmzSqRTGzR88djRaVgLirdaJKAeQSBf3wxaSwThxIVMiorswiUXHGeylyP46VNidt7FSOdv04UispVH/iouaEKVIsvXMj2ZHbtMl0Lhvp3UK3yAwVmwsVMknwst8yelV9qMaSaXzsnCrFlcCETRuvLFJISRm+TUhFpj5kdDJaZCp1m1CE85KiqvLjY1Mtdv9oXOgaT0wqiYyfjKpy8QySoFC7XadUVSGZbPQ385rk4GgRWtFg69pM+xFps1sQs6FDGSSewbVbtfg6lbh4urOVmMRrLC7VqgTGGfrmmZjTBV5EeN1yBNuiWaknGST2J5O7N6XDWPgzef/J1J7imGTv044xiWpRu/FZ3rOMoXCbQct1Ctd2nl6+vUzKArg0UwIN4lj58dH5bEpjZoRniPfi34ts3OcN7yCJbFIxshxyyCGHHAzk4sgmNpzYQsQdvNNsGmznJTGa8ztCVbJQWdZxBs5GIO4we+5otN0xWsZD+wMsu1i7naEoibG2ingZvm+ZwZv/baJdSBMmtpO9O6dqtWxViCp6pdkuHKhPefDlUZyoUmUSRyZJdc3Kh0zpwda0cVJCBqikNFHys3x3QjIBqRqQuz68brkpvZNM1SfOWTsNCaWdOQFJ5oVUktzVBKxbbimIqbqHRcrbnPbi5VPAmbQBinfOazvWFt9mude5hq6noGeZOzHb9m8XTCpGpvogM9plHFbQZf1xHy9VOQQF3b2SFhsnCQsj4sBnMs9Ep+h+nMlG4gSZ+rCoPYUyGapMH2Lfqr/FIF++D9l4ZOpVGZOU0SD7rRqnkl6HmwfTBsSB6i3jtyy5jmd47FrBSUHGROzUv+Fav9XexHlXZrKvycYtOye7ns05LmejSKPd86YqWNm4LBtNhS05Wu6SXr/0zo0mJk+vH8uce8vQ9ewlrJxq0QxN0+4D8G4AlwCI67peImkje2p/q+v6r84lLdJYEskkFcsu0HOOdolCOXi7BU+FTIud3SSXLdh0zGJ7y8LC7WxVSVVZW1FSU41FcIIRJ7N012yTBFnmkaiSVHha+f/5e4oMQVzIMqV+skijnISheoYyycs0TofPX3pc4lhg+Vb4Z6vQQIgbPJWkSjdudpKZkl5Bm8Hb9uzGvC21mUh2dI5yc473FhS9jMVxyXIwSr0cOclSbF9hSOuLCs207n/kLjYelaTtRFI+J9DHoFqcoIxs3LwWNU37KoABALUAPm7DyD4K4C/c4QFd10eyuA/zWiwqKjKdk+4yHaqc+JpOACzBmbQ/dm0GbyhVElMe2dA31nHKVDrSe3EekrKFXlSNqp6FisHKpCk71Vu2u1kpXTb3snteKhUjP/6eOxrh701Z3rFT2gDzM2e/gYzSQaZ+xfM8M5A5FoljB6xSnolxc+edJBLmx2bRHvCxY4ZDBj9+3sFCjMvjn4vyffKbNrEPLpkwk/bE9uC0DJIaaE7n9PkIiL6+8P/Ao2XptajH8WzoF+NC13hi3CQyXde/AgCapt2eoemAruud5/LeogpJtouX6dD5DzG4ogHBzYp4GJvcc9K+Vz4EGBNE1UakTzUeGWS7aSnDlASbyu7FXy8NcLbxHmP98OoVBf184lYZ3ap+nQY62y0qvFepSm0ZXrccQYAtbmJ7Gb2mGCejLQ2cldkDTd+SoObjS6bAoEMsIyIyFNMxG20Cg41anV0rqoUVz0vZj80mwCSlc8xwp80mK5PKlcJkN6TfIJVKJdk/LJ7CPJMX5nd43XIEhRyM7LoMmwLsajo/AdHvILguNAEAvq9pWo+maXs0TfuYpmmaXWNN03yaphXRfwAK7drnkEMOObwjQd3vs/03EaHr+rj+A3A7iNQlO/clACsBLAVwL4ARAP+Yob8HYKTD5P+txlqd4gbtg/oNjV/Tb9A+qIugx27QPsj+sXONX7P0Ibverm96fMWHvqOv+NB3LPeVgb/Orp0d3fy9TO2FMajGJLu36R4OaBTpsgPry3iWds9TfC+yv03tVe+U3ktyT9ou0xjE5yD77eRakTZZ20zjlLWztLV535Y+G79m/sd9y5n6sMwdybtQQfaeV3zoO9Jx2vVtam/MCcszz/CNS/uyOS7SLvtWZXNwcHCQrl1F+rlfc4sA6NcFPqzfGLwtq3/XBT48bnSN57+sbGSapn3TYDh2WKDr+pvcNbcD+DddYiOT9P8ggI/quj7dpo0PAF8trhBA2+pl98Gz9wgAWNQqUhuNjVGe9mEH0THEkX2KU/+Y8rQpruVVghnrHPH1qjKofRypnBxA5WAgo91yLUczH2xqOQ/BSQFy+4otnZLn68Smko29klcTmmyEEgcWp7YsqQ3MJnuM037trlF+c0JwtvgMsqHFkXORmFfTJqsNBU2aXdEUtrf/Ct+SLBREFXZhR5/svaie0fnI7HGdf/2YbGTPRTeNC13jiWwZWSWA8gzNTuq6HueuuR3OGdm7AfwRQL6u6zGHNFlSVDlZsEWdtWwxk0188Th/3rSYKRZPlVME37dqQbVdWBWOADI7kXgfFQOyM6arIGYLVzGdTE4iqrZO6bBdSBVjN7XJkDOQbmQy2R/tNlSZGCVbmCWp1ujYVM8RgJJZyK6jdh/T5soYU09DkDk9qeycqmelcoIQ722iS1LMkp3PIuZTRQvfJ9+vzEZmNy7ZvS0MTfH8zwsj831obIws9utxoWs8kZWzh67r3QC6x4kWgLjq9ztlYiKUC5JQxVWstAukP0x+4VV+wFw2douBHuZJYscMs5GEZPFgPFQMcVvKXILFMhbIJRJVNvVM9Fc0hS0LJTXq09/8cRkdfDtGj+I6qZTFuUw72Yyw63lGarxf0dmBnmdMTOL9pgJzM1ecF58pZR7hdcuVSZH58aqYilLqgvk7WeNaZ3Jpz5hQ2LiX6T4K7YH4fqgDzdI7N6JCaCejm/7d0xBExS5rv6rNn+nbp+9TgHSzIWobJE5PPI2Akd9VMmb6bfHZ+Z8Y+JG0v3MKXUfW2e8vkI1M07T3ANgA4rfxsK7r/53N9eMZR1YHoAxAHQC3pmmXGKeO67o+rGnaewFMBbAbxDa2BsC/APjOWO63tvg2/FV/EoB5N21RHSh2WJaFTIBpAnCMMNPCSye3bALxNNFr7Gij/Yl9i95t4gIkquzE+8i88GSMx/IcxN8rGtC+Kmhpr3y2khgd1W+VSpA/z45nkZmfvzZc67e8Z7oYUldw8X1lgvj8ADBmIS6eqmccbIuaNkwWl3hJrKDFVV28lrsX72HKFn5BohZh2fhw3ygPKlWaYGSOB8jGR6RPpJv17zLitwTaVXMGgCXMQEwErdwgqDxIhf5lUG2eWH7H1GZce+V5zoT/NoamaR4A3wVwLYBBAPs0Tfudruu9TvsYz8weDwL4B+73fuP/awE8D2AUwGcAbASgATgO4HMAfjiONOWQQw45vCOgp3To0pwTNtdcGIlsGYBDuq6fAQBN07YCuBHAL512MJ5xZLeDeCyqzv8F5kDocwq2y1VkqLfYA2DeVSpzDsIsZYgQVZSMBoUNy84RwnROkLr48djtSHlaRHWpncpJZUNSSUdsnK51WLM9rIyrs9hvJHTLxmSnQrKMV5ByRLufSrIz1a7jzts59ZjokzgxWMZtjJ3/fiyqXxsnGJNqlarNJapE8Z2x46LaT3Ae4XNDqhxLTGPh8nma5o9s3IIaVqYS5h1jbNWTAi2qecCerTGOisd2Yg1vczSkWfFZq9S3do42mb5Zfj5v2fZ5FBd/3ULvOYU+hsKaY8i1qGna1QDuAXAZgGoA79d1Qz2WbvMZo00VgCYAn9V1fY9xugbAGa75GQDTsqFh0uRa3DL4uOWjlSHTQu5kAZVNGJmKyNSPTb0ikXmqFmsAagYhUTmKgbZ8O4uK0FgUM+bpUzjG2PXNj0FcVMVzdvYYp+8i2/dJ3wNPu+pZWlSmElWkVMXWEGQqrTUrHzIxPROjVHjRSZ8L9y5U3x8fzC379sX+pRsDmXrRKDdE+2eB2ruapOpX8ftkQdUyT0GxIjb3DizlkSRej6ZNSIYNqK2KkAvYl+UvVT1DJ+3Oh43sPEpkQRDm9GMAvxVPapq2HkR1eAeAlwH8fwCe0jRtnq7rZ8dyQ8s9LpAoec5APXRWXfbP+NNzXwIArPrc91H+o5exZfBxU9u1xbch/P4rEDwTxZZtnzdloKZt6THZtfT4Dbd/D8/89LPmDNbLFpM+13wLW7Z93nTdlsHHTf+L95P9LeKG27+H4O/2snsBYPfDnoPqPjl6VP3zNK1d861034pnIY7NyTGxH/ounvnpZ22vFc/Jxktxw+3fAwBTn8p+hHdPnxMdP70Hli0G9hy00O5k3JSm4O/2Onom7LhxTxGq8dNr+O/OjiZVm7F+N9JxOPiOTO/Upq2jZ2Jcz9POPyu+T3Gc4vvlIb4/OvfF8YfffwWCv9uL8PuvYMfYfDXOs+vWfAuJPfuxHX8GxtFrcRVugQd5WV2bwCilqxZAiDsVc+KEZ6QdNElkmqa9DGCvruv/z/jtAnAawPd0Xf+mpmmNAO7Rdf39xvl/A7BH1/X/dUr3ZGBk0wC0XWg6csghhxzGgFpqGzpX0DQtH0AziBpvLBgGUCAc+6qu6w84uLeJkWma5gUQAfBBgbn9D4ASXdfXGs4ehwGshuHsAaDx7eLscb7QDuvuQUQhCLPL1O7tiIlMOzCx6c/RfmEwkWkHnNNfCLJ+nVPouj6iadpMANkFkdljTCFRACoAuAF0Cce7AMwHAF3XE5qm3Q3gryDu99/KhokBk4CR6USktN3RcOkbQxMpyA+Y2LQDE5v+HO0XBhOZdiAr+sdtbDqpIOK4isiFhq7rvwfw+7Fe/3ZIGpxDDjnkkMPkRA+AJEjMMI+pAM5Z1ZMcI8shhxxyyGFcYKQr3AfgenrMcPa4HsAu1XXZYsKrFh0iBuCrGLue90JiItMOTGz6c7RfGExk2oGJT39W0DStAMBs7tBMI5NTn67rrSCu9/+jadorAPaAuN8HAfzknNEw0b0Wc8ghhxxyuHDQNG01iKOGiP8xEmNA07T/h3RA9Gsg5bpePmc05BhZDjnkkEMOExk5G1kOOeSQQw4TGjlGlkMOOeSQw4RGjpHlkEMOOeQwoTHpGZmmafdpmrZT07SIpmkDija65N+HzzOpMrqc0F6nadqfjDZnNU37tpHy5W0HTdNaJM/5CxeaLhk0TfuMQe+Ipmkva5q27ELT5ASapj0gecZvXmi6ZNA07WpN0/6gaVq7QeetwnlN07QHNU3r0DQtqmnaM5qmzblA5JrggPafSt7DuFX7eKdj0jMykDQtmwE8mqHdR0FKENB/T44vWY5gS7umaW4AfzLaNYLUf7sdpBbc2xVfhvk5f+/CkmMFl637qwAuBcns/ZSmaVMuKGHOcQjmZ7zqwpKjBM2a/hnF+c8D+EeQrOlXAgiDvIf880OeLTLRDpAyVfx7+NvzQNc7Em/Lnfu5hK7rXwEATdNuz9B0QNf1cxZpfi7ggPYbASwEcIOu610AXtM07UsAHtY07QEjGPHthtDb7TlL8DkAP9R1/ScAoGnaHQDeDeBjAL55IQlziMQEeMbQdX0rgK2AKa0TjN8aSLzRQ7qubzGO3QaSo+9WAL86j6RaYEc7h9hEeA+TAe8Eicwpvq9pWo+maXs0TfuYZvN1vo2wAsABg4lRPAWgCMCiC0NSRnxB07ReTdP2a5p2z9tNDWpk674MwDP0mK7rKeP3igtFV5aYY6i8Tmqa9gtN0+ouNEFjwEyQmCP+PQyC1LOaKO9htaHuP6Jp2qOappVfaIImK95Wi8gFxJcBPAdSbuBGAI+AlDH4jwtJlANUQZ5Vmp57u+E/ALwKoA9EFfqvICqXz11IogRkzNb9NsfLIOrlIyDP9isAXtI0bbGu6xMpkzz9fmXv4e34bYv4C0iRyWYAswB8A8BWTdNW6LqevKCUTUJMSEamado3AdybodkCXdcdGbl1Xf8a93O/pmlBkCj0c87IzjXtFxrZjEfX9e9yx17XNC0O4L80Tfuik6J9OWSGofKieF0jRQ1PAfgQgPEvS5wDAEDXdV71eUDTtNcBnACpufXsBSFqEmNCMjIAGwD8NEObk2+h/5cBfEnTNN84LLDnkvZOAKI33VTu3PnAWxnPyyDfYD2IBPF2wHnJ1n2+oOv6gKZpR2HOhTcRQJ/1VAAd3PGpICmOJhR0XT+paVoPyHvIMbJzjAnJyHRd7wbQPY63uARA/3hICeeY9l0A7tM0bYqu62eNY2tA6hy9cY7uYYu3OJ5LAKQAnM3Q7rxB1/W4pmk0W/eTgClb939eQNLGBCOh6ywAP7vQtGSJZhBmdj0MxqVpWhGI92ImD+S3HTRNqwVQDjNTzuEcYUIysmxgGLrLANQBcBtZmQHguK7rw5qmvRdkl7cbpBDdGgD/AuA7F4BcEzLRDuBpEIb1M03TPg9iO3gIwPffbqo6TdNWgCxCfwWpmrsCwEYAP9d1vf9C0ibBuGfrHi9omvYdAH8AUSfWgIQQJAH88kLSJYOWIWu6pmn/BuB+TdOOgTC2r4FUVH7yPJNqgR3txr+vAHgChBnPAvAtAMdBnLFyONfQdX1S/wNRe+mSf6uN8+8CsB9kcR0G2f19CoDr7U670WYGgD+DOKp0gzBgz4WmXTKWS0E2CwMAoiAM+IsAfBeaNgW9/w+EGcRAVKBXXmiaHNL9K5DFPgagzfg960LTpaB1teL7/qlxXgOJiewE2WQ+A2DuhaY7E+0A/CAM6yyAOIAWAD8AMPVC0z1Z/+Wy3+eQQw455DChkYsjyyGHHHLIYUIjx8hyyCGHHHKY0MgxshxyyCGHHCY0cowshxxyyCGHCY0cI8shhxxyyGFCI8fIcsghhxxymNDIMbIccsghhxwmNHKMLIcccsghhwmNHCPLIYcccshhQiPHyHLIIYcccpjQyDGyHHLIIYccJjRyjCyHHHLIIYcJjf8fn1usfjm19ckAAAAASUVORK5CYII=", + "image/png": "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", "text/plain": [ - "
" + "
" ] }, - "metadata": { - "needs_background": "light" - }, + "metadata": {}, "output_type": "display_data" }, { "name": "stderr", "output_type": "stream", "text": [ - "100%|██████████| 500000/500000 [00:28<00:00, 17340.96it/s]\n" + "100%|██████████| 500000/500000 [00:34<00:00, 14299.87it/s]\n" ] }, { "data": { - "image/png": "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", + "image/png": "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tt/F2LRpE/t72bJlWLVqFWbPno2f/vSn+NSnPjWOMzMIAh/5yEfY32eddRaWLVuG008/HU8++STWr18/jjM7tTChBf0NN9yAq666yrXNvHnzyu5/1apV+NrXvoZMJjOuwiLI65w6deoIz21aNSmoSklBoZLrXrVqFfL5PN5++20sWrRoFGY3uhiLilbvRjQ2NmLhwoUsL/hkBL1/x44dw7Rp09jxY8eOYfny5eM0q7HBvHnz0Nraitdff90I+jHEhBb0bW1taGtrG7X+9+zZg6ampnHXCIO8zvPPPx933XUXurq60N7eDgB4/PHHUV9fj6VLlwYyRlCo5Lr37NmDcDjMrnGiga9oRSM/aEWrz372s+M7uVHE4OAg3njjDXz84x8f76mMGubOnYupU6dix44dTLD39/fjueee84wKmuh45513cOLEiZINjsHoY0ILej84dOgQTp48iUOHDqFQKGDPnj0AgPnz56O2tha/+MUvcOzYMaxevRqJRAKPP/447r77btx4443jO3Gf8LrO973vfVi6dCk+/vGP45577sHRo0fx5S9/Gdddd924b2jKxc6dO/Hcc89h3bp1qKurw86dO3H99dfjYx/7GJqamsZ7emVj69at2LJlC8477zxW0SqVSuHqq68e76kFhhtvvBEf+MAHMHv2bBw5cgS33347IpEIrrzyyvGeWkXgq5UBxAFvz549rFrZF7/4RXz961/HggULMHfuXHzlK1/B9OnTJ1w4r9t1Njc344477sCf//mfY+rUqXjjjTfwpS99CfPnz8ell146jrM+BTHebv9jhS1btlgARvx74oknLMuyrF//+tfW8uXLrdraWiuZTFpnn3229f3vf98qFArjO3Gf8LpOy7Kst99+29q0aZNVXV1ttba2WjfccIOVy+XGb9IV4sUXX7RWrVplNTQ0WIlEwlqyZIl19913W+l0erynVjG++93vWrNmzbLi8bi1cuVKa9euXeM9pUDx4Q9/2Jo2bZoVj8etGTNmWB/+8Iet119/fbynVTGeeOIJ6Xu4ZcsWy7JIiN1XvvIVa8qUKVZVVZW1fv1669VXXx3fSZcBt+scGhqy3ve+91ltbW1WLBazZs+ebX36058uCe01GBuY6nUGBgYGBgaTGCaO3sDAwMDAYBLDCHoDAwMDA4NJDCPoDQwMDAwMJjGMoDcwMDAwMJjEMILewMDAwMBgEsMIegMDAwMDg0kMI+gNDAwMDAwmMYygNzAwMDAwmMQwgt7AwMDAwGASwwh6AwMDAwODSQwj6A0MDAwMDCYx/n/4sBSHrl7O8AAAAABJRU5ErkJggg==", "text/plain": [ - "
" + "
" ] }, - "metadata": { - "needs_background": "light" - }, + "metadata": {}, "output_type": "display_data" }, { "name": "stderr", "output_type": "stream", "text": [ - "100%|██████████| 500000/500000 [01:46<00:00, 4710.43it/s]\n" + "100%|██████████| 500000/500000 [02:04<00:00, 4014.01it/s]\n" ] }, { "data": { - "image/png": "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", + "image/png": "iVBORw0KGgoAAAANSUhEUgAAAfoAAAG3CAYAAABc05f7AAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjguNCwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy8fJSN1AAAACXBIWXMAAA9hAAAPYQGoP6dpAAEAAElEQVR4nOy9eZgcxXk//uk5d3Zm9j4lrbQ6QWAZgawLMGCEBPIXgwPIB7GRMUlwjJ3Y2Cg+uYxjYn1tE5+x83Mwjk1CMF+fCQ63MYcOC2QLLEAn6Nr7mtmdnaOnf39UV3V1bVcfM7MrdtWf5+Fh1FtdVV19vPV+3kvRNE2DDx8+fPjw4WNGInCyJ+DDhw8fPnz4mDz4gt6HDx8+fPiYwfAFvQ8fPnz48DGD4Qt6Hz58+PDhYwbDF/Q+fPjw4cPHDIYv6H348OHDh48ZDF/Q+/Dhw4cPHzMYvqD34cOHDx8+ZjB8Qe/Dhw8fPnzMYPiC3ocPHz58+JjB8AW9Dx8+fFQAf/M3f4P29nbU1NRg2bJl+PWvf32yp+TDBwBA8XPd+/Dhw0f5eOWVVzB//nxEo1Hs3LkTl1xyCQ4ePIjGxsaTPTUfpzh8jd7HtMDtt98ORVFO9jTwox/9CIqi4PDhwyd7Kj7eZDj99NMRjUYBAIqiIJfL4dixYyd5Vj58+ILeh4+y8dxzz+H222/H0NDQpI/18ssvY9OmTViwYAGqq6vR1NSECy64wBNNvGvXLlx22WWoqalBMpnEhg0bsHv37smbtATZbBb/8A//gFmzZiEWi2H16tV49NFHJ7T70Ic+BEVRpP+9mYTpRz/6UcRiMaxcuRIXX3wxli1bdrKn5MOHT937mB64/fbbcccdd+BkP66qqiKfzyMajTKG4f/+3/+LW265BYcOHUJnZ+ekjv8///M/+OY3v4m1a9di1qxZGBsbw0MPPYTf//73+P73v4+/+Zu/sT3/hRdewHnnnYeOjg7ceOONKBaL+O53v4uBgQHs2LEDp5122qTOn8f73/9+/OxnP8MnPvEJLF68GD/60Y+wc+dOPPnkkzj//PNZu+effx4HDhwwnatpGj7ykY+gs7MTL7/88pTN2Q1UVcVTTz2Fl156CX//939/sqfjwweg+fAxDXDbbbdpb9bHdevWrRoA7dChQydl/EKhoJ111lnaaaed5tj2ne98p1ZfX6/19fWxY8ePH9cSiYR21VVXVWxOF154obZ582bp37dv364B0LZu3cqOZTIZbeHChdratWsd+//973+vAdC+/OUvV2K6tjjvvPM0AJb/ff7zn5eed/nll2v//d//Penz8+HDCT51fwqB2rlfe+01fOADH0BtbS2am5vxxS9+EZqm4ciRI7jyyitRU1ODtrY2fO1rXzOd//rrr+OjH/0oTjvtNMRiMTQ2NmLTpk0me3Umk8Hpp5+O008/HZlMhh0fGBhAe3s7zj33XKiqajvPZ555BitXrkRVVRUWLlyI73//+9K2x44dw4c//GG0trYiGo3izDPPxL/9279ZXvf+/fvxoQ99CHV1daitrcX111+PsbEx1i6VSuETn/gEOjs7EY1G0dLSgvXr1+OFF15gbUQb/e23345bbrkFADB//nxGJ997771QFAU///nPJ8z5/vvvh6IoeP7559mxV155BW+88YbtusgQDAbR0dHhynTw+9//HpdcconJQay9vR0XXnghfvOb3yCdTrPjbta2VPzsZz9DMBg0MRBVVVW44YYb8Pzzz+PIkSO259M1vPbaax3HKve5f+aZZ6BpmuV/d911l3TcQqGA/fv3O87Ph4/Jhi/oT0G8973vRbFYxN13343Vq1fjrrvuwj333IP169dj9uzZ+Kd/+icsWrQIn/70p/H000+z83bu3InnnnsO73vf+/DNb34TH/nIR/D444/joosuYgIzFovhvvvuw/79+/H5z3+enXvTTTdheHgYP/rRjxAMBqVz27NnDzZs2ICenh7cfvvtuP7663HbbbdZCszu7m6sWbMGjz32GD72sY/hn//5n7Fo0SLccMMNuOeeeya0f8973oNUKoWvfOUreM973oMf/ehHuOOOO9jfP/KRj+B73/serr76anz3u9/Fpz/9acRiMezdu1c636uuugrvf//7AQDf+MY38O///u/493//d7znPe9BR0cHfvrTn04456c//SkWLlyItWvXsmNLly7FddddJx1HxOjoKPr6+nDgwAF84xvfwMMPP4x169Y5npfNZhGLxSYcr66uRi6Xw0svvQTA+9p6xYsvvoglS5agpqbGdHzVqlUAYOszkM/n8V//9V8499xzPZlKSn3u3WB4eBj3338/0uk0CoUCHnzwQTz55JO44IILPPXjw8ek4OSRCT6mGpT+/pu/+Rt2rFAoaHPm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MDAwMKhgmI3ewMDAwMCggjFjNvoHHngAV1xxBaqrq9HY2CgtEwgEJv33/e9/v7wDLRI68zx27Bje//73o7q6Gu3t7fjyl7+MdDpd3oH6jAULFky6dw8//PBUD6toOGW0qgTce++9k+7bxRdfPNXDKhpu2cosy8Ldd9+NWbNmIR6P45prrsEbb7wxNYMtAm7zvPnmmyfd3+uuu25qBjuDMWM2+mQyiU2bNuHWW291LPed73wHPT097L8bbrihPAP0CW7zzGQyeP/7349kMonnn38e3/3ud/HEE0/g7rsn56CfbtixY0fevfv85z8/1UMqCjSj1T333IOXXnoJl156Ka699lqcPn16qofmK97xjnfk3bff/OY3Uz2kokGzlT3++OPS37/2ta/hsccew7e+9S3s27cPNTU1uPbaazExMVHmkRYHt3kCwHXXXZd3f7/3ve+VcYQGADDts9d5xXe+8x2roaFB+hskWYWmK1Tz/Nd//VcrGAxavb297Nrf/d3fWfX19VYikSjjCP3F/PnzrW984xtTPQxf4ZbRqhJwzz33WJdeeulUD6OkEL8r2WzW6uzstHbu3MmuDQ4OWtFo1Pre9743BSP0B7Lv5+bNm60PfehDUzIegxxmjESviy1btqC1tRVdXV34x3/8x5LnRy439u7dixUrVuQFYbj22msxNDSEV155ZQpHVjwefvhhtLS0YNWqVdi5c+e0VkfQjFbXXHMNuyZmtKoUvPHGG5g9ezYWLVqEP//zP8exY8emekglxZEjR9Db25t3bxsaGtDd3V1x9xYgPuTt7e1YunQpbr31VvT390/1kGYcTFIbDjt27MBVV12F6upqPPXUU/jsZz+LkZER3HbbbVM9NN/Q29srzZJEf5uuuO2223DZZZehubkZzz//PO6880709PTgkUcemeqhFQSdjFaVgO7ubjzxxBNYunQpenp6cN999+G9730v/vjHP6Kurm6qh1cS0PdMdm+n8zsow3XXXYcPf/jDWLhwIQ4fPoy//uu/xsaNG7F3716EQqGpHt6MwbTe6Ldv346vfvWrjmVeffVVbeMePr/vqlWrMDo6ip07d075Ru/3PKcLvMx769at7Noll1yCSCSCW265BQ899JCJt/02xsaNG9nfl1xyCbq7uzF//nz88Ic/xF/8xV9M4cgM/MBHP/pR9veKFStwySWXYPHixdizZw+uvvrqKRzZzMK03ujvuOMO3HzzzY5lFi1aVHD73d3duP/++5FIJKZ0s/Bznp2dnZMst2nWJL8yJfmFYubd3d2NdDqNo0ePYunSpSUYXWlRjoxWb0c0NjbioosuYnHBKxH0/vX19WHWrFnsel9fH1auXDlFoyoPFi1ahNbWVhw6dMhs9GXEtN7o29ra0NbWVrL2Dx48iKampimXCP2c59q1a/HAAw/g9OnTaG9vBwDs2rUL9fX1WL58uS99+IVi5n3w4EEEg0E2x+kGPqMV9fygGa0+97nPTe3gSoiRkREcPnwYN91001QPpWRYuHAhOjs7sXv3braxDw0NYd++fa5eQdMdJ06cQH9/f94Bx6D0mNYbvRccO3YMAwMDOHbsGDKZDA4ePAgAuPDCC1FbW4uf//zn6Ovrw5o1axCLxbBr1y48+OCD+NKXvjS1A/cIt3lu2LABy5cvx0033YSvfe1r6O3txVe+8hVs2bJlyg80hWLv3r3Yt28f1q1bh7q6Ouzduxdf/OIX8YlPfAJNTU1TPbyCsXXrVmzevBnvete7WEar0dFRfOpTn5rqofmGL33pS/jgBz+I+fPn49SpU7jnnnsQCoXwsY99bKqHVhT4bGUAMcA7ePAgy1Z2++2342/+5m+wZMkSLFy4EHfddRdmz5497dx5nebZ3NyM++67DzfeeCM6Oztx+PBhbNu2DRdeeCGuvfbaKRz1DMRUm/2XC5s3b7YATPrv2WeftSzLsn71q19ZK1eutGpra62amhrr0ksvtb71rW9ZmUxmagfuEW7ztCzLOnr0qLVx40YrHo9bra2t1h133GGlUqmpG3SROHDggNXd3W01NDRYsVjMWrZsmfXggw9aExMTUz20ovG3f/u31gUXXGBFIhGrq6vLeuGFF6Z6SL7iIx/5iDVr1iwrEolYc+bMsT7ykY9Yhw4dmuphFY1nn31W+h5u3rzZsiziYnfXXXdZHR0dVjQata6++mrr9ddfn9pBFwCneY6NjVkbNmyw2trarKqqKmv+/PnWZz7zmTzXXoPywGSvMzAwMDAwqGAYP3oDAwMDA4MKhtnoDQwMDAwMKhhmozcwMDAwMKhgmI3ewMDAwMCggmE2egMDAwMDgwqG2egNDAwMDAwqGGajNzAwMDAwqGCYjd7AwMDAwKCCYTZ6AwMDAwODCobZ6A0MDAwMDCoYZqM3MDAwMDCoYPz/haVyo8OYhnMAAAAASUVORK5CYII=", "text/plain": [ - "
" + "
" ] }, - "metadata": { - "needs_background": "light" - }, + "metadata": {}, "output_type": "display_data" }, { "name": "stderr", "output_type": "stream", "text": [ - "100%|██████████| 500000/500000 [04:29<00:00, 1857.67it/s]\n" + "100%|██████████| 500000/500000 [05:13<00:00, 1596.09it/s]\n" ] }, { "data": { - "image/png": "iVBORw0KGgoAAAANSUhEUgAAAbIAAAF0CAYAAABGwry1AAAAOXRFWHRTb2Z0d2FyZQBNYXRwbG90bGliIHZlcnNpb24zLjUuMSwgaHR0cHM6Ly9tYXRwbG90bGliLm9yZy/YYfK9AAAACXBIWXMAAA9hAAAPYQGoP6dpAAEAAElEQVR4nOy9fXwc13Xf/b0z+4bFLgCCBEFSFA2+yJRlU5FpknqJa9GSqYRVn1pxoqp+mvhx0zRukubNjpK4dR1bSaPUL0mbt+dpEufFTeukql07qctEimw5dSRLlBRZkmXSpkiaokiCIEAAu9jFvszO88edO3v3YmZ2ZgmAJr3n89kPsLN37j1zZ+aee875nXOE67r0qU996lOf+nSlknW5GehTn/rUpz716VKoL8j61Kc+9alPVzT1BVmf+tSnPvXpiqa+IOtTn/rUpz5d0dQXZH3qU5/61KcrmvqCrE996lOf+nRFU1+Q9alPfepTn65o6guyPvWpT33q0xVNfUHWpz71qU99uqKpL8j61Kc+9alPVzT1BVmf+tSnK5qEEL8nhDgrhJgXQrwghPi/LjdPfVpdEv1ci33qU5+uZBJCXA+ccF23JoTYC/wNsM113enLzFqfVon6GlmfIkkI8SEhxGXf7Qgh3i2EcIUQE5eblz59e5Hrukdc162pr0AGuOYystSnVaa+IOvTFUtCiNs8QTuyCmMVhBAfFkL8lRBixhOq707YR1YI8R+EEGeEEFUhxJNCiAMrxPKy8CGEuE4I8WdCiNNCiIoQ4ogQ4oNCiPxq8x1FQojfFUJUgcPAF4AXLjNLfVpF6guyPl0p9F+AAeBb2rHbgF8CRlZh/HXAB4HXAV/tsY8/Bt4L/FfgpwEH+N9CiDcvB4PLzYcQ4lrgKeAW4LeBnwGeAD4MfGr12O1Oruv+OFAA3gY87PZ9Jt9RlLrcDPSpT3HIdV0HueBeLjoLbHRd95wQYg9y5x+bhBD7gH8K3O+67se8Y58EXgQ+ghTKl0xCiMeAk67rvnsZ+Pgh5Cbhza7rfs079ntCCAt4lxBijeu6F5eD7xBevwx8d8jP/9513Q/oB7xn5FEhxM8IIb7puu7/Xine+vTtRX2NbBVI+ZmEEK8VQvypEGJOCDElhPhlIelaIcTnPNTVOSHE+4zzX+OZTo56pqBpIcRDur9ICDHgmX2OCCEGtOOjHqLrcSGE3YXPNwshDgshFoUQLwsh3hPR9hohxB8KISaFEDUhxNeEED8cct07hBB/LISY9a79j3TTlBCiKIT4j0KIk15f54UQjwghdmttOnxkQogPAR/1fj7h/eYKIf659/f7Anj+v73fbtWOXS+E2BI1LwCu69Zc1z3XrV0E/QBSEP+e1uci8AngVk/7UTx1ndvV4AMY8v5OGn2cBVpAPWqgS33uXdd9s+u6IuTzgbBxkRv0HZGz0KerivqCbHXpz5Fz/ovAk8AHkOaaR4BXgV8AjgEfE0K8RTtvL3Kn/GfATwH/H3An8JgSCK7rVoH/B/kC/3vt3N8BhoF3ezvWQBJC7AIeBtYDHwL+CGlCChII48BXkGac30aap44BnxBC/ExA9/8dKALv9/5/N9IkqOj/A34M+DTw48DHgCrSjBdGn6Ft3vpZpPbwQ17/rwD/LOCcfwa87LruE9qxrwOfjBhnueiNwDdc1503jj/l/b0JeprbFeHDo8e8v58QQtzkCZ77kPfqN13XXYg5Zq/PfVcSQgx7G5SCECIlhLgXeCvwt0n66dMVTq7r9j8r/EEKBhf4z9oxG7ngtoBf0I6PABXgj7VjAwF93uL1+UPG8V9F7rj/AXL37QI/HYPH/4kUHlu0Y68DmvIx6Wj7B8AZYK1x/FPArOJXu+5PGO0+A1zQvs8Cv92Fv3d7fU1ox37OPKbNwSIwrB0bAxrAh4y2LvBYwvu5xzvv3QnOeRF4NOD4DV5f70kytxHjPKY/O73yoR3/gPc8utrnV1bjuY85xhDwRW9u5oBngHck6aP/ufI/fY1sdekP1D+u1I6eBgTSrKOOzwJHgW3asar6XwiRFkKsRe5gZwHf/ObRh4CvAX8C/C7wJeA3o5jyTI7fA3zWdd1T2rhfB/7aaCuA7wf+0vu6Tn28tsMBPP1/xvf/A6wVQijT1SxwsxBiUxSfCeiTQBYpyBXdhzQ5/ane0JVmqv3LNG4UDQC1gOOL6vekc+s9C+uMdmkgax4X0q8Viw/j+EmkdvOjHm9/CPwbIcS/TnDtPT33cch13XnXdd/quu6I67rDruu+yXXdzyTpo09XPvXBHqtLp4zvc8Ci67oXAo6vVV88n9f7gX+OjI8RWtth/UTXdeueP+UwcnH6567rdkNwjSEXsG8G/HYU+IdG2xHkwvajIf2tN76b160AAmuAeeDnkYL3FSHEM8D/Bj7puu7xLnwHkuu6R4QQh5GmRLVY/jPgK67rHuulz2WgKlK4mpTTfk86t9+N1EZMug0J6NBpK1IoxeEDACHEP0X60l7ruu5p7/BnPKH4H4QQn3LjBR339Nz3qU9xqS/IVpeCfFRhfitdWP0WUoj9RyT8eQ5psvkzgv2c3+P9zQHXASd64DWM1Hh/ihQ+QfS88T3yGl3X/e9CiP+D9MfdBdwP/IIQ4h2u6x7qkc9PAv9JCLEZuXDfAiTRIpabzhIcpLvR+3uG5HP7VcCM//o4cI42EEaRAqrE4UPRjwN/rwkxRX+BNPW+EZlFoxv1+tz3qU+xqC/Irgz6AeBPXNf1UV1CiBwB8VNCiBuR8U5/hHTc/4EQYpfrunMR/U8hd+LXBfy2M6BtCbBd142ziMUi13XPIk2hvyuEWA88C/xbIEqQRWmafwb8OvBOpLbZQIIOLhc9B7xVCDHkdgItbtZ+TzS3roS+d7QTQlwEzkacH4cPReO0tWed0t7f/vrRp28L6vvIrgxyWLpT/Umk49wnIUQaGex6Bol2ezdyMfqNqM49v8VfA/foUHQhxOtoa3d6208D3y+EeIPZlxBiLM4Fae1tIYRpHj3vXUOQCUwnhZobMX/wzFaHgB9EmhX/KsCUFRt+H5eEEHmvz3XGT/8Deb9+VGubRWraT7qu+8pyz20IdeVDa/sN4I1CiNcafbwTCdYwNe8+9emyUH9HdWXQ/wJ+SAgxB7wE3IqEZ5v+iQ8gtbA7XdctAc8LIR4AfkUI8T/c6ADRXwK+F/g/QojfRT4bP4kEjtxotP1FJMT5SSHE73s8jSKBCG/z/o9LReC0EOJ/IE1lZa+PvcD7ok5EItQA/r0Q4s+QWtdfum1Y+CeRCzfAvwvp4+tIQMz+box6AIcRQIFS/i/PdAnwW57Wuw/pt/owEngDgOu6TwohHgIe9DTOY8hwiQngX2jDLOfcLqEEfIA0Tx5EPhO/jXze/pF37A9c1z1Dn/r07UCXGzb5nfChDUNeZxz/Y6Ac0P4x4EXt+wgSLaZMT3+FNPmdxIMrIxe6BjK+R+/LRsYIvQqMdOHzLUhEWQ14GXiP4j2g7XpknNMpZGDsWaSZ61/GuO53e8cnkAleP4I0ac0jBdlzwI+FnWMc/wBwGqm1mvD8DDCDREXmQq45Nvzem2835DPhtdnvff9QwPk5pHA4iwTiPAV8Ty9zG8HjY3SBsMflw2u7Dwm+OevxchT4N0BqpZ/7/qf/ifvpl3Hp01VLQogU0kT5l67rmtpGn/rUp6uE+j6yPl3NdA8S0r4amTv61Kc+XSbqa2R9uupICHEz0q/375AZRMwA7T71qU9XEfU1sj5djfRjwP8LnAfedZl56VOf+rTC1NfI+tSnPvWpT1c09TWyPvWpT33q0xVNfUHWpz71qU99uqKpL8j61Kc+9alPVzRd8Zk9vNIXm5CBwn3qU5/6dKVQETjjrgBQwcvFmunx9Lorq4ZfMXTFCzKkEDOzc/epT33q05VAm5FZd5aNhBC5Devt6rnzoQXhu9E5IcTWK0mYXQ2CrATwyiuvMDQk6zS+ffhdfG7ukx1/AT43Fx4XG9Xm+2/6AJ9+7ldiMxSnveItaGz9t6DvYce7XWdU+25zFXT8+2/6AM0T7VJTUfOrnwPQPHEqNp9RFNU26Dd1HamtW3w+xO4b+OwXfzF236qPXs8z51vxoj8z97z113CffclvH0Rh828+/2HH4vDcjXd9bMVzt/6jxgp7d+IcN+9Lt2dD8R31u359Ou9qXPU86zwEtdXbAMzPz3PttdfCyliSMufOO5x45jUMFZN5j+ZLLba+6VsbkNpcX5CtNg0NDfmCLCXSDA0NdfxVbcIoqk3Kykae20t7xVvQ2PpvQd/Djne7zqj23eYq6HjKyoJI+9/jzFHK8hLah1xTEJ+R/SXsR12Hzoewc7Hm1+yj1/PM+Va8dMytncPtdj9D5t98/sOOxeG5G+/62Irnbv1H3rOQdyfOcfO+dHs2FN9Rv+vXp/OuxjXvXeCcB9zf1aChopVYkF2xdLmTPV7qBxgC3Lm5OVfR28QPuMtB37v955b0FfT9beIH3O/d/nNLjsXlI6htkmtQbZOO240XvZ/v3f5zHdcYxUOc4zp169v8TW+/XPfaHEefy6AxktzbuL+HzX2c9lH9m32a15b0WQubj248x3mGenmWzXPiHos71+acB/Gs1grz97DrnZubU8mmh9wVWhPPH32Nu3hma6LP+aOvWTG+VvJz2RlYrpu2n7cvfVoCqFcBEbe9enDVS9utj7AXIO7iGbSgx1kEdTqw98MdbZIspkHH4vAS1e9yCqckY0eNqy9+ar56uTb9/7jnmxsq/dkK2kiZ/AYJiG7XGCQw9XGC+osSUkFtw577pPc/7rVF/a9fX9B1mHMQR5jra4FJ+3n7iguyc0e3uJUzE4k+545u6QuygAl9C/CXyAzkLnCP8fsfs7Qcxl/1ctN0jcx1e3shwihsd3gp/Yfx123HGrRgJRkz6pxehWm3PkyBHkdY6m27UVwBFLXDjrMYxqGohTlIQJg8BvVhaopx/g9bbOPwbPLWax9JKY6A1b9HCRSzP1OAXir/cdeDsGd/NTSyM0c3u+UzWxJ9zhzdfEUKshVNUSWEOAh8N7IA4meA73Nd97Pa73+MrGD8z7XTaq4s4R53jCFgbm5uju8fkZU6Hmk9BMAB614eaT3EAete/7g6BnBwx/0ANI+f7DhHkTqmH9ePHdxxP83jJ5ccj0MHd9zPoWMf7RgviMeVIvM61ZhqThRv5ryYfKnjqW0THdeT2jYByLlVvyXhI8kcqLnslcKuTe877Lm4a98DANgzJf85MnkP+h7UV1DbXniM4sGcqwPWvbHvTxjP3fiL+i2obdz7bj6f5ruZ5Jkwn1t1bti9S3KdQXP+6dlPMDw8DDDsuu58bEZjkFoTXzlyTU9gj2uvf3VF+AojIcQIst5eyvv8J9d1fz9JHysK9nBd9xCy3Dwy3CuQaq7rnltJPvrUpz716TuNWri0SKaoJG2/TFQC3uK6bkUIMQi8KIT4jOu603E7WLWkwUIIl2CN7B5k5dmLwBeADyS6AE0j01FB3bQJpXkAS3az+vlBO8TV0piS7Najdvy6lpVkvDgU1ne3XXjQ/dF5TkLmWFG78bB5TW2bWKKZh+3Ew56tsGcm7HuQxSDounRtN+w+6+cH9RelvcQhnRelZQOxLRLL8c4c3HE/zmgRe0Yi1oPmJO6YYe+7aaUxn6VuVhj9nqi5CqSJjfzNid+CFdTIvnVkU08a2WuuP7MifMUhIcQo8Cywx3XdC7FPXC0bJsE+sn8K/GNgF1KgvYQsu25H9JNF2oDV5xoS+MhMh3McFFVcm3qUjT+JbyuOI9l1u/vTos5NSnH6MB3dQSjAsPZRfXU7v5e5DOo76T0NOxbmJ4ziMcxfpre5462/uqR9FI9R4wXxHNfno/8Nat+Nt6g5DQMeRVHc+6nfh6g2Uc+DOV63PsKOrYaP7MSRje6FV69J9DlxZGNivuiChfDa/ARwEhmb9iSwz/h9BPgqUAF+IvE1L/ckRlxs4AUabbZ57e6MaPMhlgJE3Ldt/cnQhzDKkR6HkrxMYS9A0AsUdE63lyiMwgABcRGJScbr5pQ3/w9ro39PIlyS8h0kVOP0FXZP9AWxW99xNyVh/JhzFRSKENTXgb0fviQBF8VLtw1g0HlRgk/1ZyIxo/qKQhZGoUq73eM41xP3d/361F/1/2qgFl8+ssE9/+qmRJ+Xj2zoRZAdBH4F+L4QheU+oIbEQtwA/B7SArc+oK9x4O+A8UTXvNyTGHGxXQWZ124KeE/E77E0Mv1BihJsQe3Dvpt9msfjjBGHv27Urb2+KKgFzeS72/XHvb5um4SkgmilNhpRFIQsu9R+LoWiFvG4wiZu/902NvpGqNtYUePH2bAEbRzCeA3iu5sQjHN/et1URQl6XVCr46uhkX3j6+Pu2dMbE32+8fVxxdc1xjqbjTl2kCB7Evht7buFTMv1iyF9/C7wA0mu+bL6yALabAZOISfiL2L2G+gjS0LdfEiXiorrdfxuvpOw44rCfFBB56p2K+H76+Y7CvNX9DJGL7xFofZUG52i2t+17wHcp1+I5MW8bkVhfjbz2hRS0hwnzDcWdsw8bvKo/x7nmQvrS/c7RfWpv2fd0JvqvLv2PcDDT31wyThB/q1u16ff127PUxgiWqcoH/tqoBaPfH2cYkIfWanU4vrXTQb99GHXdT8UY+yOdV4IkUGaC3/A7cRH/Akw4rru24UQ40DFdd2SEGIYqZG903XdF+LyvaKoRSFEAdihHdoqhLgJmPE+vwR8GjgHbAc+AhwD/nol+epTn/rUp6udHFychChErf1mOvNA1npkYx1gA6Z0nASu9/5/DfB7XiUTAfxWEiEGrHhA9H4C/FnIQOgBpMA6j0QtnkTaTpPZRkMConWVPw5FmbjimtHCqJtjPMysEofPJG2isjLo53Yzs8XhTb+OuKCUbn0loZUyUQaZaLs9E6Z/NKyt6VMJGnM5TJemuVAftxfzpDrX/P1SnuOo+x/0jB7Y++Gu/so4mUf0/8Oy5sR9V6P6Xg3T4vMvrXdPvLIh0ef5l9ZfEl8YpkVkdRIXuNVo9xHgyWW75uWexNX+6IIs7kMV96WL49DWX6SoNlHHTUEZZmvvxsel0EoLiiTtwwTsclIcn0eS9lH9x90MRG009PZBuSbDfElx+Av63q29zm9U+6Q8BPUbtnkw24fNS7f/9fZR4wb9b36C5iQIxPIdJMgyQJOlfrM/AT63bNe83JO42h910/Rci0l2e3HahT3kYYvtci+6QWNEjXkp48fRMOLyFWfh67ZohfUVdk7YfellTsLCB8LmJ85zF7TYRS2wQX1Hbbx0QEOUhtWLoDXHCqKw84LQlkG8RAEyou5j2D2PI7CCjptoX5PvMNRqt34VrQZq8bmX1rsvv7Ih0ee5tiA7ggyHSgSFNwWZd+xJz1yovlvIGpKBYI+ernm5J3G1P2GmxSQLgv5/0INpvhC9vPhBlHSnHtVHEqHai4Dqdv1xoNNBx5IsNnF4jXPucgn9bn2HHQsTWuYirj+TUf0GmS6T8tarsNd5DxsnzvcoYZ5k42n2Y2ppUZuebhuXqGvQj6kxTcSwPs5qCLJnXxp3v/HKxkSfZ18aT8wXUABu8j4u8LPe/1u83+9Dxo/9P8DrgP+MhN8nciNF8rDck7janyBB1gsMOuicOFpBt+PmYhPUvxlDE0TdjnfbxXa7tm7UyyIZ9btaZJLScgses9+ghdA8bp4XNTdB9zVsIY/DX9zf3yaWBhfr/4dVZ9CvJ4nWZbbvJgi6XVOYgNGpm/AM2yiFUVRsmjlO3GfX1JBXM47s6a+Nu0dObUz0efprPQmyUCyE1uZfA99CgkaeBG5ezmu+agpr9qlPfepTn9rkIHAIzXEbek5Scl33MYg+0XXd3wZ+O3HnMWnV4shWilTMxH7e3lHVVezZ5ceXhFFU/FjcHG5xcgqq33vNKWjmAuw17ipJ7jmVUy4qt2BY30H/J4m7MftPMsfdji/HXHU7R90vYEnWc0Vh+RMvhR89E/+hYx/tyAsI0XGFZu5E8xw9N6lqF5UnUlFYLFeS+VV9BGX570ZmjsikeVO75cmMah/V91vFPTzG52AF48ge/9pGCgnjyMqlFre9/uyK8LWitNxq7Wp/CEAtJvWTKOrF1LUc58btP475MK5/optpMez3buYik59ubcPO7/Z7HLNvt/Pitk1iGruUY914uZRnezmpl/6TmrjDTJxxnrtux+LwGXY8LPVXVHaYoO+rgVp8/Gsb3edPXZPo8/jX/FyLPYE9LtfnqtHIgrLfK+plR272E2cnF6fvJFnhdQrKum1eY7cM7VHjduMj7i74UrKDLFdmkW5Z5VUbnbrtys12YdnS9d8ulf9ux/XvvdbG65aJPy4v+vEgHpLMSZz7l6SfsH7NvqOuSdewu2Wq0Z+JIM0cYH5+fsUze3z5xU09aWRvfsPly37fM11uSbpcu4+4cWTdtJqgdlGO46Q7PkVJNLgozSCpI13tcLtpbt346XXXH3VuFGAi6veg37rBu+Nqjd2u1dQaop6jJH1HadJhz2DQNZk5/sIobtC267p+Fv5LvZaoMcL6DtPsosBUcY+rfsw8iXF5C0Kd6v8f2PthX6NbDY3sSy9e4z7zrWsTfb704jUrxtdKfq4qjcysEL0cdCk5/IJ4WQ7tKC5vvWifQXnvkvTbLS9lkusP8qcl1VTiULedejf+TDJzMYb5H6PGOWDdi9izC4CHn/pgIr9sGI9x5jtI8whrm+T5jctvUPsg36LZPo5PPM77otNyWR+Cns/VyLX4hRev7Ukju+MNr6wIXytJfdRin/rUpz5dheS6gpabDIXoJmz/bUOXWyVcLjVaz+xhUq+msNV2mutmqiiHc1IelUkjCT+X4jSPMq+E9R90fhKAQzc+dArLJhLVTxwTY1h/QWa/SzXvRo3ZLR7qUgER3caPQ0H1+fR+ejXJxqGw+DqTPzXOgb0fdu946692mFS7mVK7PTOrEUf28Auvcf/u5NZEn4dfeM0VaVq87Aws103TA6KXUwDFRQuGUdSi1o26+VuSLkhJ5iWJ0IorlPT23YRyUl7j+MTi9BP0f5ycgnGOh/m3TIoKRA471/RbRbWNs9DGoeV6RoL6jOKv26ag1+QCSdqF8Wk+h2HP5WoIskPPb3X/9sT2RJ9Dz2/toxYvB+lxZF/0yt10i/XohXr1nyRBskXVYwrzkQRdq+mnCkMzBvXd7Tp6paAYoOVGpSU9V1EQOrMbX0H+lCD/oHlfgMB4piS86jFdcf2Yet2uoGdLxVnp4yieLyXOMur3sGfRpG7vcpivMk4/3WLtot6Vbj61qD5Ww0d26PmtDCb0kS2UWhy88cSK8LWidLkl6XLtPkyNLGgHqn8P27UF7VaXQ8OLi6rqxndQ25XcGUedeymmpV4prnbULT9hnP6C2kdpOSYP5vGwvuOY1uJcS9TvSU3LveQbDWtrHovqJ06/QW2D+u1FI+7WR1gbXfuK856tBmrx889vcx87cV2iz+ef39Y3LV6WC+ghIDpqAYlLSf0s3c5Pck7Yy9btJe2V17h9J+m3Vx66/R7HHBSnbVR+vySLbdCxqO9BfccJP9D7SXpvui3WcfpJMvfmceV/Snp/w5Ish/ETxmPUu9jttzibpyBaDdPiXzy/3X30xGsTff7i+e1XpCDroxb71Kc+9ekqJMe1cNxkpkXHvTJdTVeNj2xubo77dv8yQGgGjKS+rSh/iZ6LUJ2XJJPGcvrvkvQXxWfczCRJ2ix3poewTA3LOZcmmXFfUdcX5DeJ608Ky7KhYqSicg2G+Yni+GjDnnmzjzjjmG2SjGnOYVhWDLMf5TeM4+sKm7u4/tCwdaFbthDT17gamT0+/dXXMli0E527UHL4/u/6xorwtZJ01QgyPWlw1EMa5WBOuhjGBQZ0CxKOO9alCsVu19lr4HUvdClzEpXsOQ7FDaBOusBFUdD1hm2GzOsLu286gKMb37pwMIFAqu1d+x7AffqFjvPibEiCjkfxEtTGHLObYICl4CizfRB4Kupeiz27/Os3k3QH8aDPlz6muekJmp/VEGQPffV68gkFWaXkcO93HQE4CrSA33Fd93eWk78Voctt21wue3BUHJmiOPb9uH62uJTEIR/Ej6KVTkocxks3ilMhN4mvLo5PIqz/OD7PJCmH9H6C+k76rASBAuKCMC61InPSexsEzND76QaICOOjGy+9+qzDeAnyq6m/Uc9uGNglqIZbHH7N/lYD7PFnz93g/sXLuxJ9/uy5G65IH9llZ2C5bppZIVpR3Ict6AWIapdU2MVpG8c5nXTRDDp3uYR0HL6Wc6y4AIRuwi6s717GDhuj25hJABZR/HUrZhl2LO7YSd+LsOzwSRb9sP7jADmixoniSwdsmAJOCbCkCNeg/hX1Bdnyfvpgjz71qU99ugqphUWLZGCPFlemq+mq9pGZPodugahxgoWjgo27UVxASFyfTVLfXhx/hk5J/G5J+IhL3YKWexmv1znT+VD+FHumFAoCMfsIO27y0qs/Mu6zEXX9SX2HSYLHo0A6QYCM5fLVhgEzus2LDqwJm5Nefa137XuA//E3P7PiPrL/8ve7evKR/dAbX1gRvlaSrhqN7HNznwysR5YEZRf2cOv/x0HJhf1uHgvrI2rRM3kJ+96t76A2vSy2vQqvOPcljB+FZuvGa9xrTMpDUoSe+czEWfBMUAO0wR/6d338qA1br/Md1U7fJJrj6Pci7rj6e5jk3kUJ8aDn1uQvaIOpnrFuY4ahOM3xdDIBNStFDhZOQo3MuUI1sstu21wue3AcsEcvlNTJvhKU1C8WB9Rifg/z7yQFR8ThQ28X57e4/pu4YyQ5L65PNEl7c251/0uQzysIrBA0bhxfYDcy730331DQ70nuexjfSX1z3UAl3e5f0vqAUe9SFJ+KViMg+g+ffaP7Z9/ck+jzh8++8Yr0kV01psWoemSXAq/vRfOK22a5YPMmjDsOL900ibhzFmaSids+iscwCoKnm+ZfE9YOwbWsgnjrxl8S/sM02rA+kpj+4tz3uObL5TRTxwmtCHoWTc0sidk6jltAafP6nEWFMASNq1sEgsIp4oaEHNj2U/zNid+CFTQt/v6zb+rJtPgvdz+zInytKF1uSbpcu4+wXItxd99hO+kkaLU444Sdn2Q31+tYl9Jf0LlRvMdF7iXlJQ56rxsvvVDc61THgkrnXCofql9FUamrern/cVF+cbPzR1G39zMIfXgpfHfrJ8k96fbcK4rSrlcDtfj7z77J/a/f3Jfo8/vPvumKzH5/1fjI+tSnPvWpT21qAU7CQpmt9r/73CtII7uqTIsm2CPIdBFl0tCPdTNDmWNAcKaBOKaaXjNVhKG+gtrF4aWbGVRRHMBLWJ9xrrUX82SvCDrzuN53khImYdk4FOllUvRxgsqnRKH8TAq7VjNLRxxTaFzUXdQ7lDRjS5zx9XG6XUvU72Y/ZtugZ9ykqPl++KkPhvJpXttbxT08xudgBU2L/++zexkoJNNVquUmP7b78IrwtaJ0uVXC5VKj9ez3pjofRMpEshoZM8LoUs0/cZ3mYaaQOKa/pPwnNTslvc64Y0XxEHcOg45HtVE8BfWv8xq33If+e1BGirDsE2G8X0pG/6jv3XjX+Td/i3pu9XOVSVU/bh6Lep7DfjPbBQVDm/3E+b/bvV0N0+JvP3Oz+4mj353o89vP3NwHe1wO6gb2iNqBBWkHvQJDdEqyk+ul76CdXty8e7049S91LuLuoKPahsX1hJ3XK5Dmrn0PAPi76zDtsxsgwbQC6GQCDnrVdoP46ZXCnhPFU9zzk96LqOczTPMWe3YBLMlzaJ4blFfSJL1NmEZmatPmWOZ1xLHqrIZG9pvP3NKTRvZTb/rKivC1knRVCTJlWlwOYaTTcpmt4vKW1BS4HEmJu42R9LdeSEfhRc15NwEYhTgLMglGmQ/D+lK86jFtZpyXIrUImgtwt+szf09q/jT77vZ8dusriJcgMhPnRlFY5WpzzCCEZhyEZ9T9g/AkCWHXp/hVcxVlUo4afzWSBv/G07f1JMh+ds/jK8LXStJVJcjCNLLlXGzj+hG6/Z60nwPWvbT27+bRL7x/SUBs3MW5G3XTLqJ+Syps4rQN6ltfJHXNJmoRVsJGtTUXTzWG3rYXH546X18cdYEXJNCCri3oeoKEQ7dM63GeuUv1S8XxeUY902bfUZpdkqw6pkYWFqoQZ/MU5bPU5zrI3xl2/auhkX3s6Tf3JMh+bs+XV4SvlaRkYd996lOf+tSnPn2b0VUJv9d3WZdiwgvaSYXtFuNofXFMLlH9PPqF9wOdu98k/q8oE9zBHfeH7kKDfARh/KrzwtoF7XrNlFOpbRMd2lEY/+Z1BFFQe6eQ7jhHjafmIapvtcu/844H/fuh2rX278YpN+B4u73SmpvHT/qamMrRaPJmamOmthPln0lC+jzqz3PUcx2mregaSBBqNyidWNgzovOj7knQuUF8qPFBzlfY3JpzZ96HJBqrPmaYBSFMe/vc3CeVaXHFqOUKWknh9wnbf7vQVWVaDIPf90LmgxfUV1wTXhKfTTd+ejFJKup1PoIEoGlCW85xTdOi2Ue3vqPmKshsqaDq+nFdeKe2TVDfMgrIzUTQAmu2V6QEmW7mumvfA9gzpdCktKltEzijxUDwThD1YrY12yj+kvjWovgxKez9ieuj6uarDBvD7C/MzwgEXn+UeVbf9OgmzG4hGwese/n07CdW3Ef2a4dvJ5fQtLhYbvKLe78EV1hhzatSI4Nki2fQwqd/D+tL342G9RPFS7cXWH+pdL7C+gpb4LvNRTffSdCuOq4PrtuCaKItu/kp4iwsUQJfUWv/bv9/e6YEmlZm0gHrXizvXivNVQcLAJRuHCfrCbvmY8/6c3Zwx/1LfCfu0y/444Vds34sSLDrbcOuU19oo7T1IG3CfBeSUpxzwmIuwzQyXVuDpRqsTubmIawPdZ137XtgiVXC7E+dr8bTBV+U9qjeX/37W8U9XefnUqnlWrTchGVc2u2vqIDoq1aQ6RS2y1TUq6aiL/CX+uIH8aIv0GHAjrBzo46F8Rt2Dc3jJ0MX2zABGFd4BiH4Dlj3hm4GxJ5dgQJe8WmOYYIs1EJkjxYBL3BY29EHgRd0jYxTM74ZUQfe5E9XcAppMqdmwNOoYCmgQ79GtdCGZbM3rz1s0dbnU6e41gJ9Hs3xw4Rn0G9BbYJ4MzWxoGfF1I6Cngn1u3nfzXOCyJwbM5hZn5cg60zYc26aprtZSVaSHAQOyUyFSdt/u9CKmhaFEG8B7gfeBGwEvs913c9qvwvgw8C/BEaAvwN+zHXdbyYYYwiYe9vWn+SR47+5fMxrlMR002v/cfsI09jimtHi9Bv0fTl4D0LZhY0ZdJ3qPFPYKNOguVM/YMmYIyUsW/t3Y5cb1MZyZA4dBvB/V2PpcWTqe1DdsfrBvQBkpxYBqI3lcLIW2dkGmVMzHe0Vf8pHpi+aQbFOOs86Bd13Na9BC3/Qoh/3OY2a/yAt+FKg8TpSNOw5Drv+Xt6/KM272zsQ9Yx2E+A6rQb8/sNPvq0n0+Iv3fw3K8LXStJKoxYHga8CPxHy+88DPwX8K+BmYAH4ayFEboX56lOf+tSnPl0ltKKmRdd1DwGHAKTy1SZPG/sZ4Fdc1/2cd+xdwCRwD/BnScb69HO/koi3MM0m6Peo3Vuc3WO33WISbS/IVxLVRxwyzSFRFOarCmpn8mWazsx+uu2w1TGl7ahzlYajzH+WBroobc4z8HS7j4tvKLDmxTKO5yOzHnu2w2Sna0IHrHup3nMz2UKayt4NANz6zo9j33Mzdq3l9weQn2xSfH4SAGe0yCPH2hqe6tOMXdOvxbxGcy4Vj2Gaj35ukK8n6fMRZEoL6svUJoOezzAzcRK+wtqFmUTDeI7iLez5C3pmU9smlowRx3ITdS3LTQ7JTYXOyrCy4nQ5fWRbgQ3A36gDruvOCSGeBG4lRJAJIbJAVjtU7DZQkN+j28sUJaC6CcGwc8PGCus7zssb9VJ060dRkuBps88wc0oc003Y71EOdGgDNazHnvVNccpsCDJRnFpsis9PMnvfLQDkJ+tYTahszvtCp0n7+bhr3wN+33fe8SCPth7izjselH4vPCDHgE1lPIWTtXEykKq2+VKBz+7TL4Saw9QxHWLfbcHVn4ughdOcp6gsE1HPX1hKpW6CqRuf3fxEYT7PoPOjnqE47cLCAYL4DHqn1Sahm+AMOl///e3D7wq8huWkSwR7XFG0avB7IYSL5iMTQtyG9Iltcl33rNbuvwOu67r3hfTzIeCXzOP7eTtfbLvfeqJuNm+dkmRoj+tvSsLfpZ4fd4cY158Ql79efYq670iPxzp07KO+H0sHWNQP7iVVdWgO2JS2pAEQDjgZGD7RIH90Cuj0y9y17wGcgmyr/Fz1g3vJHDrsj3nxDQWcrKBeADcFa47KPazyjSnhpHhR/rU4WR9MBKeuKQdBzKMWziQ+TyX01XyY54T1FaYNRoEvTD5NPoKEoXmsm2A0+Qm7rqA50NsFZYAx+Qm7DpMPs/1qZPZ4/xPfS857nuPSYrnBg7f+1YrwtZJ0JQqyII3sdFJBlkRoqTaQzGSot4tadIJ4iktJzgl6GcN4CaM4AjxsEdJ5CFu89T5MIIEucBQpAaYDMpTQUfTqnVKoWHUYPdIgVXWWBDObpAc+z0+0H7faiMCqQysD2VmXNS+WAXwBq8yIQTkY9fEU6hEIRS0GzVnUIhl1P8OSSofFcoU9K/r3sI2M/ltcQWL+FvacBQnKqPZBfUeNF/c9DxLucUo/KVoNsMcvPnGQbEJBVis3+LVbD60IXytJl1OQbQNeBt7ouu5zWrsvAc+5rvvTMfsNDIiGYNjvciXXTSrILrX/OC9Ukl1jUh6CFtPl6DtMGwhqD3SYEO2ZEqUbxyk+P8nMbRsZfVzuh5SvrLw5S3WdYM3Rht9Pqupglxu+wBF7dvnCUCWDBajsHCNz6DCpbRPM7t1Ac0D6GipjAicPmTlYc7SBk5WmmIHPPtkxJ0F+R13QBsHy9XnR+9BNhaZQCcreHmez1S1HYhyNI+j3KAEUN2zAPK4LG7VpgWAtVbXvFrBvXouiMI037rsexo95fDUE2f2P392TIPvobZ9fEb5Wki6nQfQEcA64Ux3wbsDNwBOXi6k+9alPfboaSKWoSvq5EmlFBZkQoiCEuEkIcZN3aKv3fYsrVcH/CHxACPGPhRC7gE8CZ4DPJh0ryHlq7ozi7PjDjh2w2sGV3TSdpDu5IFI7727aj+lQjtqNB11j1PGonXIc/4BOYaCGR1oP0Tx+MtCvcnDH/f55Smuzyw0efuqDPPzUB30/lDNa5MlPvhdntIgzWvTAGZCbbjJwwSVVdUhVHT92DKB+cK8fC6b6OWDd62dsyB+dIrVtgsrOMVppwdDJGkMnaxTOugy+KrWx7NQiX/7Mz/Hlz/xcRyYPndS1HTr2UVLbJnwwSP3g3sC8jnrAtzkX5vw+0npoCYAp7nOpz7l6ztRch2n5+jhBoAkINqPqvOvvUNR7FASUOHTso0vMo6YZWbWPo41FjakjP83EB0HXEdSH/u4uh4+8T+G00gHR+4EvBvz0J67rvlsLiP5RZED0l4Efd133GwnGGALmTB9ZkABIamrrpb2iILNIWC67JOMlEZJRpo5ex9dNROb/cRaPOGU/TD+IDu6obxn1BVV9yyjWY88CnbkO6wf3kj865ZsHFakchso0pfgwa0zp13b73R/xzYcAxecnKd047psSFakxFdjD7EcXxtCZXimqFIuiMLBD1PMQZp6O+5x1E4px++52TL/msHRTUbwEnRNU8uVSzIPdSifF6Vc3oa8G2ONn/u4f92Ra/I/f/RcrwtdK0lWVNFivRxbnpU3i60li/15uMv0mUb6BbrzE5TeOQz6qPzNDRjfe9d+VUNIzdYAUaE4hTWU8A0g4PUgYvhIkwBJ/mQ6qCEIQQtvXpPvimgO2LxDrQzYAmXnH953pgvv2uz/Clz7/8z6QQ5Eep6ZfR20sR3ZqscMvZyYYvvOOB+X1D9i+QA7b8SfRqsMojnBKKuBMPuO0faT10JLqAhAtnIL84WZduCT+QDMtXNhcx90k6vMAwMRG/ubEb8EKCrKf+vLbexJkv/nmz0E/afC3F0U9eEle8jgmEFPr0sfvtvDHHTsoIFY30/V6HSZfcRauKM1Okb6AdNtp61qM2LMLPM2ptX83mVMzVMZy1Ids7JrcfFmPPYvYs4uHtcUKYPTxszijRWpjOfJHpwK1QCUk9HyJHVrTqRnYMkpl5xipquMLycrOMV+ze+TYQ34/mcee9c1R+iJ8+90fWSJk7JkSmadfQG0hTTCHIqVtZggGdejCt9sCGzXvioJyh6qkx9367UXLj+JRrzKg2kVpQ0FuBNOUqvgJah/2LEJwgHlYH2Hfzbaffu5XGB7+rSV9Lie1sGgl9B5p7ftJg/vUpz71qU+XlxxX4CQEbyRt/+1CV5VpMageWZj5IY4tvxdbeBD1ooUl4Tvq/Evxh8TpI8znZfo9wlIrBdXpUua/ys4xAJyshZMVNAcEa14sd6SRMhMFB/GuU9yg19b+3ViPPetrg6UbxwGZ5V4PylYB1Ep7MvkK0iL0+dDHFHt2BfKi5jGIgvjXA8f138J8a3r/pgkt6v5fyvsRdm5YnFiSPtRvcfoIG1tdd1CFgqAxks7DasDv3/O339+TafE/v+XTK8LXStJVpZGFpaIKejnDTAW9+ryihM2lCsMkwtc8Fueauh2P4r9bbJCOzLvzjgeXLPh6m9rOMfIzJeljOjVDZVw+nlYTakOC7LzbkeUe2vFeZnkXsWcXd+17IFCA6PzZMyUOWPf6gqmD720TNB97liYw4C1w9rYJHM/HBe3s944X36byPqoFUfkKg+6THtgNS0uJdBMecTZmUX0BSzLt6+3CkIn6eLrw7FYIVG8bdD2wdEMSNq7Oq/l8h113NxN/WLXoMP9jGG/mJi5ok/fp2U/E6rNP8eiqEmRxcil2Eyrd2naz0UcV5+tG3Xa4QS9hUr+Y7vtIEhwetTjox4NeZvCEiFZwMgjUkTl0mEOth3jzOz5GbWScVFVaC6prLSwHCqdrtPbvxtECohUIwp4p0dT4VUIhbFOha4S6BqOEqkI36jtzk5ys5Wtkpk/H95159cmax0+2/XKG/0Wfy6Dx1L0yBV8YRS28URu5MD9R0PNjnm8mW46ybOgCL+hZiatNhZ0X9ByaMP0woR8k4OJsAMPej6B3LGqDsJzk9pBr0e3nWrw8lMS0uJwUtmB3A0AkMV3G0Q7jmkiTjt2NogAG5kKsZ83QAR0mFF4BNFJVh8k35bC8VNwDF1zS5Rb505WOnIoq16LiJQgpCZ0ISqV96fXGdE1ILXhqYdbRkDo5o0Xcp1/wEYoqW4iJiNS/60JcZRQJCiEw5zWoT9WPPvdh90L/ro6Zz2s3U595b7vB0MM2OOb45jlhfcc1kZvX2q1tnPZxNLwwPsJ4Wg3T4r/40j8hk9C0WC83+MTt/31F+FpJuqoEmQ6/D6KohzdMMIX1sxxCMq6pUD+uC4Okvotejyd5kc1jd97xoL/IB/Wlf1ew9AtvSIMFwlOxiqdb2DWX4vOTHXFkZgyb3k+QryloJ6z8H0ozVH0qvv2qzx45o0Uqm/MMfPZJPzExtNGPlZ1j5I9OLUkaXL7vFoovL/j96AmPlZnyS5//+Y7rMfM1BglbhaA0U151EwRBz3m3wqdB/cQ5bo6zWhTEU5BgjhLgEO6eSMKDec5qCLJ//tg/IVPIJDq3Xq7zR/uvPEF2VZkW+9SnPvWpT5L6ZVyuIIpKGqwozOQSZwe5HGa5lTZzJqW4fIQ5x3WkXFipe0W6dqE0B1hqZoM2AvDc3hyFsy656bbX60uf//kOVKPiRR8jyP9lxhMFBUPrSXz1cxW/uqam+7Sc0aLPs0pkbH5XvjdlMgXpN1PmVn2O9SKcJrry4I77O4K7zfujU5z7q19HnGS+cTKy6G2jsmrENakrMt/ZsCwbvWpNYTxEabDKDBqkwUbxr76vRmaPH/riO3vSyP7LWz+1InytJF1Vgsw0LSZ5gVbCTLgc/a7kuPqLlSRrue7LCOvPfJlV1nrlE9MXIQWCsB57lvkfvJXqOsHQyXatWuUbM9M/hY0Z5sgHAgWqEiomKd+aLjxNAadg+dnZhg/Xt8sN31xYGU9RLwpyF10/2wgQmMVdRxDqC7Zqo0IB9GOKJzWn0D2DStDc9LIx0ylJdnvznkWFKsThI64JNKh9XD+fol6EZFD71TAt/t9f+L97EmT/7Y7/tiJ8rSRdVYKsWxmXXqgX7SXseBwHcxxhG1dLTHJM9RdHIw3qSwdNmDkF1c51/gdvZehPZWEDXVtSyXuzU4vMXV8gN92USX4DfGGVnWM+5D0M7q1rVabvTEfX6dcVFSf0SEsiKaEtsMr33UJ+st4hWOpbRmkO2GSnFpm8VfrIiq84VMZtiqcaPt96rJweo6TGV5qZ0lRVhhLTjxc01+Y1JanRFfW8KKEeVn4mrE/9mKK4wsfcgIRlNolDURsgvU3cGLawfuK+76uhkX0nCbKrykdmPuBh4Ii4mloSQRj2AurH44wRZp4LCy1IeiyMwnaq3RYbtQg/bCwoegLf1NGptklSE3xqnnRU4OjjSwOiVfyZDq5QvARdp1600txV1w/u9QUKyBRSqaqDFZLCSMWj2Z6GVd6cZXjPLgp//pUOHlNVh9pIGicrcLJ5hMfm/ITtZ+DXBa/Oly6og7SAKArTgvRrUMfCTGX6vQ4zz3WLEetGvZjmw9ooAd98+oVI06IO+jHjB5OOqfOutzMBRGHpvMx3+HNzn1Qa2YpR30d2BVFY9ntYPrNeHKRgUuqlnzCNLEowR+0Kk5iVgtrqvjL1/137HqC0fZCRw+f8dsq3Yy7S6qVXhTABHylYG0mTP12Rx2ZKfs7DMB+R6bsCqT1U77mZ4vOTgFzM6gf3kjl0mOo9NwNts6U6L8yHp1/n3PUFho+UqWzOY9dasn3VoTKewa65lK61yZ+Xx0cOn+tARkI7a4gi/V4pWL7iFdpoRtNHFIW+66Z5m+16McPHsTDEoaTmzbhWg7gmxF54udSK0qthWvwnj/4QmcGEGtlCnf9+539ZEb5Wkq4qjaxPfepTn/okyUXQIlnuRDdh+28XumoE2efmPrnk2HKBL5RZIqxPs9849v8oHsJ2zvrfsHbm90vZKetZ3KN8HkC7HMlokZHD53wQxMBnn8QeLUYCBJSGUd8yilNI0xywsWstX1Oa3buBetFicW2avT/86wydrAFge2Y/p5BG33cqTSm/bcLXmBQtrk2R3zaBkxV+2zx0aFwgzVYq64fiFaBy4zjDR2S+xzy7KG0f9Psub7IonGkxcqzhm0uVtqmjM5sDtp/Rvnn8ZIc2Wdo+SL6Qxh4t+pqY4skEdehkpuhSpB8LMz8HaWXd7ndcSmLOO2Dd6wNa4vq+lgN4EXTdUUASCEZMPtJ6KPQ+LIcVJyn1UvH5Sq0QfdUIMog2MajjajGI43w2f4+isIfW9DV1W2zC+E/iYF8u86cyf4X5IUyfjtizi8rmPOV9Rda+JP1Qrf27md2R45mnOlF4OimTm+0h+SzPrKb8T/WiRflaaBRd7JqgNiIh7o3NWYaPlKmNpKmMbyAzLx1Ts9ttBqYtnOw42dmGL0ys4ycZPlKmvmXUr2WmYPK3vvPjstaYZ1oUe3bRfPoFxKg09c3u3eDz0igUyI3tZW5rO2tCc0AweqRBfcimPmST0sylPijDE8xZIMigLzTfG7SFp2tk+wgCptgzJQ4Zz6Bpeg0TDqltE75ZM4l/N+h4mPk7qI36XyezBlnUmEmEa5jADvpNHyNq4xrV/7cDfSf5yK4qQRbnZQvKH6d/D7N5h/UdhnbTXwQTfRWX77i/x23TDcUW9ILfeceDPBrw0sPS+l7NAZvTB2DkaxIUAbI22NpyUQI2Agod6rkp9Xiwu/Y9wMU3FABoFKCVgtaggytSNAryZSucruE+/QLZwm5qI2nK10jB4qZgcY1gzYudKa0q99xM/nSF8uasj56seSmoRjw/nCJ7poTjFfKEol8DrTAvhdXkvjTNvEvuvNzBNoqCNS8ukj/aBquoOTpg3duheeqprHRkZfXGmynOtKtYKwGc8eZXLTFmba2g2DhTg4/ypZm/6/c5TIs2n4WgPvQxgoSimo9eNm7qusOKXwZRnI1iks2gOY9mPsco+v6bPhC7ba90iRrZU0KIfmHNy0m9aiRhmkcUBQmwKKe5aRpMymfcFyyonbnYxeHb3CGbi5RajOzRIlM35UivW6AxOMjwiXYwsx74G2Qa1RdkxcPFNxT8pMGpqosrLIqnUjQHpACDdmFNgEbB4uLrPD3Hdhn6hlz261tG/YrS9aJF/jQSqOGBPXTTY6rq+CAQRXNbbYSbY+CC7PvidTZ2AxoFl1bWxXLkiz/2zKIPSskcP7lE2KjckgApJpjdu4HMzjFSR6d8UEf+dMUHnDS9OVXX8OgX3s9d+x4ITEp9174HeORY50JuQtPjWhy6aVDdypgEaSRh71RUHGIUBWlNQRaJoOsKGyMIGWxWiTbnwiQzwD2qffPEqchr/DagK6qw5lWNWoxLcZBGSZFViqJytvXCk85LWBxNnJiZbjvpKP6C6mmJPdJf1EoLmjnBwAVp5is+P+lrI3rgcdA1qGNmUHGq6mCXG1Q258nONnzT4sBnn6S1fzeV8Qz1osX8Nslf/iyMP1Hy/W2KFtemyE03yR+d8n14igY++6Qf7AwweWuRZg6cPOTbAEzK10BmTmp9dg3WHJWmyfzRKepbRv2g76DsIcrnV98ySm0kTW3EYuhkzRe0Khej8jcqXvRkx2ElV4IoSvsykY9JNlVR70scARpHMMQRCKap0EwaHfX+hgnbMOqWwSaM56C+D1j30nQbKx5H9n89/C9IJ0QtNhbq/OVdn1gRvlaSrkqNrE996lOfvtPpOwnscdVoZJea2WO5ABKXSt1S/cTRtsxzgr6H7XAVJdXIAD9AWGlQQEelYjNzQtD5ym+kZ7lXfeoVmxWp36ZvyJGdl8/y8JEytbGcnylEkSoFo2tq9SGbhY0WroBMCRxvA1va6oIL+bOCdAVqI/J4bhoW18CGw4sSfejVQ2vt301zwPYDowc++6Ts3wviVloXQH6yzvxEluxsi+Lzk75vLju16KfigqXlZ9QcBcU0BlWKDrMAhD0XcbUj8zez/zjnJxlzOd/NuH0lnYuwVG5hY61GHNnBv/qXPWlkh77391eEr5WkKxOiEpN0c8O3A8VBM5lmNkXqpVc2e30BCfJL6Ofo383fzN/Vx0QY6m1184pqL/bswhkt+pk37JmSb0rzofkGbyBNbqltE74QE3t2cejYR7Eee5bKzjG/LErm1Az1g3uxyw0OHfsoh4591DcPWo89S3beZfhI2YfGO1mL0vZBRh8/6x9XwsUuN1hcm2JxbYr5CYv5nQ6Va1xSiy6lbfLTyrg4a5tUNrlUNkC6JD9W02XLp89QG0mTnVr0eZ++Ief3nZ1tMP+DtzL/g7f6x+yay/wWi/ktFhd35qgXhR+orUjPJ3nAuhf36Rc6ArTDikPqQky/J2HPR5hQU/c9KsOI6dc0j+vfo4RcHMGn+jD5NZ9bWFqgtNu71q2NPmdBY5rnmsmpzT4uBymNLOnnSqSrRiPTfWRhu7m4NuxLpaAxl2NXGQSYCHNodxszLj9B+ed0UotrkO8LOnMtBs19atuED23PT9Z9AIf79AuU77sFALvmkj9d6ai/pZMChij4farqMD8hUZNrXix3ZKSvjeVYXNu2qE/thnRJkLsAro2fWqqyERrDDrlzUnMb9PL9phZl8t8Lb9nIur892w4RGLLJT9b9XIsqvsyuudRGLBY2CjJzbZ5VeILKBgIyj6OKoVL+JlhamFSvYg0sST6sKErr0n0+isISQZv96Dkiw9r34oO91Hek2/scZEkIs0rE0QbDrjHOta2GRnbgf7+nJ43skX/4n1eEr5Wkq0aQ6dnvITpO61KpmxM5SriE9RM1Rrf2YYuHmUbHLDsRNm6339VYulDRy5VkDh3u0BbCSpP4wcyeqbAjP6NnLgQonHGway2yU4t++irAL7Spkvgqqq61GJhukZ+sU96cJV2WyEQF6KjsHOPiTtmHkwWrDsMnHBoFi8ag3JEKB2rDkKpCdt6lmZPHMyVZ5LMybpNecClvlMfTC5CuuOQn22hNkACTdLnFxetsFtfLd614QjB8orFkbpVJNgj9ppMphKKSIwcFUXcz9ekU9ryZtFybNVgaKA/h5WOihEkcfswSQGEUZqI1i5+a54Tx0Rdky0tXlSDr5iNbDT+YvmNNcg50RxX2wkvU7jOKF3Ns87ipGZkaQ1BJEf2lr+wcI3PosI86BInas2dKTB7YxMJGsLy1fuACFE81mNuaproeahuksBh5PoWTlehBuw6zO+WzPHBOMDjpUhkTDJ9w/JyNOupRZfaoFy0fYQn45sfW/t3ynPEM524DtyDbWHMpRBNaORd7wcJNyTFz5wXphbampYLJ53/wVkrXCuojLtkLcswtnz7DzG0bqQ3J74Uz7fGVVmYiPJWZ3CwpE1QCJqgOm37fzIXbzCUK4QHESRd+1VeQfzRIowuCvHcbJ2hT2euzHya41fMQFrBtonK7jbMaqMW3/e/3kBrMJjq3uVDjb65AQdZHLfapT33q01VIfdTiFURJKkRfqmYTt+/l0gSD+ja1nTian95P0iDPoGtRpj+73OgoBKlMhc0BmaYJpI9IgRqCKh6XvTRTgJ8K6vxegbOuQepsxusDUguQnYeZNzaxh2V6KWcmS/GYzfAJh6k32jSK8lm2aoLBM7IWmA6oKN0oU1aVN2dpeVu42oiguh4GzsuYMD2/YW0sR2U8xdQtDqkRLwjbdkmnHCqlLOlcE5VjtXWsQH4SNny5JPM3elqgIr1C9PxEFicrqGwA0ZQaJ0itM3PocEe2fX2+oBNoE+W/1NuouY9rNta/m2Rm04g6P4qCTJlRloyk48Ut9BlW+Tqq4kU3XuJU014N0+L+//VjPWlkj/2j/3dF+FpJumo0srcPvys0IDrJQxj0sicVQmb7uCZDk7egdFa67yDOS2/2GZaiK4y/IL9JaUua9EKK3LRN1gN7KLOXPQPNnWPMb/HSSJ11fT8W0K4GffwktRvHyU03/cBnxnJM77KwKyDOZmiOyIVfXLRJTUN1nTQn1oflYytaYDWhvMkmMwuiKaXKmm+0qKy3cLKC0o3jTL9eCtXMPEy/3qa6yWm33T5DY6rIyDfSPpQepM9PJhceZ/hrKVJVOebcdS5cENjrXNxmjsao5HH0JKQXXJxC2g8Ch7bAzk4t+kI/f3AvF96QplF0yVwUPsBECTrXqLMFbdCM6lPdSyXM9BpsYajDoEKeJhhHf/7DntugvuNujBR1M/tFvQvmeUHmzrip2MLaRZk3u20Egsy05qaj6S71kS43fSdpZFeNIAvKfm9SmN38UoRWUgrzOQVR2G67mxbW7XrMF1TX1IIWLx32Xdo+SGU9ZEqCwum2bwfaKLrFtSmEl/mpMSgkdH7/bu7a9wCPeppGUALhxbUpmoUW2SmL+loHsp5fqmGTKbmkqgKr6dLKyJfN8Tab1fXyb0omxsCuuYwca0htarfA2ST9VtWmRaZQ5x9uPcrhyS0ATB9dx/AJQXbW8ZPn6vN2174HKD7fzte4/gvSRzX9ntuway71ohSS654pURvL+fFzt9/9EQCyo0Xf56UAKfnJOvmpFPkpGDq52JF9RM23+/QLHVWZQfoVv2Rotb4geuzZrgAjPdO+DvrR70UYYCIM3ac/x3H9ZyZ6MM7mMSq9mmofdf1JtVHoTKYcRmFC3SRTI9Y0shWjviC7wsnUKroBGIIW7zimwTjmDnNBiHqh9MXz4ac+eEmmG/M81X9YH+YOVE/oesC614+JagwKhk+45Kab/gIN+EluJQKxgC2tf6x7RkLDH/3C+7n97o/w5nd8DIDZ79tE+YYGGx+2aaXbL8/QNywsB6ob27y1UlAZFzgZaKUF2YvyuJPxkglnoJVyaXjrQuGsRXWdzdx1Llv3vkK1KRGKFxfy1GopHj52PdlnBgHY8cWSz39QoUoV2+U/Q55mUDzVYOb6NI6nTM5dXyA33eTCm4qsewYN4p8j78HjFVXGM2RnWzQKFplTMzyqaW9sm6D59AuBZjcOHebWd37cL1pa3zIKW0ZpakU6dd7V/0DoYhy2oUptm5A5HFsPdSzmrsdb0CZQ9ddNO4sK5wi6BpPMvsOSDwedk2SsoJjOsGrtQcAYhdhdDZBZELmuwE0omJK2/3ahqzoguk996lOf+nT103cU2AOSmw7jamNBZo2o8S7XLq3b+EHggPJ9t3DxernnGXwV1n/hjJ9xwwyoVdnbFVw5c2qmAy6uSpOc+MdZ3LEa+edzFM7KZ7C8UWA3wBVQH5EBygD1jQ2suRSu7WLVBM6gtFum5m2aG+qk8w0aiynchuQx92qaVBkWx13cjYvkBqR6uDCdp/CNNIWzrh9blp1tYJcbOIW0nwIL8P9XcV36vNz6zo9TG7Gofe8cO9ZKpMbXzmygOZsFRyCagvwZyUt+0qWVEjzzez/r+wdrI2nypytL0naZGrsyLapSNCpWr7I5D7RDBUCGC1iaZhYEs1f31wyq1kMn1PhxgRdxtH1TcwryIQV9DxtbkW49SBLuEtRf2DzFGV9vf8C6d0nsnjqm97caYI9bP/eTPYE9nnj7b60IXytJV5Ugu2/3LwPdfUhxhEicFzQJ9YLoioN+Ms+DeAjKbuhH1Vf1npu5uNMmrVnH1j9V4uGnPsjtd3+E7NSif/zhpz7om0VNQIEiVSaldK1NfQjWfs3xS6m8uj+FvSjIzMq8h/Nb5Tn5XTPMnR0iPZ2ilXJJbZMox8WLOYbGFijkapydHMGtScknGoLR520acr0n7QEIi6ckKlHPLK9Mguo6lJCYeZ1NKwVbDpV8c5qaF7FnFye+r0jjmjrXbJTB3KXFLJblsmagwskz63DnvWwiixapsiBVlUINaFe49vxpemYOtRmwNXOkyqpf2Zyn+PxkR/VtaGfWj8pjqciMMVMC0xSqCjnZDZChKAhpqbeJMreHtQ8SqmEoxzABE8a/2XeQ6V8/FiScwt7nOO/tW8U9Kx5HdvNnf6onQfbkPb+5InytJF01gixJGZc4/qrVoKCX4VJ2l2H9hwnloIXO5OfWd36cuW0WqnDspr9b7NBgZt8tfWcqFZTym+nlRjqKR3qCzMkKMvMO+aNTTB7YBMDCJhiYxM96MXO9FAatlITeN/JQurFOpiA1rPpCBjvjoB7hVEaCQxpn86z5msW6Zzqh8Eog3X73R9o5Ib1rAQmLn77Jq4F2TYX65ACv+XyL/NGpjlRU9aKFk4HKJiQoxaPMuiq21aJycYDUrPSRWTVBK+OSPyOwvKQf40+U/HRb9S2jPtjjS5//+Y5sJ35hzVMzlG4c94O4VXVrpe3qyZYVqcVZzXf+dMUXjvr90e9N+b5beOJT7wO8Qp6ehtcNSKGom6ZmCqGwtGXd+tXTn8U5P6ivpO9+EqRwNzpg3cunZz+x4hrZvv/50z0Jsqe+7z+tCF8rSVcN2CMMtRjkeA5yVHd7iZKYUMLON3+LcjCHUZIs20HXGYUMU33pVNyzi3qxSHNAfleL56PeNa15sR0DBsVQzQ7k4mXGV114y0bK18j/8+dkOiiVLT4/JYVKMyfRioujguFnMyyu9dLurHNoZgWiYUEL3HkpEDZ8tcXI4TMd8HR1vXfte4C8VjVaCTHrsWdp/cht5CY9Z/dkgWufWOzItA+QmXeoFy0aRWjZYJfbbubGYAqRb2BVbJwBqWU6a1pkzqYRbjuP48U3FLCulxsAq+H6gklpe80BG9tDO+rUSguGj7RzR1Z2jpFHCqbqjTeTnW349+jgjvtJbZvwj5W2D1JECvP6zr3gFfOsZi2KXl9PfOp9/oKdAQ55mnvQhkfs2RUKolJjh5GyCIRtqMx3UbcgRL2L3SD6Jio3CcV558I2pnGQnCtBfdTiVUTmwt1t0Y9CMgb12e14L2ipKAoSdN18DL36CNV8jT6NX8VY7yO1bYJDXVLy6IuL0jAAPz/ixddBSspCsvMSDQmewPCCqkdO15ifyFJ8Rf5eP6/g6oLq2jQL10ghOP6E1DhK2wepbxmVJjMDrm4j51DB452sRaNgkTu4l8KrDZ75PRkQ7f8+WmTu+oKfa9FqujQHIFUBWvihAFYTmgs5atfa5DYtYNtSkFVKWexqumNOZm6AVtYld94iVRHUixL6aE3citWUGmiqmsYpyPlSGps/N56Ay3j8lbYPUl1rURmX7fIj435eSaVV1X/kNuauL5DeLAWeSqo8dLLmmyrvvONByrdJuOjwkbL00Y0WaW3p9L8pCvOxmumxggQNLN1YqnPqB/d2xPSB1L6C2gdpakG86RW7H2k95Lft9m6EaXBKuAblLtXb6tUqVJsoOP9yUh+1uIokhPiQEMI1PkcuN1996lOf+tSnK4Muu49MCPEh4AeAt2mHm67rXoh5flfUYhgtN7IwyuQYNE63/pPY/PX2SZMWh/GjdrlmZnUdGBA1dzrvZiCu2LOLc28u0rJh7UuNjnPrQ7afQBik1lEby/m+qvI1UsNJLcpnt3C6RnPAxsnKfVlYORTVl1NI+5n1B6ZlNvvsbMMvwQIwfVOR6hhUb1iEixmGvin7djIwMO1SGxFY9Tay0q5DcwBKW1tsuv486/NSzfz7lyaw521cG1p5z7boCMRQg9QrOUQTPy4uP+VSGxJk512shku9KMccObbo+8wU4hGkWXR+IutrcSrzvpoHu9bqmJOpm3IMnm3RSgsftZk/XfEBLk5W+GMOXHBwsqLjPuj3L8znpYK5zbgzvWaaifAzARSmFhSGwDQpypoSBS6J6yYI+r2bnznMtbAaqMXd/+O92Al9ZM5CjWd/4NdXhK+VpG8X02LTdd1zl9pJUhPapZj9gnxVSXxhcXgMeiGi2vQqdMNecF0A+P+H1L7S+wnqr75llEe/8H5foM1cX6Blw/gzi35ZFvCE0KHDuEgfDcjAUgXOmN2RpukFIbspwfDxFnZZ5k8cfVwWDXNGi7758EvGgmjPlDi/b5MvgDLzDqmqI31/O8f8itLzW8HaWcJq2ORetSi+4gFJChajj5/1zXGNglz40+WWzJ84bjE1X+jwNdhVQX19E5GXgsatyFABZ0uV1kKadEm+hqokjOUI1hytUXxZCninkKZ04zh2rcXAZ5+k5GUIKb68wJoXJZrRrrX8OVLCuDaW8xGh8xNZ6kWojFtk5mH065K30vZBmgOC0rWCTAnSnpm3NmL5AB57JjgTiBJQAIfU5kZDeKpnAuiKgFT3J4h0s2AUgjHq/VA+uSDBo/Ma9h4EbQx1X6Be1TtoHTLNk28fflcoH8tFLpBUT7lSoX/fLoLsOiHEGWAReAJ4v+u6p4IaCiGygL7NKEJ4rsU4KMAkwkdREkh8LztJk5L60rrtPsPs/uZ46mUNElxmSqco7SyjFYkEqUUVTsvf1WJbH7L9dFaZUzMdfR/ccT+lG8dpFPDTX41+XUL3564vMHyk7BfobA4IGbPl+ZZ0lFtr/24KZxwfBDF1U46BCylaExupjQhanoBzBlwa5/MMfstm3fMNP1NHutzizN2bKF/rkr2oF8u0/LIs6ZTDhkEp8M8PFam74NouNKXQc22XbLFOsy4HU3XKMrOCkWNSY7LLDb84Z36yTqNgURux4OBevxCnU0j7JXDA8rWvoqe9ZacWfcHcSgmaeWhuqGM5Garr5NiFVxuATfEV2WbkmBSCsztyPqgE2n4d3S+kL9h6uqyg6uLdQFTq/uggEJPM9rqfSn8+g8Yzc4zq/Zi+N72dfm636zHPC/vt4I77+dzcJ1c+RRUCQUKwR8L2y0FCiGuB/wKsB5rAL7uum2jB+3YwLR4ECsBRYCPwS8A1wBtc1y0FtP+Q16aDTNNiXLMdXD74vaI4iMiw84JezDCgimm2iQKFAEvg3NB9Y2C+tPqOVtfylIZ2+90f8UEdT3zqfUt22SAXuOo9N/vw88Kff0X24QFQFtemqIwJSt8l0X/2hTSbH22SPzq1hPfm8ZMdwBVV2fnizhyVDdAoeNWaZ6TpsHhaChaVLb+RFyzcvsDE2DTHn72W0Rfl8aGTNc7dnKOyqcWOXac5sF66eRue6vdiaROVphQ6p0vDNB0pdJqOTe2IXNAGz0AzB3YDsrPt9zJVdSlttsjOSVOmEmSNvGBgukVzQDDyx0/4wdym+REkYKS0JY2TgdxFl8LpdixbbSxH+Zo0rg35SanVqfAIVe26+PKCz09p+yCFP/+KHzAOUuO6844HfROoOq5i38wYt7BnJY4g6Hae+T7p/5ubsiCzPHQvRBp2PChrfhB/q1GP7MaHfg47n9C0WKnx/L0fWxG+wkgIsREYd133OSHEBuAZ4LWu6y50OdWny66Rua57SPv6vBDiSeBbwD8BPhFwyoPAr2vfi8Bps9FyC6ekgq8bgrDbrjNIY1LnR2lQQf2F9W+SbkK5844HccoNP9A2yiQTNaa+UIg9u3yU48Ed90uTYaGddf7g4bbJ6s47HvRzCIo9u3wUHoDjaQepqkNzwKYxKChPtEgPyMUzdTEj+/SCi/0MGV5f+aNTvmkQ4NzNOarrXQa3z+HU5MIvLgwy6AUwK7MhwPQu2Dw6x6b8PN9c26DqhQJYzSy5aWilLM7ND/Go2AnAZLlIpZqh1RJYtick054vqyWolrOQlypmddwif6ZdaLO8ydPY1ghaGVmxOlOG0rWSl+IrLs0BwdDJGuX7bvFh/B0xYx7y0cnKuDr36RckKtBDPjqjRVJVh5FjDrM7cr6mBlJgzl1fkLkuNT9aZt7hkdZD3PrOj/OElnH/Uc+cm6o6fpxatrC7wy8K7RyEur9Vp7DnP8q8HrRh0zdOURvEILOj7tMLEoj6udAWfHqxWZ2fy0EtVyCuAPi967pngbPe/+eEEBeAUSC2ILvsqEWTXNedBb4B7Aj5vea67rz6AEu0tj71qU99+k4n1+3tk5SEEG8RQvylEOKMhzq/J6DNTwghTgohFoUQTwoh9oX09SbAdl33lSQ8XHaNzCQhRAHYjrSZrhjFAVKEaT+9kgmgCOIl6twgP1RS1FWUabF5/KSvvTTHclTGMxSBFEsd7FHxNUF+jKCxxOgu7HIDWzMhKr/bo1o/9kyJJkszOSg+xrdNUC9sonlB+pSu/esSdoA5s3n8JPWde8lCh+mtlc6ysNml0bRpnpOR37m6RAIOH1nAffoFP0NGZtaiWk/z9ZlxqNp+lv/cdBMna1F4tcXit4ZpnpaIlLVAYSRNeZPtA0yqYzKOrJUGy4FUpb0Lrg/D2QkLZ7BFqixXFeFIM6eTg/oasDyQZyMvvFI2Wda8WPa1pny54V+75WlDA0Dt4F7yXhZ9L8kIYnSX9IdlJOqylfFZoTZs+zXfWimvpltJgkre/I6Pkam1OurL7f3hXyePly3FM3OC1MRUthJ1H6BdnsaMxeoGmgp6d4OeuzAy+w4sb3Os7c9yRotLrAxhFgr36RfacxIy5iOth3jr0rX+SqZB4KvAHwKfMX8UQtyHtKL9K+BJ4GeAvxZC7HRd97zWbhT4JPAvkzJw2QWZEOJjwF8izYmbgA8DDvCppH3FAU0sJ6owKXUTQqawiuM7CGoTZUaJ8o+1PJAFQH37IJl5Z4lp0eQtzNRj8mj6IB5pPeSbmJpLeljaTxjIoH5wL62qw/gznVk4Dh37qDRdaomK7dGij4hUfJS2b2D08bMsjG+iulggf0EKldEjUlpM31Tkmace8gOk02Wbma+vw8m3cNMtnIxc4CvjKda8WKY2lmP4SNlfpFv7d/Plz/wcINN9Aaz/ra8w++5baaUEjQLU1kieXRuqG1oyHVjeAS9riJN1aRZc7AWLgrZPbQ7A4KTL0J8+gQvkaQfaHtxxvw+FV5Q5dJj6/t2+cAMpyAuvNrhwY5raqEtzQ709wKINDUH2gs2At9zMb7FY2JhDOJC7aDF8xMu1uWcX+UmZs1L5y4AOn5kusJQ/LUwgmFk6gnxgOlJRbcDikJ6VRJ0fliBYIV3DTIvqmnTfmBk8HvQOrAbY4xIDootCdJxbc123FnyOewg4BGCco+i9wO+7rvtHXpt/BdwN/DDwa96xLPBZ4Ndc1308EdN8e4A9/gx4C3LzOgV8Gfi3ruu+HPP8JXFkSQVanPZxKAlQQx9XUTd/WpjgWy7+FDIQpC/Errm+byoog0ESMl9mPdGtnulA+SV0Xs24IzPllFNI+6AFkDkL1Xkqu7vqUy3u+kJZ2TlGaUua2ghkZ+Ux4UC9KDUUuwaWt74Pn5AFO1UcmaL1T5U6EhArH9Xs3g1tcIYH1bcaLuVNFq0U1Na5NIc8GKZwIdOChRR2TZAqC5+X3LTU1pys/B8gf16eZ9dcis9PtgW259vU6dCxj/r5E/UEvwd33M/MbRvJTTc5vztNQ4IcaQ20cAoOIiX5yU5JgT14VgJCqutsrKbrJ0C2HnvW3zTo+SvVbx2bJK2NXW74wjYIuAR0COQ4FoluoBGdlMXAzEYSBfNXz1/94F7/WTMRtmrOw8ZdDbDH6z71Cz2BPb7+zv8Q9NOHXdf9UIyxXeD7XFdCyIUQGaAC/IA65h3/E2DEdd23Cyn9/htwNM4YQXTZNTLXdf/pcvVlPjDmAxoGjlguzatbP+YL1q29KcBMs2QSk2ScdgB4gkwh1lzihxro45kvtjIZdixW2yY6Frgwfs0YJh0KLpfXYocWoJsTVWFDdb7SPGc92HorLaiMyYS+zTwsrvM2dgKc0QbULXKvpvyEv5XxFE5WMHDBZfhI2Ye3l7YPStDJNWnsWhrhSKd/puQyvcvCybi4XqXqwUKNlivIZ+pUZorgIRjdhiA1nZZCbKHNS7okWLgGsjOQmcM3Z9aLFplSi+LzkzhGbkZV5FSBDw5YMgTC8YSCWmwrO8f8+Lv8NZvIHJPCcWGjRXXMopVxce22gM/OtqiM2+QnZQiDigEsekLMeuxZHO2ezu7dQObgXqmxlttACD2Tf3Fmwr+fQQHXrlFoVN8MRQE4zHdfF1qKVBoz0/yt5kdtfnzyNgipbROkjk51AFVUO11LUxQWwrKSdIlgj8104g8CtbEYtA6Js5o0jk8C13v/fzdwHxLsd4937Idc132BmHTZNbJLpbDMHkm1laTn9NJ/0PlxocNB4/aaKT+M9ze/42PMT0jRMHRSxmjlj04ljpnT+9fRX/pGo3zfLRRfXugwfUUtSkqzMv2MStNoDtg++lGvKWYuINV7biZ/uuLHaNWLFhdf79IaaWBlHNyWfJFTGYdGOQMVm/Xbp1mblwCqo6fHKTw9wNhzizQHbD8IuTKe4eL1Fq6ARtGltU5KGyvVIpVxaDlC1isDBscXqJSzWJNZCt8SVNsASuqjDlbNwik0sartsjStXAtr0cJeFLgpL0N/WeDaUDgtfVcKtahrR4oe/cL7fXOenilfacSVzXmq62w/ObRrS5NnqgxOHtKeziBcWHO0Qf7olFYRvK15qphAFfow4+VurK6TpWxAVjHIT7kd5XOgswxQkMVEPSPKjKiXjQnyy5oVv9VvQEcfulldCf6o42YJJOjcOChtWIWYqPF0flejjMtr/+sv9qSRfeOf/VrPfAVoZJuAV4HbXNd9Qmv3EeB213VvTjpGEF12jaxPfepTn/q0/CRRiEl9ZMvOxgUk5mHcOD4OXHI2J0VXjUYWVI8sqmBkkC07ipbDjxYEyDC1ozhaVhjfca5HjRe0q/zWfZuorZXPw8YvS5OVXnQw7FpMHsL4Ajhzt6w9VhuBdS84fqVk1Sd0Bq9CG614cMf9HVpGbSSNkxXkJ+sdZjWlZeiVlaGNnpufyDI/IV/w+miLzKYFBLA4lZevHIAAq2aRnhfUR1us2SYTIi7WU1TLWQa/miM7J3MvgjT3NQrSrzZ4ywWcljQXXpwsYi3YpOcs8t5r28rAwAWX0cfPMrt3A/MTsm3l9YvctPU0Gcuh3MhQasjd9KlX1kkT57oqzaZFoyQHFY7AWrAZOC9IVdrZ/22tTI2er1LN8137HvD9iSr7/+IaqTFZTXn/K2OC1CJ+OjBVxVsvO6PnplSkNN3aSDs3ZTMPoolf0060YORlxw+UDsoGH6SpB/maouqamefq/+u5IHV/rd5GFTlVtfcUqfYKUAT4bcx0VmFIytXItXjdn/4idj6X6Fynssg3f/DXQCaoaAG/47ru7yQYu0Mj8449CTzluu5Pet8t4BTw267r/loiBsPGvVoEWS9Jg+NSmDkvif8pjvNZr8obZm7shXdFYeerl/aV79tEw3NjjBxzefKT7+0qxIIc5LoQUgl/M4cOU73nZqbeKM1lzUGXif9V800vZr9638q8o4pLttJSCNWGBHZdJg/OTTd9Mx/QEfCrL4rl+27h4mst3+fVHIRGsUXmooVwvPIsyMDjNUdlHshGwWLmBjlmY7QJjiB3TkLT1z8r0Y3ZqUUqm/PMT9iky50CLrUoM2nowrZ047ifJuvUAbnYtLZVmFg/zab8PC0E31WUcf7/7cQe5ucGSGUdCgM1sinJ/MTQDM+e2Uz2y0XGnlv001U1BwTr/vasvwjr86HSdKmFef4Hb6U2JKgPS0Gj0n+JVlvwWHXIzqnnQhZWVWnBlOBSgBNntMiFNxXJzrZ8XupFQabUXmeysy3fBOlkrY5QCEsLgjeLswaFU4QJJ/19hXDghR4aoHx8ajyddIBH5tBh38SpNgpKqJkCOOz9WY3Cmjv+y/t7EmTHfujBRHx5IVMq7vfvkSjFLwIzruue8uD3fwK8B3gKCb//J8D1ruuavrOe6DvWtBhHyzDh8BCcLLeXMXUortIyrMeeDYy5igOr7zZe2O+q/wPWvYy8PN6xwARpb4pn/XydR/W7P0/HIb9tgtn7bmFho+WneioeF9RG0h0OfpMvFbuVnW3IIpKnK36mCYDytZCfhNQizG1NY9flou3asiZX8flJHn7qgx21x6prvczwniKRmYPCGZfKOBRPNXxh2ByQeR9rI+MMHynTzEkJXy2lqK1xsetQeNX102tlpyTSc/Bsq0ND7BCkWvojfce/6cteBo+vD3B+7FpOrYPGiMMrrx0BYLxQYvb0MBy3uTicZ3SH7DtnN0jZLepFuLAr56MYraYUlKVrbT/Zse0BLVJMUBpJU/R4aaWgtNXFasi8kWnPvT+/w5X5IQVkZixfwNllmaTYarhcfEOBdX8rgSIX3rKRxm0bqQ0JH9kJMr1WKyVTaKnUYE7W8rOyQFtrrI2NkVHPz9NL/fxB70Y3JKKZnkyRv9HyrskZLfp+RIBD3gbL3EQe3HE/jgffV/dPtRN7dgUCstRveqaQ+fmVz/7kkjwJcI9qzR6k4FKkMi/9CfBu13X/XAgxBjwAbACeA753uYQYfIdpZEGmPfU/JNN4goREUvCFLigUzdy2kaE/fSJSe+oFxAJLBaJ+XIexg9zV6jt3RWF9QKcA019oXfsob5bmssLpmg+9Dto86HOiHOjOaJHK5ryfLqo5IKiMC0RTBgqnPa1BtKQGMfoHj1M/uJeLO6WAW3O0wcz1aVwLH3ig0kHZtZZfPkaRPVPynfgKtFC+RtAYlJD8/KQsdwKdAdY6/LwynvFzQwY9L7ppTdcMLu7McfG7pbRNDzSpTw0gGoI12y/6wJOthRnmGgMcm13L/FfX+atQZhbSC/LalIlv6GSN2khabgrGM35IQOlaGycD1Q0uufOCrLe+LmyC5oAyJwoys/L4lk+fob5l1Ae66AIb8DcOakNQG0lTXWez9rmSb87MHDpMatuE/1yYfah51589/ZkwQ0FMrUuBg8wwC6U1mSARXZNTwjY7tdjxDqjjmUOHAzU/fWOqvwOqSrnJ92qYFrd98t/0pJEdf9evrghfK0lXtSC7VGShTkFIqaRjdYsD031A5kvcbYwkfqyg3/b+8K8zdLLmj6v7qcIy35t1yuyZEpWdY2SnFpm8VS5KI8dk5nhlWqvsHAMIREMqnm6/+yMdvwftugFmfuQ25q5zsauC3DQsbG4/y2tf6MyRCPh5CS/synWUZUmXpT9QJ7WQtvbvZuqmnN+3M1bHupgmVbYYPuaSqrodfSs/iSK1kOlIwajrUovk+X1FLM9SWtoCrYxLK+OSuWaB4bwn4GyH1685x8V6nqeObCVzXgrP1ILUynLTsPa5dtVsgJHD5/x7BFJ4ljdnqQ0JLEf6LgEag3JDIBzIlGDwrIdGnKwzP5Hl8B++1xcYqh+gIy5MkUourI6reajsHJNB2p6Q+NLnf56DO+6X2vfRqSXPXZivTDc7qu86ylUfU5kjzT5CofkeSjEItWjWWDP7DqujdsBanaTB2/6kR0H2/1x5guzbLtdin/rUpz71aRnIy+yR5EMb5fiUEOIlIcRPXM5LiEtXtUbWCy03OjGszzDTnAI0jBw+FxtNmcREagJXQO5S53/wVpo54e/gTRSX3lY5yFWWCJA78tkdcvc3/d11ckUZP9k4UWDdV6V2ZNdaviYQZZZJbZvwd+v6cQUAUHFiCn2YnZUaROFV+SwvrhHkLro08lLLUKVJ7FqLxbUpmrm2lqaAGM0B2499gnb2icrmPBe+y6Z6jQRYDK5boHKugF22GDwj/HIrh//wvb4mWbpxnIHPPtnBe2v/bh/YYt4n5cNTWuib3/Exis9P8sr3SYRnYwhq6xyyUzapBekTBGn+27TnDGtzFS4uDnDqBdl+/EnXB8SoYGdFSstRc6hMmfMTWRp54YN9rLoEe2TK0neoa3DKrKhnEDHRoYrMdFWAX/TUyVodQdUDn32yw7QXhLiETuuIru2aGV+CTIuwFLCl7pPexiQzQ39Q26A2YRrZaoA9tv7Rv8VKqJG1Kouc+Of/fkX4WknqC7IeabnMlkE+JhOxZaKf9JcvqU9O70+R2LOL0vZBRg63wzoqO8d8h7y+qNS3jDK7I0dqsV3iBGB2u02qCtX1kNs9Q8aWwmPhy2MMnnUpvUZQ/JbrgwP0cjEmdF43A+lUP7h3ibApb87SzAlSi64voGoeAs9qSiGgNpkjx2SbkWNthJ/yiTmFNLWRNHNbvSBkF675izOcuXsTjQJ+oHD9mgZULdLzNqMvuVgNOQ8qGDh/dIqZ2zb69b6UX0q/Rv3aTNOyuv7SjeNc+C7JS+sNZZo1G3c6S6os0ZX+HFxbx846OA2L7Enpfxz5psw6onxNsDRNlM5H/eBeLrwhTWoRal50Q6os5zC1CMVXHB8EpPxbisL8UibIQn+mFcBpdkeOkWOLzE9Ivtf97dkOs6fyqSkBH7T5UxS2cQzzq4Vt+pSQVLB8M6uIiV42AU/mRjEoKBvoC7JlpqtGkL1t60/yyPHfBFY+q8el9BEEvDBJ7SiD8g4uB5nZMSo7x6iMp3xAAMjd8ey7b6UyJgEA44+cASQ6zWpK6HvhTHuBq4ynqBcFi+tg8ZoGwqu9VXgxg5uS4IgNXy51+BRMyLJaOMy4otL2QZ741Ps6fBWA75MDWSBTIRLTFZf5rQInI1MrKU2tlWoXo1SUn6xT3pzFarjYNbcDHAFw/o1yIVA5CHPTUvvDkn0XT0kQS6oq63m5djtPozpv8KyErSuUnl7w0/SzqPtRH7Ipb5K85C66VNdqmTG8vhe2NcmtrbJ4dpC1X7VY/wV5j/SMEur5MnNM6oCE0o3jVNfZ/jWCzOno5GDwVfldVY5WmUEg2MKg/LxBMHbdP1rZOcbcVu9Z8+5HKy18ATy7d4MPkjG1LV3z0WHx+rxGCTsTSKRrdurZU3FiQQIsCNCkeNHnRH+2zfd3NcAeE3/4gZ4E2ckf/pUV4Wsl6aoRZJcC9lhO7SpJP+aOLQz1GAZzjzIlBvGip/+BdoXl+pBNZt7xzUUgd6Tl+27hwndZ2FVY8w252MzcYJEqy526CsAFKWyqay1KEy5uxsWqeWpQS2A1YOMTEtquL3AKjWguqiq5bm1I9jF8ouGPo8xRgG/iUsJXATvqRYvqmDSP2V45FpBaVm2kMwnw4KTUqpoD8tw1L5YBmLu+wOjjZ5eg58SeXUzfVGR+KwxMQVo2J1NqMb9F8l1fA401Um0a2zJD6StjFF9x/b6DzKqqbzUfOrS7NpYjf3TKR22q+Zm8o4HbEgy+nGbzI6WOmDGFtjSFjl7UUr93lfUyNML2Muo1B2SJmXQZCq82/DADXbgECYwgjUfFW+naYf3gXhkOsc72kZ/6fdU1PxMFGGaqN3nQyYTfm5qwHtwM7ZAAsyioubnUEZNBc6Hm+7IIsk/8u94E2b/45RXhayXpqokje/vwu0gJ+SKrhyYs5iSusAnzY0W9wEnGUv2YJr+wcuwm6byZgivoHOWvKP/greSmm36sj9WEmevTjB6hA7V46zs/jl2F/HmY3iUXz0axxYavOHzp8z/fseMssovmQIHctACEn2S2fA2sf9bxUWhqcVICQi/hoha60rVCComK3GTVh2zf59PMCV9gFf78K3KuBsZwspYvjAqvNii8CotrU1TGhF9jq7rexU27ZC5a5DwLW266yeyONMVXHBoFyzdnqWBwy9ul61kxMqUW9qLF2HOLfjhB8eUFil69hlfvLNIYlbzPlvPY3hz75tn9uzt8OGrzcte+Bzruu2+K8/xZlc15srMNf24X/17yWnzF8QWvIr1sivkM6Frgre/8uAxm9syH5WvkO1RbAwOvSlSmEmLQiTjU47r090H/XyV21jXplFcTbfo9t9GyZQgASB9m5tBhMkjBYcaSBVVfVmOYmpriwxSGQYJWvYdqI6HGMufKPC8oO45J9kyJQ8toTUlCvRTKvFL1mj5qsU996lOfrkZye/xI6qMWV5PCTIum2a4XShKb1YtZMQohFfZb1PiKwoKWU9smmDywSaZiWnR9oEZtxGLkj58IrDv25nd8jOxsgzPfLXf/Q9+SpriRw+eWZPq+sCvnx40ps2C64pKdbZGdbYQGuKoaaNV1tgRqpJBZ3rxtVqqCV0pEmuf0Wld2ueFrmsoHtbg2hdVwmX69RWO4xZqXZEeLo9Lvk5ltp19SJVGKrzgdoAwd1WaCGxSqMCiP48WdOSoboDYq5zY9Z1F4VfrNVB7D/GSTL33+5wMD04PusQkgUJrJ3PUFCqdrVMYz1EYs1hz1QBIawCQsE42eQqyyOe8HdKsq0+p+OBnY+FdnlmSFV1UEFDmF9JJ0Y+qaVB00laklf7rC+X1FWhlP85ts34vUoutrlrpJUdeQ9FprSssPCjzWSfFh+g7Vb1HADKAjCBqkWV4HQUFwfGDY/V0NsMeW3/tgT6bFUz/6wIrwtZJ01ZgWTeqWOBfCzYHqtyCBEbbARGXNCOMvTFCavASNbfIQxqtu/rn97o9Q2gKZeUhVBJUxufBbTfliPuIVCVR0cMf9FKHDf6ALLuVPU7TuhUWsx56l8u5b/WDeVkowdZPN4Fmb8VMTftvb7/4Ida/0R3Wd5MO1pYDJTcPCNfhJdrOzLd+MGHRfD+64nwyAZ5ocPrLopVGC3HmLues8ZOGioJl3cTKCvLZ4KsShiejT51wtkgd33M/A8ZM0ATHa9jNVNuexay0JGFnr+qVWnJxLyxa4GVj3gnRA2eWGzH6xf/eStEtBz4T+vXn8JCnkPA79qfR1jXh8v/qPJfxeODC31WZ0YAwllkxgjRJM7tMv8OWnHuLmd/26NNt6Zth0xfV9YxfespFWSm5Mbn3nx8l7Va91Ie8+fdLn3yTrsWc5/5O3se4FKWgnby3SzON9XGprZN+uBWu+4TJz20bS5RZf9u717Xd/pCM5sZlqqnn8pF9XTOdB3ywd3HG/Xxk7yORoznPQd9WPLjQV6e9zEKjE7Hc1UlR9J9FVq5FB/FyDQdVge9HkdEhuHE2um58t6tw4fKj/1aJ14h1FmoMtBk9Z2PV2heHKeot1Lywu2cHr4QAm2lDtYMv33QJAabPF4KSEfetppGojFvUCjD+zyOyOnA9jz5RknJeTlZkjQCL8FECjOUA7T6AHa4elQlUHRuj+DZXlfvY6rX5XRbC4rQaVFIMnpfB0chJqPvKy06E16nFFQYmiTZSbAmE0BgWlLfhJiV0bmoUWLRtSZakGFl5pa6qAH3MWtgEKinvS26vrv/AmeZ9LW6QwS5fgmi+WfP7ypytL4gNB+uZUgVBFrRTUi50Z8RWN/PETRJF+HQotqbQxkJpedUwiI+0avg+TFj4oprR9kMy8l/7LQzmqtFH6pjHIiqBvJs225vupg1+CqmqHactmgmBFYUhGE+24+PI3Vzyzx5bf+yDWQEKNrHplamRXlSD7/pF/AVxaMHM3SipUgl6qbv0lQVtCuGYp9uxi7vqCb+abvbEJaZfBI2nWfLMNnTcXiCAegmDIlZ1jXHhD28xnNaVQag7A4lp5bOC8XLSdrGBxtI3yy110mdrjkp6zGPmmB9U/LeH/CgJfLwq/rW5u6jaPyvSlgm1VbFhlY7visqJmXuZMHDrZLiuirjMo7s7MpacAKrWRtF/xGODiTi/L/4BcrGujLrkL7XFVvsfBsy0/lk2HapvmxKDSIHoAuYoHAwncWbjWhfWLtOaklBj5mu2bCBXcHNqBzErgzP/grXLOp5ssrk2RLkuzsNK+9eKmQQHBuqanz1FzwO5IJHzxegu7ogkx2pUH8lPukvRiqmK5jn589Avv7/pemVD9oMDnoPsctZEIEp769QeVJTLDaVYjRdW1//mXehJkr7znwyvC10rSVWta7FOf+tSn72haxfT3l5uuSkEWFY+VVFuLA2tX7YJ+j9LGzHOjMnUE9a/v2E1b/wHrXh9K3tBQy/Z0inUvypRDypxUHxqk8HTneKYpxdTOyvfdQvHlBfJTbQh/4XSNs7fmWNjeIHVRHndtwcWdMlWUk3VZXC/7cE4LslOC9AJ+dgzwSraM5xCO1JYAmlXRkTUiyCRr7qbVnGT37yZTktpRfcTb4VvSrAVgNaQZzq61OuZQh2MHOf4ffuqDvPkdH/O1huLLC34M3OIamSFfXr/8mz8j/Hg2PVuG7vvRY8fM69Q1AfNZMv1sb/rR36C1dZ4day+w6MhBj8++psO/ppfZUUl9W/t3+5pvfcsoo4/LLCUK7g/SFNfavxun3OjwNR069lHZ5/H2tah+7HKD8uYsi54vrHmNrFjQyoAzAK20l2W/KbDq0BgUNHO2b9Jc86I0V7tPv0ATsL05uvWdH+eJED+WbnYFqXmmmFgCl3dGi/68mmEDfsC6EW5jxpap+wPwyLHg9//ykPA+Sc8BJGoxcWHNy0VXjSB7+/C7llSINimpSVCdE0cARsWRRZ1rCoggB3HU+EEmr7v2PeCjtGava5v+cAVuWgYVu0+/QONNtwEyc/sTIdeprt8MCAUZqKt8Qaosi72Yw55PkTvvFaIsSGGR3jVH41SR9Jw0G2bnoEY79RNIEERtLEfxlEQ+upYq1+KVR9mzi0Mxqw/opqC1Zcl7bbhIY0jWIsvM+VPi+wqBjswOTW/hVPMAXlzUTEkCELQA8umbitSL0rQ699oWw6+ZBWDulWHyp22/cCVIQVa61mbdC21znSJ9gVVCwfTz6Og8tVB3VH3emqZ6coivN21sS17byDfdJf4bRdZjz/Jwq7MCt11ucP6OTaQWXS7uzJGfbAedF19ekPNDe1E33xd1vHbjOM54hsagoOaZm1s2uCmX1IKgOehiLcr7nJ2VBUkXRyE3Awtj8nh1bZFMGWzPdKr8pSMzpcCAY2e0uATBqAS44lWf00Pas2++f+7TL0i0o4FmrN5zM1/+zM/57YLQjiYQTD+uBUSvHF2aRrbvSjItXpU+MogWWkHQ/ChhkbTOmEnd7Pj6IqAnU9WDk8P61cuuq+Sz2alFH6Je3pxl+vVyQWhlXIQD659xeeJT7/Pbp6pOB3Ra9a3I3FWW77uFzLyDk7V8oALIsioqz+G6F+Uivbg2RXmjwG7IBUylWaqOS8QaLhRekfxlSjIno2hKmL/awStofFBttKCFw5xzHRyiamCpQObGoMCuSeDJxr8646dRUnOoEuOaYA819/o8z+6QxSnLEy3EOolQbDVsrOk0btolOy0lmZOBoRNSW1v7nx9fAiyJChvRBZbKflHZKQPCVcYPgNkdAuFC2luKCmckolIHfEBneROdWvt30xywKW1JUy/Api91JpM2rQfmvCiqbM5TfH6SM3dvoqncNZZ8RhbXuyBcrKqXWqws66i1PPSq7j/LXpS+VpUdBegAWwT5NPX8jqa/Ufcj61We9esxc56q+dIBI7rADNr0mkJT8bIamT2u/d0P9eYj+/EPrQhfK0lXjUYGSxFDQRQmVKIE36VUhdZJNwHqmpp68Q/uuJ/63g2UNltkyjZrH1vah8m/KmR4wLoX9d5XPITY/IRM5KtipYZOCpoDkJlvcnDH/XwpIivBI62H/HgpncfS9kHqRYvMfBssAnLhaxSgssll6GXhm8wW1xa45oslCbkelihBkFqRVRfU1rksbPL6OC+oD7mkqsKLcZML3Om3gV3JsnlAxu7oWTb0BcwUairmqJ2XAh8AohIMNwfk4rn2pUW/DlZ7btswa/U3tW2CO+94ENsTYio9FsiFd+Fal9SCRe6kVDUbBa/Q58V2hpHya2QuyKET8ruuSZtmLHVdOnJUUfWem7FrLUpb0lTXtRf+VFlqNwMXXMobvU1MWlAbscifbt8vkJWQTQCDolTVoXiq45BMfeX9H5R3UE+0q3hn2wTrXmhnQSlfI9GQufMyS4vrrUL2ojTzut6UKm0/XZLpslTtNx9dGJK1Q5EuhBTYQm0W/M2DF4NoPfbsEiSinjBYN1Gq5w46Nf+gzCId86mtT28ffhd9Wj66agTZ99/0AT9psCobEUSX6iPrhdT5YQJRRzONALIaeHuxCeNF7QgzHmJNLcIDn31SCpZBm7HnFqkXpPRo2TD23KJf2n33j/0GAOMB/d+17wEuHCwy8NmTvPkdHwMvUHZho2canJKxWn7KogEbqw5DL8tkwnqqpzvveJDcRZeRYzIdlKJmHgZPCR9+79qQnZF+s8q47cPT3YxLy3FxspbPZ9D8Bs2rvgjN7t1AZt7h/B6b4WNyURy4gF/GRVU1hva90rUkfc6bx0+S2TaB9Zg8Xv2R2xg8DXPXu4iWoHCmXYiyOWAzfUOa6gYvefGaBk5RsDifpnzfLe2qA56pzNyQqTFVFe/FtfK1beYE9aKWPspTVgpnXVopCaHfcFhuKCrjGdYcrS0Rhro/SdcwDn3h/X7slY7OVKmvdA1HzZMOTVfvoEXbT5Yuy3svmjZOVpoP6wX8mEMnLdGudk0KteET8gcnK/xYPx0ir0IuxJ5dS1Ceat50bdz06YF8lpQeq8yl6lz9OYsqAWO2Me+d4k3//XNzn1wF02JHfbH451yBdNUIsj71qU996lObvpNyLV41guzTz/2K/7/pS1HULTYqiLppY0kDqKPamYHZYcjBIP/V4toUeP6dzPGT2OUGE5+SAc6byu3il9A2zWRnJbQuyDRT2Zxn+IS7pKRKdtalMiY4dbDIlkMlZm7bCODV30pTH4aSbTP+hAwKOrjjfuzRIqOPz+CMFslrCWhrIxa1EfxsEna9nZU+P+n4yWQHT8gkv1/+zM/K3bZhUgryYao5a+3fTdN7Hp7w/IhrjrTf1qE/fYLW/t3kj05R3zLqowb1rB06qEIf683v+Bh5r/3ABYfyJpvMjEVqAT/JcW0kTXWdzcjLDm5KXk/VSpOZl77AkcPnQlFwJsjDKaTJnJqhsVPaYpsDUB+R8VfOgPwAzOUEg2dh/RfaqaUKjz3bAQwxfT9BpjJ9fJUVwyU83krXPkxtxSmk/ez22Tnbr0OWQWpbIDO4OFlBZb0M2NfjyFRQfOnGcd/c7T79AocUSEWzXtS3jPKopyHqPkCdL90MqGtyuhVEnRvkf6sf3EvWMPeafjVds14Oy05i+g6C319VYI+gwppBYIAgkEVcc1UcigP/D3rhTUHVrWqtaquCf8PAIWZQqHJwz+6VJkwVkKuXeIFOmLnyhzlZyzf1zG21mb9BLk65M2mGTrgsbBTkZqDiweyv+T+LvtnuUc9cBTBz20YW1wiq47D2hXY9qsLpGt/6nhzNDXWGviol3Jqjcowvff7nQ4WWed1h83L73R/x+9HnxHTU60G/+pzoef/0ua3sHOPizjTO7XMszA6w/U/kNU3dlKM2IvNHZqdlH4UzLZoDglTVpfjyQkcBScWPbs5TlbhL2wcpvrzAN39IbkDs8SruqTwIsBqCxrA0xVk1izUvyWKjuemm33dQsLeioGcvKvg8COyh96X3o+qj6XOuQDeZUzM+wAbk86UqeatcoMXnJ31AiwKrqHnqQJlqG4KwOmBBORWjrjEIFBMU9hJono14b1cD7LH5Nx/oCexx+qc+uCJ8rSRdNRoZBL9MUcAOczcZ1F+UQAv7PUw7CNrJBsH2TQhz0Ljq3PrBve3krd5Lrfdh2uY7+vAEGbBkF3no2Ee5844Huf3uj5CfWuT8Prmz1xPIXtxZJDUnH6FWGirjgsprmtRGbQqn2rtpVeH3rn0P+MCLJz/5XkD6M1W15mZOcG5vjuaIA8L1BVh9yKbw51/xr1v3exw69tElC7P6X2WkcLxd9gHrXlL7dy9x3iuYuzm3Ydr2wR33+30oYZOqOqSqaQYHFlkzWGF2h9RUKxtdmsMOgy+nyE/JTWPx5QVfKKnEv4qUEFMVukHmwcwcOkzhaSjddwsD57zMJ4t5ho8LPwl0zdN2177UBlaoPio7x8homqUp9PU5UfdfLcjmexVk1TD71Bf+DEs3U9w4Tm0kTWV8A/lJqYarXJfy+cr5gCFntOgnWXbBL4tycMf9HeEYvl/usWcDhbUaW+zZ1VF7TBe65ruihFmQwAor4Knej7C5WS0SEhSa+ByPrqg4sqteI4tLYYtWFJw2br9hu78kfYW9FN/1079BbQS2HCotgSN3o1vf+XEAnvjU+5aMAQSaSVQqpOzUIhfeVPTNQpUxIQtKbqqRO5Fl/CkphM7vTpOflKa3/OnKkpyNOlx7+qYi02+uQylF7oLl96EEoeJRN8EF5btTvytTnDpXZT8Pqr5tasGqMCWE59wzQRmlG8e5sMumem2Ttc9IAV85UCKdcmg9MdKuIzYq49jqwxLwsO4ZDcDg8VzfMuoLeFX0NHNqxs9WDzKLfG1MW/CV6bjcwCmk/WoAag6hXWcrTPMK2gxGBeqbFGTt0H/T51gFuat8nUo7VaEPuiat7tmb3/GxjtyUejb8oI1fVEoqvY2eEzGofZhLIsh6EgSAMbW3VYHf/8feNLJXfubK08i+IwVZkACJegGTULe+4/jcuglT/bjYs4vTB4psfqS0JB4mjkapk/liquS71mPP+osNSCSeWmxV/NneH/51pm5xyK9foDI7QO5bchEWTS/bflUWvNST/yphpuLZ5ramZXhAWWakX/e3Z3X2/GKc6pp0wRQkxO/a9wCl7YM+KlBdD9AhpIKEatimQEfm6Xn/mgO2vwBP39BePOZuWaRV96oMLMi/2RmL7AyUbq5ivZpj+JtSe00tun6Wk/Imy89sMnKs1aG1qAWxtX93R5JjHVlY2j7onwOdfmOVyQMI3FgEXbM+F0nLDJl9mpXKzWKrHdoyBCY6VjwHZa9X91GP/zP5UxqZKTCDrkfnEcLfryCtNmw+V6OMy3eSILuqTIt96lOf+tQnj76D4PdXrUYWV/uBaO2rm6Z2qRpcXJ5MEyW0TX+m+STIdBZnXL2d0mbyk/WOXbIOjNCd4ZM/cxvzuxpkT6dppdq29nQJ8pOuD2xQpDKuO4W0b0IDqe29ensOu9KOgVLjm8izKPDO7Xd/hHM3p3FTsP5p6SdSwI+wUhvmfKi+guZexe3pAAOlEVd2jjG3VWp+ri1jo5p5l9y0F5ycgup1ddaOzTN9eoT8SbmfLL7iaWMbBY2iTO0FEpU4OOn6mej14pDKnwad5kOlUZqxiOr6lfamjqlrMOPMoPN5MucoSCMJA4mYvk3TbKnMhmHmziBTYlBpljALiAIAqTFgaV1A0ywYpKErjVYP/Na1TP35Cqt3tiqmxV//5d40svf+uxXhayXpqhRkUYtQmC/A/D2MupkJk/rQuo0VdB1hbYPMH2Ftu/F4+90f8UEWZliA+n7Xvgd4+T6ZeFhcW8GZHOCaL7qUN9msfaldrRjwUY+ZQ4dle00In79DwslHji1y5rtz1Edc1n0VHwShO+/DTF66UK0f3MuZf5Bm3e5Jzn5zjPwZCY4YPi7TNOkLmSIFAjBLqZiZKkxzlu6PU74pu9zoqO81u0Pg3lCmcdbzbW0pkbId5qYL2FNpUlUv1+BFr08H6kP4xT9V8tyhkzXfhAkyRKI2YpGdbfmQdMAvm5KqOj7oQ5VFaaUFVsNdUjpGkX6dQYG/UYJKUdxnVRdmsDT4XOcpzC8VlXXHFMxB/irzmk1QhwLahJkQzUB5vS6eIrWxWHVB9vEeBdn7rjxBdlWZFrtpR91QinGAGOqBjTNGr/yqseMI2APWvcz8yG08E4DSCus/yPlsnpMBvtR6CD4VzLvKMpGe97SMY4PkLsL062XKJ0VOVvgFElNVxx/r1nd+nNLttzEw7foZ4subs6QXYOhbcuHV/T+KryC+79r3AIe0GlutqkN9naDaSJO5aPmaTvHlBZxCukMw3373R8gcOkxr/27Km7OMzkz4fSoflJ6oV5HSapSvSfnqLu7MUTxlM/Snsvhka/9uZl6XQwDpTRJdmss0mD4/ROpcxq/PBjLzSvG0l83Etlj/hTMAvsZVGc9QL1qUr5Gbg4ELDq2UIDvb6FhAayNpH7GpsmnMbreprwGrBuNPN/0xZ999q18oUwfR6EJFFxhBOUr1e9HtWVUU9uyltk342m1QQmI9vVSURgZ01F3TBZczWuzIUq8LRn2Do2+ewiD1HRqZ8ZvSHpWmttzWm67UjyO7cihMI1tpbSmov17AFUG/d9P4FKmX7hs/vpGJ/1XzAQxhueeSXEsQT/r31LYJjv7UBloZ7/lxIT1nkz8LtVGZYkjRuucbviamKgXbtRbnd0vTn0omu+aoS+laGcw7+gePdwi9Jz71Ph/UYe6GzXiv+sG9XHhDmoUb6owczvjaocqurwJrQSL/StsHmdtmYdWlCQ+kNmg99qxvRtLNhvmjUzijxY4qxoDfr4qzAxn0PbW/weBwlUZTSuzhfJWpyWHy38wwfLzl96FK6xRO1zriq1JVx0cgnt+dpiVlE1YDNv3dIrWRNPnTlQ4gi578GODU3UWqmxukZlMUTgm/+rYey2WiQ9V9N01vQdp+2MZI9fVIwEYrqK15js4LdGpZZhUAvahnFCglLqDKLD6qxneffoHW/t1LYuNMoa9fo26mfPipD/JWcc/KF9b86K/0ppHd/4EV4Wsl6aoRZPt5u1/G5VIElrLjB/kEdLpUlGO380yBpQJImwN2R+Cs+v38HZsovCq1gy99/ueB7ln7g8bQs9l34+/8T97G3Ou8INyhOq35DLn1FXihyOCrst3ABYfqOpvRP3ic+sG9fpXgVkplvG8xu0Oa/lIVGSycn6xTG0l38BK1MVHXoaobz79GUNnaoLC2QuoLw4wck/PiZC0/uLbuxVzZNWkKrWyC5oAsLQISHr/2pYY/lsrz2ChYfm7GizvTjD0nBYUSNCmvtIuCyJ/5BxaZ15SpVdOsG5XCcNvIDIefei2bvtTqEEC6oAU6/FggNa0L32Xj7vI0r/N5xp6yyE82qQ/ZvvDMn65Q2ZzHyQqqayXfdh0W18gExmtf6kSPdlvY4yz8ptkuqOxPN0QkLA04D2pj+nLV5sYMXo6DwtT7DEK/qmMKtatCVZQmr7fVfdfq2nX+dB/2//ibn1l50+J3kCCzujdZeRJC/IQQ4qQQYlEI8aQQYt/l5qlPfepTn65kUgHRST8ePSWEeEkI8ROX8RJi02X3kQkh7gN+HfhXwJPAzwB/LYTY6bru+bj9fG7uk/7/ccARYaTvyKL6UMfDTItJ/HVBbR9pPeRnKjj9xhzr/37Rz6K+uFZmjRgeLXLqoDSnbP2vZwLNQkGk+FQ71wtv2ciaF8vYtVbgTjqM/62/9XGsIRmrlMo4tEYXEX9fZOhbrg/UqIxnWFwrzX1O1vJLc5ReA/lzMLujfayVaseo1UbGAxFj+hyrHTPIXbhKx7S4Jk21KajXU+RLboeGU9k5RubQYbJe33PXFyiccbDrNiCoeQnJRQsm96WpjbZwLSicbBcEnZ/I4mQFg2dbviamp1RqDtjURrw9ou2yuJDBzjjUHdn26xfWkyoJqutssrPtwOXKeIYnPvU+31ylTMWze2X2CwnWgPo5qe3ZFYvKmCA7a5GfrHNxp1dYMytj55zRIsWXJRu1sZxfKVuZRkHG4mW850DF5am51X1kpnkv6HmAcB+a3iboPqpjepVp89wgK4jyPynwEUBTMy0GvY+6z0v5Fg/uuB/XQEqqY9DWxPzKB9ocKVJaof68Kq2saZSHWRXqF9ZcRQaEeBI47Lruv/a+W8ArwG+5rvtrMc5fYlrslZbbh7bcpJzhyuSUOTXDzG0bfRSa8uOorBTdfGXq5T5z/21s+bQEFsTJ4KCbkc5+r0Qc1oelOW7sdx/vKE1SunGcua02i+uk4Kpp1rLMHDhZqI575U0yLdJzNuOHnUATp+l41/m9a98DTN4qF+fSNpfWaJ1MvkHmKwXfRKib/VT/SsCePgCiKRh/7QV5jZuO8IaB09w+8Cq3/e2/JvuSzMjbHJR8L9xQI306S042Z3EMmoUWuNAaaDG4TiJe1gxWaTg2g5ka24dkssXHT0/QfGkYqwZrviHzLkIblajyDV7cKU2OVl2WOslPOpzZL1hznRRw1Voa95lhBi5A8VTDN5fqYQ46qedDDwxXYBU1JyZ0XEfjQWeNrqj7E+ZHU/2G5TFUfekU5Ts2zXmKR0VB/lTd56U2jCoDjNo86v5m3f8G+FlT6kO2P9e1sRypqtMR3qFn+dATTx869tFVQS1u+Q+9mRZP/cKVZ1q8rBqZECIDvAnwC4i5rtsSQvwNcGvIOVkgqx0qQqdGlpRMlGCSc5aTuvUZ9IKPIl+ShzXtBGDywCaKp6T2oV4mPXmrvtBs+ujjfv66KN5Mqm8ZZf61HspOQCtlyUzyk3UuvEVqjUMna9TW2DQLLYRjyarQwMA5uXgv3FDDuiDjyKyaRWYWX8iY2mHY3BzccT+VG8d99GMr22JopIIQLnNvqONaKk4tjd2QL3b5x2+TRyoutRHBxGtf5XypwM3rTwLwxvxJNqTmOOOkyL40wOJ6eZ2iKXAtwcjoAgunszQ8lH1jY52h0QVu23SCkXSV4ZREKG5Oz3C2sYY//9ZuTpSkFF88OYTIutTHHGbsFLaXanFhY47cjKoGYDN/vdQw0zMp0iWorrNhrMo/3PwSADmrwe/P/QOyFzMdGqGetkpRbSzH4vUFhv70CcToLuYnVC7GDIU//wrZwu4l6DyFtDMrJes1zBSZYSlBgi4q7ZN+3LQodLMsHLDuXQJvV+Rr7Ez4gsW0NqjUX6r+GkAT+fxVb7y5Iwt/frLO7I4cmVKLetHyEz77871nFxXvmAnz1y0mn579ROA1LScJesi1uCKcrDxdbtPiOsAGJo3jk8D1Iee8H/il5WSiF6DGSqAik55rttfRXOOn2jvqm9/16wA0Br2qyAlQjSbsXEev1W4cZ+xp2Wd5o6C6yeXCrhzrXlj0Id2t/bvZ+ESD0pY0cztcrLpsL1xZwbhyJovwCk2PH3bIzjb8hVOPxwkyUd15x4Mc3HG/j0Csq03zgEOjafPasSm+OlVkYUICUtxMC1GzSC20BarVFLjrFqnPDbFrw1l2DcoSyg03xeOV63h06npqN1Rxa1JKuos21RsaVGYGYW2Tta+RO/e1Awv8k41PM2JXmHdy1Lwyx/vz3+JIfY4/qNzGxW+sBaBwSlBbA+6mBvVRi9aA5C9/Mo1dc8lPtph6ow1pyWNjY536mCA7UiMFVL1S0DfmT/G6rWf4em0z6ekUo1/3gB21FpXNeR+CD3KhzU5BzcuTOXRSSs/MqRnq+3fTHLA7kHXmvaYLgCKMguDxitSGygRYhQlJ1Z9OYf2qZz/oGQpCGuoJBECiaxsFi+EjZS6+oeAXeZ2+IUd1HHIX5FzPXO9BSK9PUzgjhdvoHzwOwOx9t5D3No/KVLmq9B2U2eNyC7Je6EGkT01RETitV4iG6MDlOAKnF2EVZFa5FOEWd8Ewx3BGi1x8Q4GUl91e+at0/0dcqm8ZZfqGHMMnJJxbR6UVn5/0TS7VdUVa2RZOxsYuN3hYWwSbO8dwMuAUHdJn5SM3cEH60UYfn/HHUv1WNudpXH+rH4ulFjplBlLzYu/ZRWXnGJVxm0a+XY/LSjtkM01Ol4ZxXcjMer6hczatlKzh1bpG7qAHCzWGBhYZyVaZref44kW5fxq069RaKVKixdqRMlPnRuTxjWXymTrTR9cxfsN5/sG4dELl7To3ZV/h8OIE16ansTxnwzV2kW+KFvWpAfLn5SLhCsjMQmMqizvSQFTlnDQKMu6uMm4zMAm1MU8wjdRxLAtcEJbLtxakZldzruea/BzH1ozRyLUolaWAW1yTJlNyyZ9uoydVLTCQfsHhI2V/zjMAW0aluc/TvEyNqn5wr38/TWGiU5j5zzQJ68LK1JCCtH9lVm8eP7nE1Giep8ZS55j8AX5+zy95glS11TdJav6crKC8yaslNw6Noktt1CU9L3NmgjStF87ITC7T75Hafna2hV1u+FW/9SrTq0LfQXFkl1uQXQAcYNw4Pg6cCzrBdd0a4Ne9EOLK3EH0qU996lOflocuqyBzXbcuhHgGuBP4LPhgjzuB307SV/PEqVD0Xy8UpXVFaVlxy10k5aGbdqZrgiqjwfk7Nsl6YqdmAs/pRgese8lsm2DssbajunTjONkto0zdlMOqF/GsXLKys+VSnmhReTnfUXAyO7VIZjzFwCspv33pWkHh9NIxH37qg/5uWG0OnULaR9bp2e8Vj+PbJjh17ybEdVLLaFXSzL46RGrOxs5AY7Pc91TdLIVXoLYGWl7Gi7IraDoW+XSdcj3L8XNS83RmMuQ3lalMDTL8YoqxkuRmfmKYhRrk6zC/Nccr1TUAnJhby5994000ThZwBlvYI3LMf/TaF8laTbBdUlXJ89hzi15+SYvafNYPgkktyKrP6TJgQ25SagH1xRzkWjRm06Q3Vjg+JzWyFoJKM81IocKMU6CyWZooB0/ZpKqCyua8X6tOgRFSVYfcdLvkS/PgXmbHU6x5sdxRm00F/KrnTsUmBmlL6niQb0x/V4JqfYUFPuuIVEVh75Z69vV+grRGHYmZ16pl2zMl8LQ99dzao0WmbyqSKbWojUiNC6Ax4oDl4lrQGHFxLa+ygSOD350Mvq+2eMrxtd/ZvRva9dIi0motK/U1slWlXwf+RAjxNPAUEn4/CPxR0o7Uw5s0S0VSuH4353Octkmpm1AzX/L6llFGjnnBulqqn27Xqid2rd5zM+f32FiNTWz5vPQ1KGSb+8ZNtDKythZA8RQMvpxicUyCJ2wjs4STFbQy0CjIN6U5oPIwtkvB3LXvAd/3Vt2RY6QgE95ajz0bCkap3nMzF6+zWXPnWW4bOwHAf//qHtIzKTJzUHjVZWpP2m9fWQ/OgEt6Rj764nyK6haLV9w1WFbL944LRyCeHGbttMx1mJ+UwIvq2jS1UXAtaM7keaZ5LQD5XJ3v2fp1nhm6ltcUL3J8TvrDjpfX8Y2pMXKnU36h0Is7c6w5uohdS+OcaafwWlyb8s3AelB1ZdymssGmmXepl7IsWJLHV61hGi2LieGL2JbL1Bk5540iZGflnKucj8NHyj4IJKNvbLaMkp21/CTOfsXlctsUqT8rcWqTmRB5CH43gnI2BrXXfVtBPjrTB6f75XRznnk+4JfiUVW4Z7cPSt4GBK4t/zo5fD+uaAjcQgtRtRCO8FGrmbJ8ptccbbC4Vj5b9SGb0cfPShTxvNOe0z27ePvwuyLncDnoEgtrXlF02QWZ67p/LoQYAx4ANgDPAd/ruq4JAImkz819cknS4G6C5VI1N33nZwoLvc2lCjOzD/3/gzvu58wv3LYEkq4S2M7uyLG2HA/9p1/PkZ/egFtwsEqCVtql5L3gTzzV9jGc/D6BSMs3vFLL4AzAtp9/wi+8qca8844HWXN0Echx8QYFtcfP5K4vTHfe8SDzEzbz1zmkFiWybtTLdaiKeqqCoPWihTVisfD6Oj917ZP819Myjn7gmxnSC9IPVxsStHJSUDjji9QraTJDNeoLXtHKUxnG/yZNYzCDXXPJ5KWp2nIkelBlS1HQ9sFJl8FJqA0JqvU0oulpdgWXz51/I3a+wTWD83zXWpnapNZK8cLctQwu4i9wa44uYpcbZKEjU0uedlyTM1qUKEVkDsb0PNiLguaIoNmUKtx8Ncu64gKVZprp+UGcgpfTciFFy4ZWWjD6uKzp5owWSVUdmdR4pl3rS+WIxMtvqEI7rMee9Tc1esaL1LYJ7rzjwSVVmE2EYbcNXVCMl0pfZlLc98f0kZlambrm1v7doMHrM0DdS0Wm4PQX31CgkYf8ZIuFjTZ4giwlLFo1QXpBYFdgYFqBhsCuQWU85QND9DFTVcd//+6840E+N/dJBb9fOfoO0sguexzZpVKcOLJeQRNxKG7w8XKSPuZd+x6gNpajPmT7sVv6DlPttAHfVKKCO/XigpNvyuHkZBFMRZUNMPgqbPyrMx27cLWwfetXbsPJegl5TwgKZ2QVaH1BVHkKFQBFpaaqDcOmL5U6CiyqJL3HP3YrroD8Gdl2/JlFHv3C+7nzjgc58905HC/4or6lBtUU9nCdf3rD0/zpYZlGaOilNOmKjK1KVR1eeZsKFHZJVQS1zQ2seSlUrEW5q772f56hvmWU82+UbSvXuORfFVhNWPfCog9XX1wjyJQkQnL4hEOjIIVKKwWNvKA+DJVrHeyRdlFLp5oifyzNxifaOR/1mC4dbaoXM1ULsUqpZddcLl5nY3sb+9LWFm6xCVWb3HnbTwvmZGD4RKMjzklVnjaz/OvaS1DJF1haKVyPAwtK4Gs+o2GkowvVOd02WWYF5m79BJWOUddh8q0LbLFnF7WxHKUtadIL7YKnzQFBZVyQm5aFUBUSWDiyekNlPNMRx2e+C+rY4svfXPFcixO//O+xcgnjyBYXOfnv/u2K8LWSdNk1sj71qU996tPy03eSafGq0shSIr3kd91pHJZ2KSgTQZQTOg7F8RH0QkH97P6x36BeaJs51rxY9lPjmLWR9Bgy5XwGmN2RY+461w9UFi7Mvb6BPZ/i+M++d0km8NS2CWb3bqC0uZ26af0Xzvg7fjWuSq+k6mP5fAy00yXpu3i1E3aylh+IWnx5gcrmPPMTNnOvbyBseZ1brr3A6ck1CAv2TZzkiReuA2D0WWlasz2lqLxZ/h39eouFjRZOGhbHZB9OvoWbbbH26TTFUw0/LqiZl9qpXZemvbmd0lyUP22RnZc78NSiNF2CNJWWtsq+rnvtGfIpufv+xtQY1XKWkSezZOc9M5SXiUXPLgGdPqDqPe1A3Opai/qw9NNYdXByag6h8CrURuT3wque2TaFb95SsPvy5iy56aafYb/lbWFbKUGm1KL48oIPCFH3J390itm9G5ZoGEorMv1VSUJdwsqiJMlYrx8PAqEEmT7NvtR4Jj8qKXD1npv9RNOKVOYVlUgaZOye0oAVkKYynvFTrpljrEb2+60P9KaRnfjgvwU4ijSo/o7rur+znPytBF01GpnYfQP8/Tf973oKHDPY0Xzwg17COC9BFK0G6EPRumc8M5V6gTyQgFp0FB3ccb9f2fiufQ9w9oC032fmYGC6xbaHOtNcCScnM8f/bDsT+/xEluzmm8mfrlB8eYH8ZDvVUX3LKNbxkziFNE5Btq8XLaprcyxcA610iuxFuTiPPSed4s6N477Pq4BML5RBxi0Vn5e+I2e0yPk9NvnvmuGO9ac5V5W+0FI9S3GoyuxkkZdn15E7LR/n7GzLz2o/MN0iM+cFr77OojHs0kq5uJ7fLDWbgoqFXXNxshbDJ9rlTeYnsqSqLuf3CBiVUtGZyZE+65KbblIZT/nC0snCmpcs5q4TzFYHmHalT9F1BWIuTbri+sJj+MiCb1INqgGW2jbhB+MCzNxQpLbWAQGZaZuCZkJs5GHoZIvSZovqOjm3g2db/sKqqm9X1wmauTTnd6dJL0B2Vgo915YbBVWSRm0wQCJUn/jU+9j9Y7/hP2OVnWNL8gsqCtq06b/r75MZa2keNzeSakOqm6L1McPeL9NPdte+B5a823oGDrXpzSLdRXatRenG8Y7CsK39u6mNpLFrLd/vCe16d8okW0CaKOtbRkORlCtKlxYQ3c+1uJqkdh9v2/qTcFI6tk37fbcA5W62+eX0cSXJitDtHP347Xd/hOkbvNx8DlzzF9Lno3bi0H4JQe64S1tk+/SCS3WdYMOXSx1CP2j+br/7I37dLb0qMciFT5UlUci4M3dvYu5NNQaHF6kdGfbRX40Rh9HnbUpbYPTr8hlMl+UCnDl02Be4IIXohfdW2Dw0x1w9x+kzUkhmT2apjTnYVYtUWdYxAynImgOCRl7QHGgjzqrrpQY2+oK1pOqyPjeAX0ames/NTL3Rprbeg7Yft8lPuaSqLuVNFhlP4XUyUntLLXp1yDxNTfkN9bRRetHIoOdA15QBXnlbjmbepZV2yU5buJ4iMDAF+fMtypssCmfaAIPMvEN2alGmpfIW2mZOsLBRzkWjAANeOu7CmRa1Ecv3J6qK0qpUTWU8xdDJmr84Kz+mGfyva0b6JlIPhA5DOyZBD8e1lJiaWtA56np0wJF65p3RIpXNeYrPT/q5S6EdTqI2iepe6SjPIP+jXkftgHUvTGzkb078FqykRvahX+1NI/vQv1kRvlaSrhpBFmVaNCkIhqva9iJoIBzaHrSzXG5SPJ//SZlRYPwJb/e8OU95k+0XllSFIpXZSE8+DHS8sM3jJynfd4tMmXS64ifkHTnW4OQ7YO3TacYfOdPBx+m3b2LhNS0GzlpseUj+NnlgE7Ova2FXZOFKVRSysbZJ7tWUhDZ7FsfiKZjbDs1NNQZfynLNo/I65q4vcPG1Aifn4gy2wEvpRNUmf9om56HJ85MeOtErbFkbkdnh81PyGa+uFdh1Cd7QTZuK9MSwCqCinPVqgVfC9vQdKVJbyyxelAvFyPNp7LqsbzZ0suZnol/3TAl7ptQh+KOS4yphqmqTKVJ13FJVl3pRSrLmAOQuuv5GRV2LMoPpwllVl1YCXJktmwMS3Wk1XDLzjj/OmhfLPohI1TkDfJOaXWv5sWWKdNBFlABZrvch6l0Ns6aYZArfoCTD+nEFztHjJEGGmegFPfU+zIrXqW0TqwL22PZLvQmy4x/uC7JVJ71C9PeP/Aug06xo0qX4uLqdHydOS5EuTMNiZ5K+5MpEN3L4nL9bDNptBlWyNc2tKtfc3HZB/hyUr5HH69fWGTiWYehbLsNHyj4sPzPvsLg2xcK4YO1L7YrQj7RkrsdmTjB7RxXLlppD6vlBCq+6NPKCdEX5dgTzW6FZbJF/1aIuLYhkZqGyuYU9XsWp27iOXMituRRD37AYmJYamMofWBtJUxuxWPNimfP7ij7KMT/leqhD12+royrNxaa+ZZTaSJri85Mdi5JCeS6ud2kOS+E5/LUUmZKLkxWkF1wf9q4E2MxtGztixHSkoi7Y1KJa3zLKub3aImRBftIlO9vyg5wvvKlIftLxYfqZUsu/F6qIqNqs6KYwhbAEmTR56GS7urheOdsppKmMZzyzq2z/xKfex513POhfQ1AlgqDnOEx7WomNXtB7aArZKH9b0HddOAUJZ12zU78HhSmo6z+w7adWXCPb9sEeBdkDV54gu2p8ZH3qU5/61CeNekAt9uPILhOFmRajkExw6bs/M3ZFURRKK0ky4aT8HbDu9RO7miXYFd217wGcQpqpm3IMXHD9pLxBbVWKq7XPSdOYMqGcvTXNmm/IhL+n9+dY3OSVGplOkbsgs0qMfr3lZ6vITi3iFNJc3JmjfA3Yr5ebvMxjQ4wca3DmzWlaXpb3wTOC7KzMDFIfhpTEOlAfBmdHlWvHZjj35Wv84yrlk5OVwajrn5KmSD1buV1r+eYypS3VhoTf1n36BVr7d3dmu0CaWZsDdoc/BOQuuzaS9s2tGS91VarqaZVpQTMnfO2outbCrrdjjEBqzHqtL31M67FnKd93ix+vBLC4zsW1Ye3zdGhkAKXtg1TWW1THIO2BC1WM0+jjZ30NKzvb8PtupYWvHdZG0jhZ4dez082SulaqwA5O1urIqm/6g0yKAlglpTjvTFTfQb+r2D1dQwaWWCtMHsLG0t9zU9tWdOcdD2KdPLvyGtkHfhU7oUbmLC5y/FeuPI3sqhFkumlRLRD6A6pTGMTXpCSmwiCzhOIlCqzR6wut951U4M38yG04mfbCX9o+SHmTxYbfeHzJS276PADmf/BWho+U/cwhAKXvKTPxH1ymbyoy+gePLyl0OPvuW5mfENTXyAXx+v90jvqWUV55W476Zgn9y53ISDOgK6HvOVmHkuk3Omy//gylWo7Fh8fY8GXJ95nbi1iO9LG5dluwpRdcKmPCRyCqas1OVvhAkMN/+F6fP1VYEWDmNllHrXC6RnlzltHHz/pVpYEloQWKMvOOD5ZYXCMk2hOY3ZGm+Io0/6naZVZdokT1zBtqbOWDS1Udpm+Qc1tbIwt6tjIuA2eFXyj0S5//ee6840GtwnTbj5aZdzr8f+oaUtsmOqDkfgqxQrojUBvaWUYAv76c1ZThA/nJup89Btom2qQB0Ulyky6HTy3MVRC1ATXdFKqdHkAd9Lvq16znBuC88Tq++OyD0Bdky0JXpSBTtBLACpPChIq+8KvYKF1TCuLvUvwFcez+eizY3PUFP1tBZt5hcl+aLZ8vLYltUn3oSYNrIxb5ySaZQ4d9gaUqDB//2K2MHBGs/4IEe6i4slMHi6TL+Ii75q0l8o8Uyc7KBR0k0m/+tS1cAYOnLL+adGNTHZFqYZ/O8Zq/bms2ynejYnUmD8hq1flJWddMITYVOtOuuaz727Ocv2MTAxe8GmAeolAhJVUclSq2qFf+Bek7VL4mBZAAfJRg/uiUfx5IDWZ+wqY5gO+rc1OQPyOzbygNB/D9cfUto8zuyPnAjEZeUNkEG24+QzFd4/gjWwHY9HeLfgaQoKrP+uJpbixUOig9E4vpu1PIPQXlVzS3zSJVVdks5FhKaDaPn/T9RerZiaIwbaebRSWIogAeSd+rKCGrfM/m2EF+Z7NPWL04sm3/tkdB9u+vPEF2VfnI4jhwgyiu87eXvlPbJrjwhgKl1whq33sL2/5nveP3sHi2Xq/FJL29noZn+vtvY/jltgP/TT/6G3IhNhIvmxnIpbYgyB+donJwb0dWdLFnF/lXpVnNXAS+66d/A9duJxl2v1lEOHRoDpWdYwyfgMl9acq76qTPSIHlNgXUUqTLMmygsl5KQ7mIWjQHbGo3jvvmRKmBpbEaLvUhuyPOrnn8JNZbNvqppeyZEvmZEs6eXR0B2wrBmVKhBAq1lhXYNSl0h0+0hWT+6BSM5aTgHt3lazql7YNs+HKJi28osLjGq4r9mhbz1wkaxTS0YM035ZiVcRtn7wYPOAN5L7qhuh4aWxZpODZHp9djeXXXaiNpsvt3U0ciUv3wXE8DMGMpFSrSAr78mZ8D4M3v+BgDKnbPi3cC+dy6T79AtiDNrnVP+7RrMou/kwZhw8Wd8vqzU3JzNHT85BIzbZjlIAw1rNp1A0GZgi/o3TDbxlkL1HlB6OZHWg/5eSh1a4/Ys4tDHvhFF2YqKYEJElmNXIv9zB5XEHXLtRgmKJabwnwBIHfxMoM5fhZ58+EGlrwcK0HqRaveczMDn33SP16+7xZKmy1e/OjPdrQLmjMdHalIISEVhN0MQm/t301lPMP0LrncpucgOy/NgOmy8r9IX82FNxVp2TIGC6C6Tmo0qao0ISq4fmrR9U1xSiOCTu2gfnCvn4FBaT46tF1pUKXtgx3ZNlRGB+UjUpSdbfg+I+U/g7bpTsW/qXkw440UzU9kqRcF+fOtDni7kxV+DJzKJgLAaB1huaSPDTDgCbiB6RaFP//KEh+frp2ZoRXmM6fujwkRV+hMlbPTNKdW11rU1rRj9FLVtslUn8e4sZyXSpey6VTvXRCCNMxqEpbvUZ2r2urfFR3ccT9//uy/U4JsxTSy7f+mN43s5V/ta2R96lOf+tSnbwfqZ7+/cigKtahIz7XYLa4liOK2DYtfqewc6zBbgaxJNf7ImQ4gQVj/cXewcYO5b3zvbzD/uiaDx+U+5ppHS/6O29w5B+2od//Yb5CfdDriq6Azfs8MLFW7WAWmAJi5QVBf1yQ9LfnIzMt0WRv/6oyf0xGkdjB9U5GBCw5OVjC7Q2pYa7/m+Gg8XRtUZjU9wBnwM10oxJ5/fCRNZdwmveD6aaFUbFlp+yDVtZZfLFH5hBSwQwdr6KQHm9e3jLbLpXg0d32BdLkTgaiO1UYsqmsFC1ukuuNmW+BIs6RdsUiX5f/rvtq+ft0vBfggEPXcqUwlSnvT50rNsQ70UOmy9GBgkNrehTcVcTJQH4L6mvb6kZ0WpKoyq4y6z8NHykvSSqmxTGAIdGpCQf4tEx0ZBuDoxV2gB6SrOdLXDEXKXKhM9dCZx1W/Hj2zvm6laLqNFfeR7fjF3jSyY7925WlkV40gm5ub66hHthxAiaTnhL1oeqqa8n2y1Ei9aFF4teFnBIDeIclB5wYJVfX/m9/xMV75Ry3skhQgg6eEj1jU4eBAIGpRCSz9uFliw+xD8ai3P/u9m5h/bYvWsITwY7lY0xm2v/cJvw20TWUqrZZe70nBxoMytahFSWXlUOAMPSHxyOFzHemIdEGsNiCzO3LUPZmoUlKtfa5Eafsg+Unp81SFMFX2DlOIquweIM2HmXnHz7yhzH+zezfQHBDUi4K53XUGRyQMc+F0kcxFi2bBxSk2sSpSqg4ds8ifby1BKKq+ABY2SqG/uA6y0zB6RKaiUoAQZWLVj0EbEKLMz3r6Lrvc4NybiyxsdnHGPJ9v00KUbbIXLPLn20mLW2nhh3kEZc1Igh7Wv0N0yraod9pMrRVEpiA1/9dTdUEb+ao2LWocJQzNmm6rkdmjL8iuIArzkcV9kBWpBy0M3dTt5VG/BWl8CjGmMiXAUv8SxH+xu1E34XbnHQ8ydVOOlqdlNPNw5MM/G9iHgg4HoTF1MIiKxzIXdP3azMVdzYdabBc2u9iLgjVHpGZkQsHVOcpnpbQRc4cPdPCl4uuUEKyutfxsIiN//IR/f1QRUOhM51Ufsv20UArtqOKqdAGix56p3feb3/GxjoSzQEe+SwUKAYn8dLKCqZssstfP0WpJYVs/USQ3KXDy0Bh0SVXl8dGXWj4MXq87p+poNfJQ2i75tZqCoW9YtDLSl2VpBgKF/kwvuCx4sWuDkzJtVXWtxfqnSr7PbX4iS+laWTW5ee0ixWEpbMvlHK1ymtRMiuwMfs20NUcbS2LxTE0vKMNMlNbUbcMXJ8ZT93GZmzHz9ze/42MdeUV1f7Dui1R+SDP1mwpj0GMRVyOObMcv/ip2NqEgq/UF2WWhINOiehmizBDdqFfThLngq8VFmbvUQ64S1QZpNUn5iuPoVqTzN/MjMjfj2udKofF2wBLzoeLRjKNRGp3SPAAfql8fsqmulQspQLoshYKCyYMsWtlKwebPnelYYPSEq7rGp6DeekJbaIM58kenqOwc60BFVsZT1EYEQyflSl58fjIwE7sSjpWdYyyuTfkFFIun2nBz3fyprl0tcvp9drIWA599siNgXT0XyoSp6JXvKXLDwW+yeeAin3v+JgCsmTRu2sUdaiKsFoNflYvT4KTMs6gEpG4CVCCVC7vkbsVqSrOtXYfFte0wCCcLqQVYXO/iDDlYg/L6WnMZUmWLzKy87gFPXteLUrtrZVzcTYu0Gt5uyBFQs7AXLNY/3V5TVGhEGCw9DOberbRSEHUzrYcFKIf1rdYQPZ5OUX3LKJXxjL8hVcVP85N1f7PaSgty080l5V0AWl98cuU1sl/oUZD9hytPkF2VYI+wB365fGFhY+i7PV1g6DE8apeWATyDWocfKsgk2O0auqGkwq5FZWqfvqnYYfcHb9foJQ6u3L2J3EUvW7xnJjq4434eNgSAWigGjp9k+j1SSNaGoDKWRrRg5GXHD04uXSuwmhbZWXzU4vAR6S9qHj/ZIbDUImLutA/uuJ8LE1nWePOrm+hmbrBI3bhJlk7ZLePLBi7AwkYZaK20pPqWUd9/YfqwCqfTOFkLq+Fie241FVNW97Q1Ty7LEjleGZvm8ZP+cbaMygTN+3e3s99vm8ChLcTUAtccsGUguN3gqzPXYF2Ux92xGq+9dpJN+TmePruFxbVeouKXPeSkYdZtHj9J7cZxBj77JFtO7/KvZ/Txs5y5e5Oc8wWv4nFOsLgWRFNAusX4Orl2nXOHcatZFsdbDH6rXXcrP+WSrggq6wVOYwCvNBxOzqU16GDVBeD6SMzaSJrMqc4q0/pzGiSs1G8mhWlTJlxfrzEWZkI0K0entk0sqRAN7fp7hzQTovKpFk81OgLFq+sEzYGsP4aTFdSGZAmfM7cXGXlZbp4GPvsk1tYtcGLJJf7/7b17fF3FdS/+nX2eOtKRZMmy/MLIj4RHMXENtjGlYDCmuLSFPPjRe28uoe9HQto8SEoSkkDTkhKatE3T3LZJm5D2pvlw00Lb1E14hLQpFAwOAUJx6tjGb9myLOlIOjrP+f0xe/aZM5qZPXufcyQfeX8/H30k7TN7Zu199p41a63vrNVUnEv0e8e/SYQIESJEaDvQkD8MzxFCXiWEvHNuhQ6HBWORPTr+kEf2APTppfzcE0E3baqYVWIfoptTTpnFrRhxVSqvLpsBeZNnpS+L6raNXvmPkxsTSK7tRO9ozmvrgK1K8/0OJldRxIq1An3cMpKvVcyqX2K1PVHoA8pLi0i9nvTcjAAwPZiAU2blRbq+9p8AmKVSXNWHJxTxOH4Pxbhc4YIBLP6340LdNWapTC1zUH5DHsVTKRAKVONuGZfzKEhnGfGptJepIp6vIDaa8yzMa256AABLUTW2Lo2OkYoXh+KIrRlC0T1XdOeVO2JIuZaHmLNwjJfDcfso7z+I6qqNyK2tr76cW5UAjQEv/v3FyC+jWHIR8+ddtXQ/SlUHB6f6USzHEHdPyS+OoZLqRMa16LzYDJjLNHfLFs8CBlgKrFgRKHYB1Vgt+33XUQBVAqeUxPAEkzs+5YBQIJEjcMosVyQAjKxnxVZTYzHkVjqg7gwytbQMJ10GPRN3CStsXJ5zEqh3s4vWk+zuM7EQVSmjxGdEbi9C7Fdk6Xp97q+XcfK2K9C7+wRyt2zx9k5mJ0tIASh1OZgejMPhPKUSBamw/X+c4QqwPY/VOLvXnGBELl+P0u49ymtoJhq0yKLCmnMJFWtRhBzgNaWQUZ1raqdScjLE7ABymiDdCysTLOTrsIUpnnbZr34G/S+yl/nk5ixoDPj+H7+nTpZrbnoAuVUJJKaol5ViyWef9voqCpk9+HVyF+XJ65g7b2oFKzpbXDuDxIG0lw8xv7SK5BkHK5+aqauBJt5LlQtJdDlyt8/E27ei0M0SDQPA9MoK0FUGLTpwUhWv7Evq9SQK/VXAoej/Hpttuo6WvByEct2p3NpO9O4+UVePrO/p4964dUpMKo0jEi/i+Uod/Z5vPOabxPmknx9gsahkroqRNzm442efYDLGZvD0mXV4/pk3Iru/lvCYb1iOrxmqi0sCbNKcGGKuW4Cl7Rq9KIZSFmzV7a5LYnkg7u4AKHXXCgQnx9lmZ0JZPLPrKFPC04Nx5PsJyl1AsZuiax0boFxxMDWaQXw0jo5h4rnRAHi5I3ksU4QcIxaTKasUlm7rjN+CE5hN6OIQt5nINcSA+jp9/P9jP5FG7z5GHAJYYmu2IZwi319b9CUna+Nwd2v3wQLoeK7luRbf+L5wMbIf/mEUIzsroFNAqnpJJgQJLO9wblW+YOKLIcZhyOXrPTnEceJrhrBLQbzQMSjDkj8K77sS4xeyLLYz/bPP2+HciiSAjJtbsBpnjwrPRziyPo30GVoXl/Guf80QplawP2eWVoAK4JxMednZAaDjhIPO45SlnHKp4s9IMQ9V9WFRmRUG0ph5+1YAjMSQHHfHXOKgOpEA6Sqje3cahV52PDYD9O4jSJ+uoOhWcOYxpkpfFthfs2qmB5OYXO7g9B3L0f+DqpeXklcIli1sPvHyCZBP45m9p7yYX4XXBhsYQKov61l8STCrpdzhoNwBTA86KGWrePr0GgDAko4cTuY7QeMU1WR96frizk2Y7I6h62v/iQn3XiQmq5gYcjC5roSZLqaARseTcLJ5JFNlxGJVTB1zMxjTGJI5eHkw4zUSJcppFhPL9xNMrmRWX2GwAlIkoDEK0lNCboLly6LFGGITcSTHWVJjnrpr0d4ZFHoTddYr/16vuemBuneGL4R0jGFy+fpZ8WcOzsYFWKyUt5MJS/E1Q3W5Evn7yL877K9df+7SQVRSxKvBxp+LQq+D/h+wRNA9B9z7e6HrYRggSJ9h5xd6WOFSp+hWD8+3t9FwNmPBWGTXr74Tj+3/EwB2WbWbwWBUtZOZh+KLJAa8xdVns8YPAnESmHj7Vo/9prMSxSSzhYE0hi9PIH0aXvVpkQKeW9vpJQLOnUeQmAQqSaD/1ZJHeOAUfXnvmaq8ia4AKJepkmKurLKbg7DUxdh4MytKcPIxLPoBWzVnD5XqkgIDtcKX/Pvh+6pGL0yg0M9IDE6RIOlOTiu+nfPaiHsARcUmb73gSXl5lvrUqRmc3JxF/6tskh9fzY5Xk2ziq3RQ0FV5UJd+H09WUJxKInYygfQp4imbchooLgIyx2tKBwAKvQT5rVNYs2QE5Sq79rGZDvz4wFHsG1+Mg0cGgJmY+705SI8QxKdZtWnOziQVJks5zeQq9LO+6UABoADNJeCUCNLD7r09zKz2WJFZf3yjt2g1it+juIFbfEdEy1ikwoubinX7u3g/fC8Xd6Nz8A3xPa9NYnol832nxkp15Xp4+8JAGtODcY9xy5NDz/SzBV01ziwrbqmX08Rj4fLq4NUYkJqgyC8m6Dxe9dy8i1/IobR7T8tZi298b0iL7NPtZ5EtGEV27ca7kRpnqyPRlSfHpMK45wD7BKa682XXFa89Vdy5aVZWfN5eRQsX4Te27hpUsvPPddasnFvuhs33eZnRAeZy4rWyhrdmPZZjYrLKYjkuja/jNK8TRpF9adijtwPMbSfS7mWatkh3B+ApTV5CZWKITSpjbyCopCm6f0RQ7gCyR9w9X8NFlDtidXu/uOLkLlGOYzctR34QcErM3cZdoqTMLBeu0HgeR3EzNd9PB7AJkcfj+ETG80tWUgTVBPH2bk2+oQykqxgYYKblyeO97F5NxN3SNgTVRM39V01QVJcWQHMJIE7ZD4CegRy2LD2EfCWBfeOLAQDdqRk4hGL/SD8KpzuAlBu7Kjjo3MdiPekztC7mwxcj42sJc8kCAGXxs+Q4gCo866NjhFkovftm6rLoi8+t6LbVlT9RLQZFmNz5V73lQXa/XFcmAI8KL9LfxcwmXKFlXxr23MlArcp2rFDF+OqEF/dK5iiKWYL0Gbb1QVRsPP7LnwleJSF9uozJFQlvDyIAJP7huy1XZBe8J5wi2/uZ9lNkC9K1GCFChAjnPM6hXIsLRpE98u3f8eqRyRYKtyZEC0S16rPZu6WzfEysRdFNxnPQJSaryK4ZAgR3nlw2QrTmTJuz/axMkZQgyiWubk/95pWzSraIsSneh/d3XxapsZLnohtfvRyZ4SrGL+zC5PmMwcWuE3DKFBU3tsNLsGQPV1B091glXUum4sZAuEWjy7ggun84GWNiKIWRH2dv4eJ1I8g/OQAaY9ZYuaMWV/rONz5QR7x5bJ/7/fRlkbt0EPnFbOk9fkEFy9aNYOKJQRR7gbhb5DOZYxWsT2/IegQIwCUEoJbdg7uXBh87hsqlg8wlexmTe+J8gvxyIH3SQedRRrIAgOTJOIrnF3DqUB9IZwnpo64FMcZW/E6ZZWHhdc1SkwTT3ewVJjMOqh1uVeqZJF4bX4JiOY7h/2YW2QkAmaMOSBqIdVEkJt1X3zW0EtPMRdt9kPkteWaT0xenkTkBr+TP+GqC9OmaZc2RfWkY3xUZgC5Elum0UHFgl/C+8O+Cx7VUz79uI7MYRuDZN/hm5eRExXMJTq/MoNTF9gROrlzm5dtMjZUY4cYl9NQqMTjInRdDPB8DjQGZk+z4yKUOkhPAZIYgvziBzuNuKq44weSKBIpZlgYMYCxUTvBI5qp17la68WJgz6NoKc4hRbZgXIvXr74Tccf1V2tiT36bjVUI644UlYfI5jv8Zsbmyx6p4pmvvg/A7AwaPDMEd09xl5ccP9K54YJez/br7seJTWl0H6p6VHgVc5LLKqaLEl1oM/1xTK5g2TlSrsup1AmUsowBlz7Ngt4cez7/nlmMMa7ECgPpuvRNnP0HzE79k7t0EGNrY5hZ7I65uITsawn0/oglGebMslgRHlNTvKeTt12BZ776Plz1lgeRO48psslVFKQKOAXCCmG6uYGTORYLog5L88SJJB0nWUyp4zRFKUM8ZUMoy4QRy9eyacwsqeKCSw7jyFgvKi/2YMlVrAhpZ6KIHx4bhHOgAyC1MUmFxalKnYywMr3CjVfFKKgDJMcdJM/UFGK5w3U5VhykDjHXWucxRrzg3xcn+gDwtmHE8xUv/VesUK0rR8NdcNwdmpisIjVWqntGebkameEnF6EUF2zyggrQKyvdu8jZiGLx11KXg8Rk1Ys/JlxmZvZQyavaLV8nz+cJMFf5olcmceKqLOJ5YHqJez29FKlRglIXY3v2HKhtLHfKFNU4wcwi1rb7UNVTpLxPAFj8b8dR6Em0nLV44bvDuRZf+5PItThvKB84BAjZ71XQ7RELsq+Mn2dSiCrGFU93dN4/HPM+4y+oHAvjSkzOSM/74gpv57q7fOMJJvm5QnT2H0TXyq0YvchB1WW+df/NM4ivGTJuWbhh831e3IGvRmMFYOmzM14QfGIdAApU+0sodyWwZHetKrVqIkseGkXu0kHEClWPVMGD7gCzFCoitb0rwSowdwHlJWxSJbEqyl1s0j25iaCSZpNJz96YpxDHL2SWcdeqPiQnKthy+6cxvTqGqZVMvmpHFU7eYfT0XG1FPrWM7a/iDElO+a+kWOXn3Pn1rELqMMJIqZt6q11nUQHDk1lQyijsh44x2mh37zTocBrVJEXfD4BilvXVc4BNvh0jjDSTyLHj5U6gOliAs6yEqaOdcAru8b4ynLEkOg87SLlTUWbYpb+7cWNx8SRa3U88WXvWim5C4+kLBrxYaMcjrOZa6tQMsyzcWNcu93ly9h9EGTUvgFxkE6g9z/xZkjPbyBAXeHK2jviaIS/DDL8m0fLpcbNnpMZKOH0xW2wNPlPLHVnoTdQxVTkqKeLFy4DaFoXYDLvHXYfZ4oJvS8keZkSPUxvYghCAS0AiWPTKJHJrO7HoFcbFz106iI4XD826zqYjssjaByrWYjPhpwzC9qXa4Cm6YeQchiblKSsE3q9tAuIdzq2YePtWzCwiHqmhd99M3SSkosJXt230FNbkMoLUBOqqMQNsA+3keRSVngpIwfEYhItfyM3aiyWWtBH38YxeuQwjbwJAgMUv1iyI1KkZnN6QxcRqVgKGE0oqHcwCKmUplm04gZ4ks+xee24Iy55mk8zYWrbyLmdYe6fEXHhldyP39FAJsYk4Ok4wOjVfZS9+pYRidwyxAsX0YMxLvJwbYrkKQQlAqFeaJj4N5JdXgI4KOv+LCTg1VAE6y0A+jt6XY972h/yqEjqOJJB9nVl1vLAoBy8wWnWXn5lTFCNvAiqZKkiZUeIBgFQJMq4SW7S3nlXKIe+t1LFor7npAWT2nvL2qfFio5yJqCIkyQxF3b5I3lbVh80eShWRBKhVS+CLIgBeIVQAdYpczInJv1egliOUVz/gz1ZimhFiWNoy6hVrLfQm6v7mY2b2nvIWpvydcJ7aMydlXC68M6RF9tnIIosQIUKECGcBzqVciwvGItNl9hDhZ12ZrCzVZme/sUT4WVEA6jKi69LwyPtvTLEDcRyTjOTy9Ti5OYuZgRq1e+mzJY86zDf1ArP3v/GNosOXpUEdoOs49ep+AczlOLOIbbSlMUb+AFimiJn+OJ596L2z6P+qEhk/umM5ylkKpwhkjrulRo5XPYr4zCKCovv1U4fF5BJTbrb2NW5grkow8O9xxPMUw1fU9ks5RYJEDqik2XkA2wPU/4Oql81cTPVU6GZ9OxVg0t34XRwsM5p+tohUqoTOFBvz1MkeYCYGGq8iNeymkuqrIDmQR+L5LnQfrMVRON17ckUCS5485lkLzlN7MPH2rbPij06llvx3eoBghmWXQiVN0XmYoOtY1UuBxfeyyZnoxfuuekaJ5IoEarFMOVuJCFUNOpWVpctIb+MJ0cXaxDRT4jvFLUnVeycnCwaAM5d0IZ5nltfEEE9pxmqt8dI3YgysknLqyr2oYskAkFvbiW/++a+gp6cHaKFFdtE7w1lk//W59rPIFowiE+uRhSFAqBBEYQVVgHJKJ4D5zr/79+9XyiRWmuWQ3TXyXi+VDLoqzvlbtuDILWV0ZBmbq/sfsp5C4kw/fg2qPWhjd2z1SA5OuZ7UkRmueHnmxBefu3q4whI3VYtux5Grl2FiNQElQDVFvThF36tVbz9a7tJBTC6vbSwu9gDpUzVXEFALyGeGyxjezMacWVxlqZgqBIkc8WIhACOn9L+Yq9sLVk0Q776MrUt4bsHi2hn09E7jTQPHMFbs8PoYL6Rx+FQfKhMJxCZYH5VsFc6Mg0U/YJto+eSXu3TQq7GWv2VLXZHO8Qu7UI2zuFnJ5WnEZti1ZoYZk9Jx73kpC6TGmPuWP1tiFhLTIkt+XvnzyV10nODBvx+VUlRBZCfy51aVwSOIu15+rnU1BkXZ+DliTTi+UBPd2VwJyZvZc6sSHmmGE5wAeOQXsSq37E4U35mvj32x9YrsN0Mqsj9rP0W2IF2LYroaHcSXppFYl0o56WTi5/L/eT9cVq7EgNlxBr7yFCsK75ImA1XtNXkFK65+ueIjl69H5sg0Uq9nkV/sxnYGCCppguQ4s0TECsHytQBsM+j46gSSOWZtjVzCXuDEFHDmghgW7WUvN3/Jyx0xL7tHpYtZHlyJTa/MoON5Ici/aSnSI26RyW6CJXtKXl+TK1Oo9GXR8ciziAkFNDtGKMppdg5PL9V1uoxKykFm7ylkBxnZg5QdpgAcID9IUexlbTtOOOgYqWB6ZQb5xTEv+W3a7SO5azeSd2z1thmUO1M4MxPDUycuAHGA+Ai7j0t//ATWLTuJ/EACR06yQFumo4ip0QxoLMFIBYKS4LR3cWVfGEij1ElQ7KpfIBQWAYkcy54Sm2GsRoDFC7mlxiGm0pIJO6q/eRv6/MsoA+D5McQ8k+IG/+kLBmbl3RQhW0EixV58l3TvkErJ6RQw/z++ZsgrlcTH54sk0avBnzOxXAtvW+nLMuKVa1HxvJyVviySu3bjO8K7VenL1lm8FCz5tuy9eKL6MCYmWq8jCLyUmoHOaUcsGItsfHzc20emUhocJrJEq6AbU5ZNpuHLcsvKzSSz6HYRLS85KS7AqlVPXzCAyRUJjK5nE3Z80gF1M0UsfabqlbwXx5Wv64bN9+HMJV3oPljAyHo3E/1yRk3ve42lh+ITgjgZigl2J1ckkMxV6zIxOE/tweRtV6DcQZAaq3rWHS/ayFfMYgHNmf44uo4UUOhNeO0BxiTr+8LTXnqryeUx5AcZZZ1QIDVSa5s5xejUlSRLNQQwF2Yyx8gYiWnqZTaPz1BMDxD0HKhgejCGguvmLF4+hUuWH8cPRwYwNcYstc5Xkyj1ABmXwMr3ZJU7CBb/23GMXL3MKzIKMDZk53Hq1reqfcc0Dsxckkd1MoH0kTjS7l63xDRF98HCrGrFXAmZSBf8GRSrGl9z0wO1WmruMZUXQ95zCMyuGSZCRVJSWfvyGDrPg6pvv8/kdvLWFq74ZGtSrt8n3kduzfF0WuK5/BquJbe0nOxx8W+Es8he/Xxkkc0r5I2/Omq8/PDq/PjNgu7FVI2lyvTOFdD0BQOAwOwzxcjEl1y21OJrhpBb2+ntGcOaIcTzFfR9YTeK72EFMatJYHJtBcmROM5cEGObt6W+5FX2Y9WHcdVbHsTEUArE9SB2Ha5R1JOHRme9+PIkMnrhclSSDnp35zxLDWAphvimVr6ZFWATLmeJjbnJh5MTFTglitMXp5GYri3UShmWC/Do3Vcie5gd7391BqeRxthFFL1DYxjf3wuAWWSlDMHYpWWWINe1vJxsCZXpOGJTMaSHWeJjAJgaZH1PDzJm4dRad28WBQ5N9MIhFM5YbXtIzz52Hs/lBzCXLC/USCij1wNMYZ25gCA9wlJCTbuJ7ssZoDqWBE1WQWMsZgawzbm8oCWHmFpMtHr4pFx+/uX653N/jVL/HUHBieeplI7u/ZIhxtxU7+Jj1YeVfYsyiJ8Bs8vEqFyP8qZr3oeOtckXXNwhLlqquxTXxcvBiFBVX4/QXCwoRRYhQoQIERjOJdbivCoyQshBAOdLh++mlH4yTH86ph+HyeoyWWI2rkebNjb7v4Daxk8OvlrkqY5iCuvIZkweY8OhUfTuPjFrRblz3V3oOcDWnqc2xEBSFcSn4ug6SuuyiKv659fQ8cizKL19q5cVXwx+82KT4jUBtdjMt1zrsrhzE8Y2LUVmmAWE8rds8Ta59j193LO8MsNFjFyW9cgkPIPH1DIH+SVAKVtF7385qLp7gFJj1NuwnDvPTdS7LI1KGkiecTC1JAX0sTHJsTQmz6dAsoqO7gKqLp3zosFh/PDUAMj+bpAyyzQPsIwe8TxFvt/B1AqK7mWMNEAIRTJWwRsXncKhDnZPjmYWo9zJXIHVeC2ZbLmDFbFMTFZRzMa8SSV5mm00L3UyFmbSdfhUUoAz4yB9JIbkOGPT8fvCXYnclXvVWx5E5si0F/MS2YbUde/m1nZ6LMdKV0LrEpfrhvHngLvb+N9A/X5I0cUtnmvrDeHxLJ1bUJRRHrPSl63zdMjPbaUvi8f26T043Mri1y+7UVVeF/FvOT796PhDnOzROpxDG6LPBovsowD+Uvg/p2voB1sGVJA4me1xP9aiHMhWEUbETB9i253r7mIU+Y0xLEEGWYnqLLtUdTKTy9fPKp0h/l3efxAd7su2tLAJo+Nss7NToh6bSxfHk11KPLAtxlaSqE2glVV9cKQq0yL5pZJyvDhbPA+cuSCLrqMUY5uWepT7ckcMi1/IIbe2E/l+x8tQXo0BlRRFx/JJTJ/pRtrd113oJaw+WpkgfZIpvZl1bhD/eALl4Q6Qfua2pA7QeYQgX0iCFJJe0phX/7sLpAwki8Dy79RKukyuSCAzXACrz+ygNLLI6+dMHDh2Xj8S3a5LtMRSXCVzbNbgG2lTY/BievE8UHYZlJwFmpimSI1VUepispMKgVNhcbOuYyw2BwBdX9vDSA77pQnWdb2JdHOsGWILh3UJLH55pi5uWkaNxPAtwTUJV1kBNXafHBuT2YIqEocuf6L8P1ecKgKJ/Dzy65tFye9bbwwryIzOx6oPI75mSLlNBqi9k7ukenSqhanqfby553bMCdpUMQXF2aDIcpTSE83uVPXQ8uOAPcFD10a1AjPF5PwC2wB7GeUgMsAmi+mVGXRtPA3s6a1LUQWgLkjP+1ZNHHLpDNVKmCua5K7dWHZqfV2aHj6WaSHA+3xCuD91JBV3ZSt+LicrfuLJu3HNTQ8A4JRntr9rcgVB11F4NbPKaVawsZh1ECuirsR87w8Jqj/qRiVV27uWzFUxsziGUraKoluWJLMvgcIiysqzxCic40wxpUdZwt/pCwZQ7I551iFXNJyMwgkmmb3upD6Y9OqMAbV0SbHRnJcwOn26jGI3QaHXweBjx+pYi5kj0+y7nijBKcfd41U3gS1huQ45CSQGJCYoElPMEk65zFJOIxcn9/iaIRS7Eii76aWKLsNzdEUC8RmKZI5ibF0afV9gFcCnd25Cqi+LXS5hQSaFqOK9sjLjxwE1o1Z+hnQxX34dqudOVB5+nhbxGRXTYukWquTy9YhjaFY/YhuRzs8TXIkJtvl1yovYubDIziXX4ryyFl3XYhpAAsAhAP8XwGcopWXTeVIf2g3RfsrKTwk1ApPCMsmgYhtW+rI4uj2LShoYfK7kTZ5isUFxz4ytG9R0/SZiinxtqs9FK1NMacRX8CqXE1BfXJFPtmcuSKDUyTYC59ZQdL3OFFl+kKWi6n6dYmqQeJuZew5UkDuPZS1ftLeE8dU1koVTYamsyi6Za+luZjGe/PE0ZgaAOPOsIXWG5TgUlRjAlOxVb3nQq3nlPLUHAFMenLE5MZTy8uqNX9iFxGS1rkYWz6PJr1XcOFvoTaDQ66D7YMHLoA8AM31s3xgAb19cMsf2yFXjLBGtyJaTi1DG1wx5+xR3rrvLc/PmViVQjTGLb8mTx+pcyKc3ZNH/Ym7WAshEjlIxDeV2JmaiXENQbm+C6bk0jVndttH7HnXPuWksYHblCt15HHPBWrzkV34fsWRA1mJxBq/8ZfuxFudbkb0XwB4AowCuBHA/gL+mlL7XcE4KQEo4lAVwxCazhw1ayV40jcfHVLGwcms7cez6ChLZIlIvdHqTr5g/T7e6lV2UpowL8oTRyL1QXZds+fHJXCU7UHNbnd7AfncdLeHElgSqrl6icYpKB0XXAQelLmBmmZsdfzTGstOXgPRITWmVehiLMjVWn/Fi9MplSExWvfyLAJCcZHuxel6brLNuxu7YikWvTHrVhLlsALOQyh1AfgAoDjJ3ISFA7wsJJKapl/iYVyOWwS2ziaEYUmMU027BzdQYK0RayhBMnk+9zCakwophJiZZiRBxYznfoyfmEkydYq5DsaxNJUWQGa6g1OWg57XJumS6fMuFTCnXWU42E7/uc94m6LNmO6ZoSeq8CbLVpOrXNl6uk4ljYmKi5Rui1/9yOEX28hfaT5E5/k2CgRDySUII9fm5EAAopZ+mlD5FKX2JUvp/ALwPwJ2ustLhbgDjws+RZl9DhAgRIkSYOxBC/oEQcoYQ8v/CnN+KGNkfAviST5v9muPPgsk0BGCvps39AD4t/J+FQZkFXeXZkDZUx03n6uTQBZJ5X7x0+9g6B+ljDgp9McTTqMvbpgNfWZZdQgVQ8+PLZTR0MYuwVqlqpc5XvGLcRuc/5jFBHl/qOlrC9GAcxe4Yzv/nnGcF0RjBor3MlTe1CkgOsNT9RXQg1ltEsqOI3OtZVLNuVpHOIk4vTaLnlQTy/ayPckcWvT+quK6/mMe2PPqTaaTGCBIrM+gQNsRya4zvF+oaYO7PSspBqcvBTB9BcgIoubkZnRkH5Q6g50DZS2eUOlXbcAzUYkAZ91gltRT5fgcVdzFd6AXSpwmcCtDz30KKKtfjmRpjrsrCAHMXPvHk3ew7XzPkZYEpuNZecoLVHMseKnlyp8ZKSI3V5wT8rptHkT7/MrOaBUafmCpNtR9M5ZY2Eabk9jq3ne58E+ISw1dl/XNShzy2GNsWr0U1rl+1CdndXq4WtG2bhvZiLf4xgL8C8I4wJ59VmT0IIf8LwEMAFlNKz1ieY500GGh9Fg/dGDxm4SeH6uWubtuI4cvSKPQBff9F6wohAvD8+yI4+08samgTE2vWvfHrT2Zzcuza9ylseNdnUEkxyjkADPzZ0yju3ISZ/riXPYOj1OUgfZqlx5pYy57lSrYCkqwi0VFCtVpzo6VSJUyPd4CWHMQm3SSwkyy2VhisINZbAD3Gsm/E8wTF8wpw4lV0/0cHeg7UFg/xfMXLvce/gxNb0ih3MEp8eqSmZMpuIuLkJMs5CdRYiiPr016BR34tvL5VJcko/QDb4Exj7PxYoYpKiinJQq/jJrCt4jvf+MCs+yjWiwPgxe5yazvr4n6qkiwi5H51WWNU37VqghefcdvYl2rDsk2pIr8Yrup/FXTZRFTHRde4ajP0Dmduci1e+ovhXIsv/dX8uBYJIdsAvItS+rbA586XIiOEbAWwBcC3wSj3WwF8BsAuSqm1VjalqJIhKxM/zIXSs8E1Nz2AyRVsv1F+cQxdR9lEyCv6Zl8ansVQ4yt+mZbMCQDNikUEVYA6MgDvgxMRjlwbRyXD2Bt9L8c8JcDL1QPA9BIHSz77tFdRmxdGPPNGB+UM229VygLlTtYP7SkhfjwFUgVKvUKtr0wFW954AGXqYM/+8wAAznAKlUwVNFlF1w9ryiAxBS9bCCd2AMDEaoLCYBnxM3HEZ4CEOwV0HWPZ7SdXJLzvLbP3FEauXuZl9ShmmWIqdwDTy4BqnCIxRbzinakxikWvTHoVjMV8lXJCZ36P5Ymf31deDZlvGxCJQ7JiCEqWChJXEt9FP2KU36JPlieoZ0R1ruxF8COr2ChC8d7ORYzs0l8Iqcj+OpgiI4RcDeAuAJcBWAbgzZS6Gdxrbd7ptlkK4PsA7qSUPie12YY2VGQbAfwZgAvByBsHAHwFwKcppdZ2t84iM60Eg8DPJWjzggVxjaisJtE1OD2YRO/u2m4FvuqTSR0AvLIdckVd8bwwaLaCF1f8AFvdn7zzSoy/kSmg7h85WPGPxzC2aSkmlztIn2HPbDxPvTRbPNkwAC+NVfLQKEauXublWswvBpb/xwyGL0t76ZxmFgPFnirSy6Ywc7oDHYeY+6/UTVHOVtH5egypMaZkAGDgxRlMDKW88h68vEvuPIKZJVUgWYUzHUPnITZmrMDyNHLSCMC+F16IcWR92rPeKklgchVlCtwBMoeY1ZccB5Y8x/asJXft9hI4y9WXVYxQGZyhJ5cM8nN7B1EuMkznqv7WKRVRuQCzi72Ghen9VMkfZExduzlRZHeEVGRfCqzIdgL4CQAvAPh7SIqMEHIbmKft18HCR78N4FYAF1BKTwrttqHdFFmzYHItmlwPNqvNIMoqSJ8mmJQbuXw9CgPpuhV5ctfuulU3UJvQeJmJntcmvb7o8y97k5kcPwgDmwSu8nUAapqziOq2jRhbV3sJX/iL93hJiSeGmJLoPsg2CIulRQB4Flq5I+bFgAB4pTdSp2ZwcjOPkbH+U+PcnceUJ88S4lRY4mO+Ry09AjhFppzyi4mXcb7cCVQTFPFpgnInRfKMK+PrjFXIWYEAvJyR1XjNbQgApQxTfOUOoHOYevvFqnGC+Az1aPaqqsemDBqA2rXN24oLIPlvsR2AumOqxZrKSjK5LXXQJQ8I8j7y6wbg69Y3WV42Y8rbHTh0z/lcuBbf9I5wiuz7Xw7vWiSEUMxWZM8C2E0pfZf7vwPgMIDPilmcGlFkTWctRogQIUKEtkeWENIt/JiY5FoQQpJgLsfH+TFKadX9f2tzRF3gFpkMPzdJoy6KZhIm5FWoWP9JLPrHXYSqmMPJO6/E4DO5uv1F/Lwgrk7bfT+q/Tg2/YhtANSVdQHqC3BODyYxuZytv2IFZkFlfzSF2GjO2+Sb3LUbo798JTpGKl6NL4DlbOTWG2c+OmXqFQQtdQOLv+/mhRyMYfAxVmfl8JuXY2oVs9QSOQeVFEXmGEHfayWcvpjdW+qwjcrVJKsRxt2FyVy1jlgB1EgXvGAnLzZ6akMCHSxk5RX0BOC1EUkmADzSh2jtATWrO3lo1Lsnmb2nsGvfp7D9uvu9DdmAvgiriU3L29laXqrnwYaoIfbt58aUXZKNhhF0FqFOJj9vg3z+XGyIftPtIS2yhz6k+uheSunHLcaus8gIIcsBHAVwJaX0GaHdAwCuoZRucf9/HMCbAHSC7Su+VWzvO+5CUWRihWgRNm4JHcIQGRpxLdp8XnRTDAH1m1N5TjyO6ZUZFHodxPPUm0h5TIXXpeKwVTC8rSrYLX+mi3P4YYdzK8bu2IozFwHd+5l7Lnuo5JWuETH6y1d6E77I2hNrSY1f2OWRQ3gpmImhGDpGOCMQmB4kyK/Pwzncge6D8MbkZJrMkWkvVdfEEHMJZoaZC3D5N5iyG71yGUqdBLECy7YhKhYAs1zC3/nGB7Dl9k8jfbqMyRVMGcZnKArdxNs8LRaqVGVHAWplRkSyS6HX8aoYyxuv5ewTovLRLUwaiQXrFJbKlRcUQSjvqv9tEMSVGeSa5iJGtuF//14oRfbiVz4MACtRn/e2YMNdCKvIGsWCUWRnW2YP3QotDOTVoRwDkV+qGzbfh+mVGUwujyFWhJc/j7fl7EWvYq2778j0wupIKGKMQCzaGOT65bZXveVBHLvGQTzHFFnPfsbaE2NgALysFdziEuM4nHo+ti6NKZbiELEikBmmmBgiKPUyC6vroIOl381h7692gFSBnh+wwFQyx5RJZu+puuKfpzdk0TFS8ZQbt6aA2l6yriMFz3LiWTzEPrwaV3zfmJQ1QyyAyq+TVx4WyQ5itWa+947Jwe5bNUE8hSrW6JKVl+p7kq1rnbXjt2DRWTO6+l+m80wIEvOWr1Vsw6G6dqDGCFaxf+V4oirmxvueE0X29pCK7G8+HFouhSJLApgG8DYpbvZlAL2U0puDjqHC2ZA0uOWwVU7NJHaEYTTp+vRzcQCz00/tXHcXUmNsAqy4E6inBN1VOrfQZNagOJY8nollqTvPtLJXua+yLw1j3ZFsnWtRnIhVVXmVCZK3bUQyV8XUMjfTfT9FJUnQdQSYdMPDE2+ooJLIov8Fdh4vCCpufBZz8SXXXoGOR55FZdtGL80VwNyezOKqp8gXBtLIjOY8JcblBVgexr6na4te8Xq48gKYoi6jltWdg/StB7l8PcrPv4w4hhDjlPojtSz2XpVt9xz+bOgUmFiWRVw0yTKqzvX7X/ceqghDQS0p8d6YFJbqWeEKK+iCU75vKre6KEczQg5BcDYkDaaUFgkhLwDYDuARwCN7bAfwp80aZ0EqMvkhtn2AdO1sYmpBlCVvF0RJiO1V13fD5vu8TN1AffaFb0mlJjhU9dtU16Fzo4jtbPbo6a5PPs5Xwd8R4hU8C4gqu7o8ud6w+T7W7tAoCr2DWP23ovuPuQS7D7I3doLEEJ+pbTbm+6rK+w+iLMjGrzf7oylUtm1EoTeByYvTXiYQgC0MCr2DdW7QJOCVVOEouoqxe/9B729+bcVVfai4sUxuqT22j02QFcx2BQLwlNl3hONZrK9zH5PL189a7PC24vcrb+FQtReffR1rVf5uxRpgMvxiZbpnUfxb9AbI5/D/dc+xim0pvys6WeXrl88R71EzY+hWaCyzx3OEkCqAz1FKP2c6hRDSBWCdcGg1IWQDgFFK6SGwTExfJoQ8D+A5MPp9J4C/DiidFgtSkUWIECHCuY4GLbLNAVyLl4MltuDgKQS/DOAOSunXCCEDAO4D2xD9IoAbKaXDwaTTY0HHyBola4QJDrcaplWl3I7XpRJjSToihlw+QxeXk1ev8opUXsmayB4qt6Kq3pXNdyCSXXisiWew4Oy+jkeeRXHnJkwPxlGNszhSoYftFVvxj8dmxbEAtp9NTvMVXzOEkauXoZitpb9K5ii6Dxa8WJZ8TSLBhltecmxSvmaxirPs4hTbmeJeqnjN9uvu15YtUW2Y18WCdC48v3iq6n+5XxmqwpWm/nWyqtx/ssyq67FxlevihSpr72t77ml5jGzj/wgXI9vz1fAxsvnCglVktsFf+W/bDb5BGV66McMoS1VmA6De7SYSAVQKibfh4JOWOHnyMXQvuSnOImaZ8Ls+kXQi0sNFxaS6T2IRUlmRidfKKehiPTAeOzp8fRqxPMv4IYJnvxAVGkdssoQzl3RheoBg8Ssl77gYy+P3kZ9f3LnJGx9gFPzMcBnxfKUuQ4e4xUJUfKpNy/yeiCVx5PZyHNGP7CB+tyZChsiWBdSFM3WwfUds+ws6Bv8cCE7VN7XVLeJU580F/X7jz4dUZH8XKbI5h0qR2T6YYX3WQfbA2MgQ9MVVvYSq1bxcq0yedFgVZjYBy3vN+N40sQAkAI8G7hdz4BAzHuisQQ5uqYi1sMTrNE3Goiyi3MWdm7y9XqUscP4/57zsHgAjXJTTBB0jlbqclcWdm7yciDzPIcDqdI2vjmFyqApnyQwqI2yiWPkERfYl5ikZuXoZug8ypvLpi9NITFNU4wR5pk+RPcwKgXYOswTQYlxOtIhUikz+HsU4mbylwnbhJMe7eN9yG9X3ZusdCGJ9yW3EazK19bPIdPEw09g6JQ7olbeN3HPBWrzstnCK7IWvtZ8iO6diZDorLOiKL6i1ZoKqnd+54oQtEj74CyRbmPKLxf/npdlja4YwfuEydB0peJOh7K7iL2/y0Ch2GRQoVwS8PVUU8pTlkGnzhaEUcMsWTzFsv+5+JAVZ5AkjvmaorhQHt2hI33pk9p5CsXspAGB8jYMzl3TBKQPxPFNMfU8f95Tn0Z9bjsTkciZ3DJjpX+a5IPkerbF1DvJriyDxKnqyeZzOucfXxgEMsg3YQn2axDRF7jyCUjdFJc0WjaUux9v4zPaQMQ2X3H9Qm/dQhLzqV7lodfeYH1O5HFXkBg7eXjfB8+fB1EcYlyBvu8O5VUkgUZVnEZ9NUW7xXVGNZ/vO6liJ8rVxqJT7zT23W43VEOaI7HE24JxSZBEiRIhwLqEBOn0Qsse8Y0EqMlPgeS4IHKYVn21wXAcdhfqx6mx6PjC7TpLsvgIAjOa8BLWydST3x2ncuqC7fI/FPh6rPuzFw/hY5f0H66y+GIBqPIvTPxYDwJLjdjzybJ0VKEKO6QDM/XnmgjTLztGV8DYtZw8TlNMEmeGSZ2HFJrMod8RYEt9a9ifkFwPlDmaN5dZ2oppw64R1ACAAnUqg+P1+ZFzPTecwRWqshEJvAonJal3C48xJYNohSEywPpI5oGOEJRN2SqSWqUVjVYtQWbWm+K6JjKA6rrPuTMm3xT518VPdM66yXlTPt6q9jgovtilLHgGdJal6rvy+C5X8orw6S3eHcyseHX+IuxZbB0rZT9Bz2hALJka2DTcjTpi7KEggWfe5SfHI5/DPmxWUtiWSqOJGHDwmINcpEwP0HOX9B3HqN69E17GK586TwZWet8FWwZ7jkAkJ4ucqObmy45hemcHwphhonD2bb/jz495nqiwTsgw3bL4PpzdkUe5g2Tz4JudkjmXziBWoF4Mjl6/36nyd3JhAqZuNmRxjBTercVbXLJ537+EMxdg6VissmWO5GgGWlZ7fp9hoDqNXLqu7pvTpsseeTI2VvMoFqnto++xx2MRkbONCKsXHFxzi337Pu60iCwLde2HTFghWDSPou2z6ruQYZHn/wTnJfn/ZrZ9APBEsRlYuzeCFhz/SErlaiQWjyMTCmoC/Dz4swkwIfsfl4L2N0vSDKrAtW2TianX7dffXTa7yOZy1J9K2TROD7ppk6256ZcYrs8Kp68Wdm5BblUB+MWvXu6/qKR9ba/eqtzyIyeUxVJPw8ip2HWEEjOnBpJd/khNLJm+7AhOrHOSXsbaJCZYBRFR+7Df7X0w9JYJP9GN3sMTei16ppYgS23CIlH8xmXOQGK7q+m0WSH7HRYiTcNh3yxTLk2Fj6fiNZVJMfosh09g2SssPc0H2uPxt4RTZ8/+v/RTZgnIt+rlRglhkYh+6MWzkMPXN/9e5goKMrdv3JU6aqrxxQI3+ntl7CrsUFl/datI9z+Tikq9JbD952xUAgGe++j5sv+5+pMZK3j6tGzbfB9K3HpWUg8xwBYkpXjmZoHf3CYzddsUsooIon2iRZUdzyC9ejkoKntt0ejCJYtZBMlf12JmZyRJw+XokJypY8e0pT+Gc/rUrEZ9hykvMXs+3BnDX62P76okH/DpFBcYnP66wdknbCfg5ZcV9FL8n3fOrcuv5KTFZMfkpOdlFbVs9QTyuks+0uJPHCOpNkc9VET50Ck0eX9WfbUXtuQhnKHEOkT0WlEXmt4+sGSspEWFeaA4//38Y2K5Y+Z4rkZ7PFYRoYXBKt/iS8zbiZ6rrkBWm6JoCalWSeYZ+oJadPvvSMKYvGPBccUB91WedFSRvZp54+1Y4JYqJIe7SY1ntc6sSSEyxMXteY9R6rqDEUjBVNxWV6G6Vtx+I1+y3LcNPeeiyp9s+myqLTPVMqPaiid8voLekVe463l4nk86trCv7EuRdVC02gxbytKHl6yj3HEG9KHNhkW16cziLbPc/RBZZhAgRIkQ4G9CYRdZWWJCKTJeg1Da2BJj3ivlZdjrIq3hbmeQxdStBPzeqyk0kQjx+zU0PsI26Cjdi/pYt6Hjk2TqXocptBczOSiFiYiiGYg/QeZTUHefWWObINADgzCVdmFlEkJhMYGJoGdzQmWeZ8f45aUSU5ZqbHkCX279TosjsPYV4vs9zLVa6EnCe2oNvVetJJ/w+Z1wrj5NdeFopOYAvyuHn2lO5ZeVxdd+rCrI1pTtHleYpaDxN/ly0jm1dizr5RbefbSxaPM9z0WqSYev69dsXBtRnwRH7kJNY28gXXzOEr+25x3htzcDZkP1+rrCgXIsqsocOupiV6uHze6F5ez/XXlhfuW4SDNOXKfOCGMfh2TgAzHI5qsaW3WK6e8GPV7dtxKkNaVRjtWrK6TMUXUcKmBiqr6pejRMvJ2I8zzLVA/CUqVhIE2CuRZ5nkrMIgVpdL7FEClBjGvplszBdr+pe6s4V+za1CQrVsyt/n/JkbuMel59bsfac7fti427nCLJAlN9hjiDuRRPLVjW26fpsQxpz4Vrc/HO/G8q1+Nw/3tMSuVqJBWmR6eIB4jHd5OFn1chQlRVRwWSp+UEVaJb7tpk8TGQBPumJmT34cTmnnhwUB2az2WQ5ZDhP7cGijk2Y6Y97bMJyRwyxyRKccgrTAwR9rzGraXx1Ao5LoR9/A8VMH9vw1ZO6Apnhohff45kMuRIr7z+I6qqNiLk6K3loVKms4giXqFi8fjnDhN93FER52RAibBSCqHh0CzA/xcTv9S7pOuXzdPdF7Ecnp3h9vI8gCzmdElJdk833ourPtGCRx2zWQiWCHgvKIlNlvzdNKLYJgnUIa2HZ9qd7SWxdNLLLiWc0t2VbqfoWoXNRmTZtq/rL38KqnVdSBNkfTWHkMrYHLMGIfyh3MEuMxoBCL1BxF5mZE8w6K3U5SJ8ue1sH4muGMH3BwKx9WqJlaWuxmyYqUx+2WyrOFtjUkxMR5L7YejU4ZMvGpHj8ZORtZSvS5h1SeUJsxrZpu2PNu/H4gc8CLbTItvxsOIvs2X9qP4tsQSsyGbZ+f1s0MkH5vUwml5XfC+63atW5SuTjottOZLMBs+nmtmOJfU9fMIDM3lOzlMs1Nz2AYncM+X7GNowV2cbjzHAZY+sSKLvvJs88z7PKc3chp8Zz16KYEFmVSNkmRqK6Lp37SqXI5b7DLFJUCzBVPyYrWbXI0WW4t5qQNeObEgeb3HCqPmwXWiZlZ3pOm5kEnPcHzI6ZivdqLlyLW34mpCL753sAYC+AtqHfL0jXYoQIESKc65jDwprzjgVtkYV1QwD6YL7pfCDcipfDNFZQ14+frCprQl61iu1sYjAmV4wuhgLUs8zEmOPxG1km+p4DzPLK7D3lFcsEMKuWl8heFOuCyQUiVRamnyuxEYvAVLtLdW9sxpD/t7UqTNaK6HpVFRQVZZQt8kY8HX5xOfHatl93vyeXjctR5yrUjR1WRj+PiHxsLuqRXfHT94WyyP7zXz7aErlaiQWjyGxyLQL29ZJM59vGWRqBahy/yUqliMIqctMEoHPTmOJotopcdIsVd27yPpvpj6Pv6eN16bK4EhOLeAK1Mi5cgfm54lTX73c8CML0YXLFqb5n/ndYeVTuMD/mn26RIH6Pfs9rs94h1eKEHxfh57q1jX/yrDI216e6zrlwLW7dGU6RPbOr/RSZ49+kPfDo+EN4rGpmCO1wblU+eCorgbeXoWNh+YH3tcO5Vdmvahz5evzKs8ufiROh35iqCVJ3jfy4/Dk/R/yR+75h832z9muJ2LXvU94kkdl7Cpm9p5DctRvp07UiX8lDo16Gj/L+g4iN5upyGe7a96k69uWufZ+qI11wSrrqmjh094s/I/KzYjpHldJL1141kcpWpHx/5fa2Y4nHxXvE75O8R0x+jjilXzVh8+9GHoufr2MOm2QXKynIsjxWfdi7BvG7Ud0ruW9RFrmtak7g76a4t0y+Pt7XvIKG/GlDLBiLTK4QzaGaoIPCdL6f60JsZ/pM7sPkXgnSt23/clve3m8823ursyZ07XgaLQAe01K10ZX3KbrC+ISnYmiarkW8HpObK4jLWTzPzxPAlZXcv7yROewEGfb55J8D9sSPoFainzxBZFc9n7bvUhDZdC5EG/flXLgWt94Y0iL71/azyBakIhOhYz/p3CvNKtNuUw49rL/eJFsrzrNl9vkpSZM8IsK6hsV+xD1xNrLolIppo2wQBHX7NjKR+8khKxrdxG+7+Aorox/zVXfPVaxMG4R5bht5lk33cC4U2ZU/FU6RPf3N9lNkEWsxQoQIERYiqpT9BD2nDbFgFNnNPbfj2/SRWcdVpRh0qyRT/Ew+poo76eJZfDxdTMN0TIYou9/16MDbqjbtqlbHtuU0/GTQycmPcbYhb6tqY3Iv2loHwOxVvSlDiyyLn1s27Hcr9i1bTX7n21jNotyqHIFy3EoVKxJjxKbn32TZ8f9Vz5WNq1ouKSMfU0HMw6lzLYr3RPwegpZr0cUj5xxRGZf2QdAyLkHdM0FcMfJ5quN+0Lk5bGNLgJkabSO7Ti5xfN3kZDoujmWSg38mxrp0MpkmW5Xc8nFy+fo65p2K+aa7FzbxIr92QaBzzwVl0crn2DwnJncch42yBfTFOU2boG3jUSr5ZXnDXrOq/yAZXMQx54K1+BPX34t4PKBrsTyD/3j8Yy2Rq5VYsIqMwzSR2VgQ8nny56ZVqDxuEMupUZp/2NpWNrE9UaawdZr8YBOfEWEzjh9RQzdmszI/2MSVgsbOZDkBfTZ3m8WQ7nPdQk6nnHT79GR5w+59kz+3ocKL16WrWiBC926LMpnmCFW1Ad52ThTZ9o+HU2RPfLwlcrUSC0aRbcPNStcioN4jA9itqE0bh4MqxqCwtZhaMbbYb5D+dZNBozLqJisba8Hve9Ipapvr91uw+FmqQca0ld1UsJKPIyog+R7xtrbPPqBfJPhllg+DVr5/KoUlj+XHIOYwfd9fH/tipMiaiAUTI3t0/CHlcdsJRNXWxrXXrJczLJphWerg54oxycLb6+RTTdg2k758Parvju8TU1mNKlnEMVXfv0l5qPrzqwsmj8kh738Kys7zU3KiG1UVa5Shc5dx2cX+dBO7OI7NNQT1Wqhidn7vp8mFqLtW3fjy9Zm+77nGuVSPbMEosggRIkSIIOAcqhC9YFyLNvvIdFBZEoB93AWwc1sGdX80y4USNqYUBn5j+cVxxGMmV53qXJVrTXW/5LyVQa3aMDGZMDBZGBw6i8EUR7MpgMrb6q4xTKo3Pw+IHxp59mWLTRfzk8fyKzwqP3M6b8J8xMh+ctvHQrkW//2pe1siVyvRMkVGCPkwgJsAbABQpJT2KtqsAvB5ANcCmATwZQB3U0rLclvDONZlXGT4TRR+yk0+HiSmEuRlVr0M4phyYl/beE6QydaP5mw7ydjIaDtZ2UyctnEmlUxBYoR+E55NJWbdmLYxPz+FZnM/dDEiuT8/l7Mu7qdqK8O0ULB5twB1sm4/N7ftOKoxTc+J/N3vXHcXvrbnntYrsqtDKrJ/az9F1krXYhLAwwCeAfBL8oeEkBiAbwA4AeBKAMsAPASgBOBDQQe7ued2q6TBQO0h1cVLeBs/BF0Ny/3bTtimeEyQFartfVHBz6rVTWTyZ7qJRPzMz+KxWQzovj8ev5InPdVq2iZGJssiT1r8uG0hU9WEqFIGouzymEEykpisPfFznULTXbcpTuj37JusRVVfPFanUyJALVanUtyqPXVB303TAkR+jm3ik80AoRQkoKEStP1ZA0ppS38A3AFgTHF8J4AKgEHh2K8DGAeQDNB/NwA6Pj5Orydvo9eTt1GOG9e+n+ogthP/toFfey6H3E53PIgcqj51bcTfNueFgel6TOPJMoaRy+Z7kP/3uyfy8Ubvm6m9LIssn01//Bk3tVd9duPa99e9H6p3xU928fMdm+6t+3zHpnvpjk33+j4fpueXy+j3zgSRU3Xc9LdORvm47nvQjT8+Ps4jWN20+XNuNwB69VUfpddt+/1AP1df9VEu12sAXgXwzmbL14qf+SR7bAXwMqV0WDj2TTBX448B+J7qJEJICkBKOJRVtYsQIUKECKHRVoU159Mi+wsA35SOZcBWAzsN/X0ciuID4+Pjdaug+UAzxg2zgtUdb5YVprNQGrVOridvM1rNYjt5XNVq2c/i1clgWnn7WbOyZWNzvmksP8jXy8fmcnALRieHrdfCdF+CeCRU/cvWm18/fmPqLE65D9tz/T5XXZdJTtV3sg03t94i+4l76HXX/F6gn6t/4p6WydXKn0BkD0LIJwF80KfZRZTS14Rz7gDwR1QiexBC/gLA+ZTSnxKOZQBMAfhpSukujQwqi+yIXFgzSGBXBb+gsmoM05gcQWJaNgQLVZ8mgkEj5WBMMqjkEMc0ZRmxIQE0wnDz2/wrniNmpAhC2mkENvdQHM9vf5nt/VSNKR9XpTsL0r/fOxjmmTP1BWAW+Uklhx9xRte36hz5mJxaTRXfnIsN0ddceU8ossd3nv7dlsjVSgRVZAMA+n2a7aeUFoVz7oBakd0H4OcopRuEY6sB7AewkVKqdC0qZNLmWuSlPMIwCE3sLV2Auxkwvdi2yUtbibBKuZGxdJOnTa0xU3YKuT/5Mw7OgFO1141re29s8gv6Ta62z4tOtkao9CJMSst20WcaT16Y+DF1m8GAtSEWyX3YKPq5oN9fs/Uj4RTZM59oiVytRMv3kRkU2U4A/wxgGaX0pHvsVwF8CsASSmnBsn8t/V7eL+QH21Wqru+wFs1cKyNxbMBswTajb/5/0ImLw0++RizJZlkDQdqJE57ffrRG5NApLV22DZVFGlQ+28KjOiUtH9NdRxjomIVhqP6qz1WKTLfw2LHm3Xj8wGeBFiqybVvCKbKnno0UWa1jtkesD8DPAbgLwE+6H+2jlE669PsXARwD8AEASwF8BcAXKKXW9HtdrkXVA+r3wtu8MKZVvh9V2bSXSG4rIkxV4rArVb8JXmc1cIRVVuK5tnuudJ/ZTOy2iiyMJeF3js3zZut+E/viqbl4KRwA2uS9fhaVzfMjKz75XL/zdddmax2p+uKf27ynKqi8ACLk702VEEHnxRH7nguLbNvmD4dTZM/9XkvkaiVayVq8D8A7hP+5q/BaAE9RSiuEkJ8BYyk+AxYb+zIAexMqQoQIESKc81gwKapUFpm8aqr0Zb3Vqrzi8rNQdO1UfbTKXRi2X9vig7bjNtvVYwORdNAqV6zct+6+ibI0apEEKdqo6083po21Y3M/VZkpTN+FbZ9y3NHWCrUZS5WKS2UFm2r36eQ2pT/jxzl0n5dpCU/hUaCVFtmmkBbZ7vazyOadNtnoD4QN0SroqMa2NPJGKOut2DzrN57fZl7VJlzbMeR2jWw3CLOJVYa8WdZ286tJDr8NsbYbc/1o+UGh237AxzK1F4/xeybLZ7oPNv373SPdWLq+TdsTdNssxE3YfvLaIOz7qNoGMR/0+2sv/xDdccV9gX6uvfxDbUm/n3cBmvWlbcPN3kMSdgKxnTxVbZuhtBrZ8+KXAcEEeZJpREE10o9pYg3Sp83eML9jYRS8rr3NXi3TMdvPZOgyd+iuVVYQfvdJl7nDT36/d8j2fsv9BHl/VIpaVPCqvWKqPoJAHHMuMntce9nddMeWewP9XHvZ3W2pyBaUa9E21yKgdgvYsByDuDxEWYK4IVTuTFUQOgijSvWZiTkmy6Q7PwwRQrwOv8C9Sgbbe9sst53pWnRuMZ3stv3K5/pdo0oWkQDyrec+Gpjd6Fdp2vY9CFopIGj/pvselrykupeqflSEDptnei5ci9duvBvxWEDXYmUG395zf0vkaiUWjCIbHx/HW3tZbuIgbC/V32IfpnODKqegk4BJ5magEYVoe291x/yuxaYKbyOKx7ZtEFad6jOb+2ej+FTM1SBsVpvnz4ZVC9Rnlrd9hsQ2JuXRqvir7Ri2ixCbPkxzylywFq/78d8Jpcie/N4nAWAvgCqAz1FKP9dM+VqBqLBmhAgRIixEUABBDZVa87bKtbigFJm8QtK56jg4K008z8b64H+rXH7iZypZVCUjgiLoCjaoe6WR47pxbGQVPze5osJYVbZtZXnFz/lxk2Wh+95NY9rc4137PuWlPvJzc5lcZWKWEhE3bL4PVDjOx9+57i7vtyiL7npt7kGQe2TqN+yYYd4DFTuVf2bqk39m8wxGaADzHaRrVmBTx1oMiiDBa1MfzZBDd0wMytuwGf3+9jsWlvFlQxpo9F6HlUkHGzaf/DsosUTVj5/cfsfF50FFplARUEzMOp7Y15ZcIhInxKTAYa8/6HMRhDSj+tzEiAz6rqmeCbmPuSB7XPemD9IbNn400M91b/pgRPaYD6hSVAX1swexagC2wgqa/mouEDYgL54fJu7EYRNTUlmTQckRjcQZVTLr+vaLhcrnccul2fk3VWMBQHXbRjhP7fHklWUBZidMNrWV24t96K5JTpCrktXvHvolQVb1CcwuIOr33KksVVUladOYvIinLLvf3jKxj8eqc5PZ47r1H0Q8lvJtL6JcKeDJl/+gJXK1EgtSkdnAhqkVBLoXVsfa8iOYhCFZNAp5AjRNXvT5l62qOMsvvi4QLh7THQ9KGLFtY3Oen7L1+76a+b35LR50Y6o2Icv92rAcxTGCfhakTVCYFkm2JA+Ty1yESSnbpMWaC0W2/ZIPhFJkT7zyQEvkaiUWjCITM3v4PZS2L2CYl01X9iLsZGrbh2n1aTOOSakGlTnIBGc61mhGEj85OUyrcp18QGNMPRFhVvW8b50VHuQZMClpHVtSN1nbvEM2mUHEWHIzyg7ZLgxNcUbTcfFz0cLULfauJbe0nH6//cfuCqfIfvCplsjVSiwoskeECBEiRHBBaQjWYnsaNgvGIlPVIwPU7jpVHja5rYyglkqQVbZuvKBuEN2Ycv0meeXcDNlsVrw2eep0/YV1CwWVUXdcXn0HtVhv2HwfYqM5APYWpu66dO5Z+ftU3UPu6vWzGMX/dbKLlpNpX5nOvS5fT3zNECp92bqClBzNcFU24q4P4v63wZy4Fi9+fziL7NUHWyJXSzHfbJNmMXR0rEW5rLqJWdZobrygKXLC9B/2M5vPbViLfv2oyrqbzgtyH0xtOQvPJnef6Xr8WKsmNluYa7S5JtU5Yfv0g46xJ/dte4/85FGxKf3a2TKLbd9n+TsMw1BU3RfT8zAXrMXtF72P/tQlHwr0s/2i97Ula3HBuxZlNpVqhW3aIxIk3mDyq8t9hImdmdqaLKSgsgf5TG7HrT+ZiWZaCdvGwkxy8HgE71e3XyqMZaWLRcnn6/ryu7c2xBYVVIQGsU9bq1n8TB5ftqTia4YCP7fi9yJC9Vw0Eg9V9W/zbNncc/Eec6ameK7qf/49cHap+P1MTMyBsVMFQEKc04ZYMK5FVRkXoPHNlir4sRuDTpY2L5vf9ZhcQ7qJ1zSuretPlku3LaGZrlWbtkGC+yrXp2kswJ5I5EeksXGhhiUv+Z3bDDTq1g3Sp+7+ycxYm/HkhQlX2LoFqOpd4exdUSbb65wLssf1b3xvKNfi4z/8dEvkaiUWjCIz0e91E7aJ5WWzelUpLNsH2Y/FFmZl2uxJy09G2eLhL7yJtenHrAsSr2rV5GwaW/w/yDPj1z9gN3Gbjquec10sTBdP1SkLDvG6Vdery/9o+/2pFl2mBMYqBPGk6BZ5XEHS519WWuRc8cn30fbdnYsY2fVveE84Rfbfn2mJXK3EgnctRogQIcI5iSoFSEBDpdqehs2CscjkMi4yQ47Dxt2gamdihvn1q0MQy6tRV5t4vFGr0WZ1rbpfcjs/OWxjZ0HdSEFdnCKCupDEtkHdcH73TPe3rUymvnXtTfIHeRdMz76u/I6f+9z2mdYlKFDJ7hcmMFmw4ncoZyH5+tgXW2+RrfmtcBbZ/j9uiVwtxXyzTZrF0BkfH6/LH2fDRAzD/hJz2dme02yIbDYdm8sml598n8S2uqKM4v86hpfMFNXJoWOfmZhspva2DMsg+f1EJmYj7EQRfgVEVbC9p7YwMe1Uz5ANg9LmmVNBlfdRHkMcS/fe8grRJvj1IY8p/y32If+taqvrey5Yi9ev+S164xs+EOjn+jW/1ZasxXkXoFlfmki/1z2oOiXULAp4mBe4kb5sKOW2VGjdi62jY5v6UU3UzbjHOvk45MlWTHyruycqpew32YVRaLbXb0v7DnLc9hmw6ddGqTRSrVwnn2pc3Tk6BW0aT3U9fsmX/ej9ujFvXPv+OVJk76Y3rrsr0M/1a97dlopswbgWVWQPFSmjUfecDmKQuxGXj59MgN6NEbY/3WZVG9enLeNSR/oQZbch2NjAr7pxUFKP3Ic4jpy7sFEiSjOeFz9XnI27NIirTuzD77jfOa1mYOrmBJU7NwhZxPROqvqZE7LH6jsRdwK6FqsFPH7gs0CbFdZc0IpMhs2LYuP/N01wJp+6OMEGpXqbGH6cBqxippkymNiyv3QymeRWxRKDxoY4WsFODHodNp/73a8wcULVeH6y8+9dRUu3hRxLEsfUJR+2ZSaq2quugUPFjjX1EaRytnye7v2Ur98mvme6vjlRZOe/K5wie/1PWyJXKxGxFiNEiBBhIYJW2U/Qc9oR8+3bbJY/2FRY0yZOIPrFVb5xv/5kqFIm+fnsg8Si/GAT7zJB9v+LxAdd/+Jx2wC+aewg8trGCP2gIjWYyA4meXSEAJtzTOfJffu1F9vp4oVBiA+mGJRNPM4vzqQ6Z8eme5XPk0l+Xewr6DNlun6RYGLzTHNsw82tj5Gd9xv0xvN/O9DP9ef9RhQjmw+IrsXbNv4ugHBpboLETkznAM1xhXHXDmCX7LcRSr3oRrLx7wcZo9HzTcf93Ja2rmLVcfkzW7egTWxI7F9204W5FpMstnR6WTbxM53spusXkwnLYzQaP2xGXJgj6HYD0W1vs0VAhZ3r7sLX9tzTetfieb8RzrV4+PMtkauVWFCKLGhhTRnyA6siQQQhEjQKXUDa9twwxAk/AkgY+MVCVNWLwywkTO3EvnWfi1DF+Ex9AMHqdKmuIWhsJ8yEHnTBY3vv/JSsTfZ73T2X+7e97rCLKAB1mTtsvhNT3GzeyB4rfj2cIjv6f1oiVytxzioyW5hWuqoXrVnKTJcCio8h/q86N6gS8ptsbPto1GoIsrK1lUmsemzTHtCTejhMpIcwMopjqvqzvXcA6hIm+z2XthaEzmoMU/w0qAK2URK6NvJYulygYl9yvyJk5aazZPmYuud5ThTZ8l8Lp8iO/XlL5GolIrJHhAgRIixEUIQorNkSSVqOBaXI/OI7NqtSG1dhsy0GuW/V3yLEMvAqhLWqdGVPbCymMK5Mk2Ubxi0qthH78LPE+GpeLM/Bz+fjqca0dSXJ/8vWg03MU2UZcvm4Bab7nkzymeQMEu8Trw2wK5uigq3ccl9+zy7/m2erV7UzWbxcHpPLVfwuZMjtyrQ0q03TQaMK0W0DXRkXDtvgLqCO19hOwkHcM6b2JtcSMDt2FVSh2rixdPIDszOr2058uuC4eJ4ol20cR1dLTiWPzbUH2eCtGkMeWx5PPGaCLm4XRpGrZLZ1U/uNYxpD169JFtkd5yeb35hBrk/1PNm4dAHM2stpagvMkWtxyS8j7iQDnVuuFvH4yS+0RK5WYsEosvHxcby195cA6IkKYSeBViLIpK17Yf1iCBx+q++g1xxGdtWxZt1zv36aMabufsr9c/AFTKMLENU5Nt6DoIrZVg4dVBZ2UGUix99ka1N1XFRCJnKGn5L0W1TpFiSmhZ5qzDmpRzbwS+EU2akvtkSuVsKZbwFaAZVpD5gnOP6jcyPpwM8L287PMlO1k2VUucXktjoXHgev/Ksb308+m3Pl+yyO7ecuVfUjQ75O1T3UuaxsvkPeh6ov3Zh8YpMVie2kbrLsbJ7VXfs+NatgpPy36b6owL8rleuT/82/U90ixjQGP8ZlF4/tcG71juueGd094crG5lp5H/IY8j3fue4ubyFpk4GEH3t0/CGljBHCYUFZZJy1GGa13aiFEma1rGtr2tMl/i+Pa3KtiJBlCnKtJmUY5Hzd2OLEqlphyyt2VQouUb6w1ynLLPbBUz+Z3GK66/W7J6Z+bF2Lcr9+4+vOUZ2rKpyq6sPWAtdZQDrFYvqOba7XVm6TxaZ7v0zXI2NOLLLFvxjOIhv5q5bI1UosKLJHhAgRIkRwUeVJOoKe04aY79QizUrHYkpRZYNmpejx60N1vk3pEL86S6Zxw6a6kstZmGSWP1f1w/vi/ZnSEwUpwWFzDarjNmmLbNMc2aTiUpUIMZ3jl6IqTPov0/fVSGovGwRJE+X3HMnYseleq+9UTLNm6tv0HQS5N6qxblz7/jlJUbV90TvoT/X/SqCf7YveEaWomg/YbIhWuTJM7hL5c1NfjRAUTOfbuCjEzZ22LrTt192PJ568e9a1mGTUVdS1ITvoPuP92mayCOJC9ftuwnxvfm5e3X1qBmR5eTxUZsmZ7ksY8kPYCg06hqpI0gCgdaGbrj+ou9TGlS32p5srbP823Xv+f3zN0JykqNreezviJKBrkRbxxNhDLZGrlWgZ2YMQ8mFCyNOEkGlCyJimDVX8/HyY8W7uud37WwyS63ztIvhLp/Ob28A2gM2xc91dxiC4SNKQZePXx+M0MsQXTM5MkDw0OmsMEx6rPqwlz4iyyOPK4Nk1xH7lgL18rqpvXf/xNUNW18P7Ul2HCjvX3eUpKVFWeSx+PTro+rd5VuTP6PMvK6neXCbTfeLXI54j/hYhL+5E2eQxxElcR2zhJA0up27vl/i3Lv6lendEmeTnXjxXbit/j2KMVvxbJK9Ut22cNYaosEwKsxWLHSX4PrKgP22IVsbIkgAeBvAMgF8ytPsFAP8q/D/WjMF1L6ifJWFjifHJQNfWZjJVPcxBmHvyWLqXprz/YJ3sqjyRtjKL5+nuoa4fmRzBodoYrINqtc8hTop84rGV3/Rd8n5t7puuH52yku8XvzaVglL9Lfaje4Ztr1PVt+oagrwntpDlVeU3NFnZKmVnWpyKbfkCS2U1mfrgXg0TTIvot274iO/5DaNaBci5Ucal5a5FQsgdAP6IUtqr+IwCeDOlip3M9v17cDXxjwAADbNJREFUG6LjJAEgOJsuqBtK5+YSXwJdDr4wL7qNnEHltpXFdkzbeyhPFDaFCG3cdjrl1Kj8qkmSo1Hlb2pnyq4uj29yD+og7nvSuSRV182PhSna6efmszlPPEe3qOGbk1WFQWV3tikpsLgHkEPHoBXPkYtzit8px5y4FrP/K5xrMfe3LZGrlTgb9pF9jhAyQgh5jhDyi4QQYmpMCEkRQrr5D4DsHMkZIUKECO2DyLU4Z/gogCcBTAO4AcCfAegC8CeGc+4G8DH54KPjD3mZPTj89rzIKz15BadaeTXinhE/N63mVCvsGzbfV+d2sekvqGy6c2z71lmqKvD7bErbpbMUVO11Fom4mubkGNkKNEHe/Ct+N/J9MZEjxBW5ijjD2/D+dM+tzlWm6083pt8Gbb8xVdaYn6vaNIZ4vmx96yxi3Xcoflc6C5ZDzGIvy6Paoyj/L/cvu/JV7s4dzq11Mf1WgVaroAFdi/RccC0SQj4J4IM+zS6ilL4mnHMHNK5FRf/3AfgFSul5hjYpAGJtgiyAI9evvhOP7VfrP5PrhP/tx6DTvaSyi8Y0kQdxDcpjhzkvDHRuHJU8fq6VRuXwu2bbmBRvI7M8xc9Mffu5TeVxVMeDfodBrl/nHguyAFPJDeiZhSZXpx90ZVCCsFhFWcPcX5NswGyii2quEI/zz2zc2zucW/H1sS+23LV4XcdtoVyLT+a/1hK5WomgFtkfAviST5v94UQBADwL4B5CSIpSWlA1cI97n3FP5Ndf/IQ2N5uNMuEPrvggixaSXK1ZhtyvzYq0VZDltqFQB5VXF5fxYzia4jCm++cXl1St9uXxRCvCpKB1n/tdj3hMPm5D5BEXAflbtijHE2F6xkXGnfi57juQ5fSLBanST9ksGFVy8+MmS1W3RUa0jP0WJ6Yaf6rrVFl2skLzg4qdDGBOLDJUKUCi7PfNGSCYRfZhAO+jlPYF6F+7j8x2lSa79GxgmpQbUR66VZypiGMQ609exfPzTJOkLVT3UXYX+U02JtlV7YLKarpXNhOzTsYwFoHOklJN2qIcOrlM1pFNYmmdC49cvh6x0Zz3v6ofP0vc5t6aiD+m6tt+Y8mfibC1yP3am65JpTznIvv9dclbPQKcLcq0hCeLD7dELhMIIT8DZig5AP6AUvqFQB20aqc1gFUANoDFwXLu3xsAdLmf/yyAXwZwCYB1AH4DwBSAe8PsYhcze9hkDbhx7fuN2RFMmRfkvmx3+gfJEBA0s4EtwmT5aCQ7CD/f5n76ZWTQyRVEDr/vwC+bhkke2+N+Y5rul/hdyBlX5KwWYbJ28MwrcgYS2/ui+twE1XtoO6bfc2XK1sEhZsyRj+uyzKj+t3kOxXt7/eo7W57Z47rkrfSG1P8M9HNd8tY5z+wB5hn8IYAVYByJvQD6g/TRSrLHfQDeIfz/Pff3tQCeAlAC8E4AnwFAAOwD8F4Af9lCmSJEiBDhnACtUtCArkU6P67FzQB+QCk9CgCEkF1g5L+v2nawIFNUBXU5mVwHQd2TQc5R+fZ1cRdAXWfNdK1BiRcmV5aq/+3X3Q/nqT11sqn2P6muTdenidmnIhc0SqJQxT7E/k1yiXGSSl9Wy+QL4/4K4vKydXep7qEIm2dR/n7FvVE2rktVH35xPD800j6se9pmnjARQ+Yi+/21sbeEci1+u/L3geQihFwN4C4AlwFYBsXeYELIO902SwF8H8CdlNLn3M/eBmAbpfRd7v93AaCU0gdt5Z5v+n3T8NYNH0HcYWRGm82aqsC++ILbMKJMcSu5H51MKuVhCjrLspkmYFOcRZaB9xWEePHEk3fXBeqDTCi6djaLAd01+PWt+0x3D0UZVJN03f3ap5dVjnnF1wzNStmluh6TrKbr4edzwoeqX1kB6ZSJHMcz0fj94kpBYrlyH6p+gPrUZypyiOraxe+NKxqbmLVKDnkOkeXVKcpHxx/iMbKWYQ4tsk4w5fRXAP5e/pAQchuATwP4dTBC328D+CYh5AJK6ckwA84aY6FYZIcPH55F9ri55/a6AnacKfTo+EN1rCHeRm7vh6DtRfAUNV9/8ROzGEymPlVy+0E+h8st3g/VOeJxLm/5wCHEV69C+cChWeeJ5zQi56PjD9Wl8Pn6i5/wZOB/m2QU76nNtelk4O3kcVV9iPdUddx0zbp+OOR+ZRlV34fNd6ySg7cnGy/GI9/+Hd92KpnE+9XIfYmvXgXA//u0gc3zIN/zt274CMoHDtW1VT3zOpiesTJK+C7+BWihRXYVfhpxBLTIanKtBOM2cBSohkkujT0rWxMh5FkAuwWLywFwGMBnKaWfJIRcCeAuSumb3c//CMBzlNL/ayv3QlBkKwAcmW85IkSIECEEVvLYULNACEkDOADmxguDSTDShYh7KaUftxi7TpERQpJgCS/eJim3LwPopZTeTAiJA/gvANsAjAN4AcCVlNLTtgIvBNfiMcxePcjIgik7v3ZnI9pZdqC95Y9knx+0s+yAvfxZsPmrqaCUzhBCVoMlbm8WfK0xDRYDiAEYlo4PA7gQACilZULI+wB8G4x+/0AQJQYsAEVGmUlpXNEI6RtzzTbjW412lh1ob/kj2ecH7Sw7EEj+ll0bpXQGwEyr+m82KKX/COAfw55/NiQNjhAhQoQICxMjACoABqXjgwBONGuQSJFFiBAhQoSWgFJaBIt5befHXLLHdrBalU1B27sWLVEAcC/C+3nnE+0sO9De8keyzw/aWXag/eUPBEJIF1h2Jo7VhJANAEYppYfAqPdfJoQ8D+A5MPp9J4C/bpoM7c5ajBAhQoQI8wdCyDYwooaML1NK73DbvAu1DdEvAng3pfTZpskQKbIIESJEiNDOiGJkESJEiBChrREpsggRIkSI0NaIFFmECBEiRGhrLHhFRgj5MCHkaULINCFkTNOGKn5+fo5FVcllI/sqQsg33DYnCSGfclO+nHUghBxU3OfZCf3OAhBC3unKO0MIeZYQsnm+ZbIBIeTjinv82nzLpQIh5GpCyD8RQo65ct4ifU4IIfcRQo4TQvKEkMcJIW+YJ3HrYCH7lxTfw7/Ok7gLHgtekYGlaXkYwOd92v0CWAkC/vNIa8WyglF2QkgMwDfcdleC1X+7A6wW3NmKj6L+Pn92fsWZDSFb970ANoJl9v4mIWTJvApmjx+g/h5fNb/iaMGzpr9T8/kHALwbLGv6FrDCu990cwnON/xkB4B/Rf338D/mQK5zEmflyr2ZoJR+DAAIIXf4NB2jlDZtp3kzYCH7DQAuBnA9pXQYwIuEkHsA/AEh5OPuZsSzDbmz7T4r8F4Af0kp/WsAIIT8OoCbAPwigE/Op2CWKLfBPQaldBeAXUBdWie4/xOw/UafoJQ+6h67HSxH3y0A/m4ORZ0Fk+wCCu3wPSwEnAsWmS0+RwgZIYQ8Rwj5RWJ4Os8ibAXwsqvEOL4JVur8x+ZHJF/8DiHkNCHke4SQu842N6ibrfsyAI/zY5TSqvv/1vmSKyDe4Lq89hNC/pYQsmq+BQqB1WB7jsTvYRysnlW7fA/bXHf/XkLI5wkh/fMt0ELFWTWJzCM+CuBJsHIDNwD4M7AyBn8yn0JZYCnUWaX5Z2cb/gTAHgCjYK7Q+8FcLu+dT6Ek+GbrPsvxLJh7eS/Yvf0YgH8nhFxCKW2nTPL8+VV9D2fjsy3jX8GKTB4AsBbA7wPYRQjZSimtzKtkCxBtqcgIIZ8E8EGfZhdRSq2C3JTS3xX+/R4hpBNsF3rTFVmzZZ9vBLkeSumnhWMvEUKKAP6cEHK3TdG+CP5wXV4cLxFW1PB1AP8fgC/Oj1TnHiilouvzZULISwB+BFZz64l5EWoBoy0VGYA/BPAlnzb7G+j/WQD3EEJSLZhgmyn7CQAym25Q+Gwu0Mj1PAv2DA6BWRBnA+YkW/dcgVI6Rgj5Iepz4bUD+L0eBHBcOD4IluKorUAp3U8IGQH7HiJF1mS0pSKjlJ4CcKqFQ2wAcKYVVkKTZX8GwIcJIUsopSfdYzvA6hy92qQxjGjwejYAqAI46dNuzkApLRJCeLbuR4C6bN1/Oo+ihYKb0HUtgK/MtywBcQBMmW2Hq7gIId1g7EU/BvJZB0LISgD9qFfKEZqEtlRkQeAGuvsArAIQc7MyA8A+SukkIeRnwVZ5/wlWiG4HgA8BeHAexK2Dn+wAvgWmsL5CCPkAWOzgEwA+d7a56gghW8EmoW+DVc3dCuAzAP6GUnpmPmVToOXZulsFQsiDAP4JzJ24HGwLQQXAV+dTLhWIT9Z0QsgfAfgIIeS/wRTb74JVVH5kjkWdBZPs7s/HAHwdTBmvBfAAgH1gZKwIzQaldEH/gLm9qOJnm/v5jQC+Bza5ToKt/n4NgHO2y+62OR/Av4ARVU6BKeD4fMuuuJaNYIuFMQB5MAV8N4DUfMumkfddYMqgAOYC3TLfMlnK/Xdgk30BwBH3/7XzLZdG1m2a5/tL7ucEbE/kCbBF5uMA3jjfcvvJDqADTGGdBFAEcBDAXwAYnG+5F+pPlP0+QoQIESK0NaJ9ZBEiRIgQoa0RKbIIESJEiNDWiBRZhAgRIkRoa0SKLEKECBEitDUiRRYhQoQIEdoakSKLECFChAhtjUiRRYgQIUKEtkakyCJEiBAhQlsjUmQRIkSIEKGtESmyCBEiRIjQ1ogUWYQIESJEaGtEiixChAgRIrQ1/n+nD0tii3HOFwAAAABJRU5ErkJggg==", + "image/png": "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TMevvvpqvampic2XXvdHP/pRU7u//Mu/1FtbW9nfTU1N+vXXX287v3vuuWcCTS+j7m+99VY9EonoIyMj7NjRo0f1YDCo33777aa2APS1a9faji2iGur+zDPP1NevXz/h+B//+EcdgP6DH/xA13X3ayuDE3Xvdh4UX/rSl/RYLOaaNudR633vBqOjo/q6dev0pqYmvbGxUV+xYoX+y1/+0lMfPnxMFnyN/iTE3/zN37DPqqpi5cqV0HUdH/vYx9jx5uZm9PT0YO/evexYLBZjn4vFIo4fP44lS5agubnZRG8DhC4988wzce211+K6667D2rVr8Xd/93e289I0Df/93/+Nyy+/HN3d3ez42972NlxyySWmtrqu45e//CXe8573QNd1HDt2jP275JJLMDo6OmFOn/zkJ01/X3DBBTh+/Dijhpubm/Hss8/i8OHDtvN0i2uuuQb5fB6/+MUv2LH7778fpVIJf/3Xfz3heh5//PG6jGuHbDbLQsB4RKNR9r3XtS0Wi6Y2x44dQ7FYRD6fn3C8XC67ngePBQsW4B3veAd++MMf4pe//CU++tGP4p/+6Z/wne98x/W1V3vfu0FjYyMee+wxjIyMYHR0FM8//zyuuOIKT3348DFZCJ7oCfiYevBCFACampoQjUbR1tY24fjx48fZ39lsFps3b8Y999yDQ4cOQedyLY2OjprODYfD+NGPfsRs7dRmbYfBwUFks1mceuqpE77r6enBf/3Xf5najoyM4Ic//CF++MMfWvZ39OhR2+ueNWsWAGB4eBiNjY248847ce2112L+/Pk455xz8O53vxvXXHMNFi1aZDtvGU4//XT09vbivvvuY8Lkvvvuw7nnnoslS5ZU1WetiMViyOfzE47ncjn2vde1/f3vf48LL7xwQpunn34a//Ef/2E6tm/fPixYsMDVPCj+4z/+A5/4xCfw+uuvY968eQCIyaRcLuMf//Ef8YEPfMBVUppq73sfPqY7fEF/EsLKRi6zm/PC/FOf+hTuuece/P3f/z3WrFmDpqYmKIqCq6++mmlqPP77v/8bAHl5v/HGG1i4cGGdrgBsvL/+67/Gtddea9lm2bJlpr+drvH9738/LrjgAvz617/Gww8/jLvuugtf+9rX8Ktf/QobN26sap7XXHMNPv3pT+PgwYPI5/N45plnPGmh9cacOXMsk7gcOXIEANDV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", "text/plain": [ - "
" + "
" ] }, - "metadata": { - "needs_background": "light" - }, + "metadata": {}, "output_type": "display_data" } ], @@ -355,9 +341,9 @@ ], "metadata": { "kernelspec": { - "display_name": "density", + "display_name": "GridProperties", "language": "python", - "name": "density" + "name": "python3" }, "language_info": { "codemirror_mode": { @@ -371,12 +357,7 @@ "pygments_lexer": "ipython3", "version": "3.9.2" }, - "orig_nbformat": 4, - "vscode": { - "interpreter": { - "hash": "c6ccc72f525fee77f582e34469defd9abbcd0441e48593eaea42affab1e56ba8" - } - } + "orig_nbformat": 4 }, "nbformat": 4, "nbformat_minor": 2 From 81c34f3646d08ce4302f130d21dffe7f0d6a9564 Mon Sep 17 00:00:00 2001 From: Julien Date: Tue, 23 Apr 2024 10:24:33 +0200 Subject: [PATCH 20/45] add missing throw statements --- src/GridTools.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/GridTools.cpp b/src/GridTools.cpp index 27f38ab2d..a930a7f6f 100644 --- a/src/GridTools.cpp +++ b/src/GridTools.cpp @@ -324,7 +324,7 @@ ref_ptr loadGrid3fFromTxt(std::string filename, double c) { return grid; } } - std::runtime_error("could not find GridProperties in file " + filename); + throw std::runtime_error("could not find GridProperties in file " + filename); } @@ -418,7 +418,7 @@ ref_ptr loadGrid1fFromTxt(std::string filename, double c) { return grid; } } - std::runtime_error("could not find GridProperties in file " + filename); + throw std::runtime_error("could not find GridProperties in file " + filename); } void dumpGridToTxt(ref_ptr grid, std::string filename, double c, bool saveProp) { From 8376c76cc47f37d54088dfe8b01d3998d3676285 Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Tue, 23 Apr 2024 15:35:15 +0200 Subject: [PATCH 21/45] implementation of comments: codestyle and optimization of particleMass function --- CHANGELOG.md | 2 +- include/crpropa/ParticleMass.h | 2 ++ src/ParticleMass.cpp | 7 ++----- 3 files changed, 5 insertions(+), 6 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index cf17ffbb7..4d7d0ccc3 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,9 +6,9 @@ * Fixed wrong mass inheritance for secondaries other than nuclei or electron/positron ### New features: + * Added new backwards-compatible function particleMass that returns particle mass also for non-nuclei ### Interface changes: - * Added new backwards-compatible function particleMass that returns particle mass also for non-nuclei ### Features that are deprecated and will be removed after this release * EBL model from Finke et al. 2022 diff --git a/include/crpropa/ParticleMass.h b/include/crpropa/ParticleMass.h index fdfd8579d..06175f20c 100644 --- a/include/crpropa/ParticleMass.h +++ b/include/crpropa/ParticleMass.h @@ -15,6 +15,7 @@ namespace crpropa { @returns The mass of a the particle */ double particleMass(int id); + /** Get the nucleus mass by lookup from a table. The masses are the atomic masses from the NIST database: http://www.nist.gov/pml/data/comp.cfm @@ -25,6 +26,7 @@ namespace crpropa { @returns The mass of a the nucleus */ double nuclearMass(int id); + /** Get the nucleus mass by lookup from a table. The masses are the atomic masses from the NIST database: http://www.nist.gov/pml/data/comp.cfm diff --git a/src/ParticleMass.cpp b/src/ParticleMass.cpp index cc474eb2a..075668487 100644 --- a/src/ParticleMass.cpp +++ b/src/ParticleMass.cpp @@ -54,14 +54,11 @@ struct NuclearMassTable { static NuclearMassTable nuclearMassTable; double particleMass(int id) { - double m; if (isNucleus(id)) return nuclearMass(id); if (abs(id) == 11) - m = mass_electron; - else - m = 0.0; - return m; + return mass_electron; + return 0.0; } double nuclearMass(int id) { From cb9f2d9fa8e8bf29a7f41458251c0fed812e9590 Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Tue, 23 Apr 2024 17:35:59 +0200 Subject: [PATCH 22/45] extending the test of addSecondary() for the secondaries mass and adding new test for the particleMass() function --- test/testCore.cpp | 23 +++++++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-) diff --git a/test/testCore.cpp b/test/testCore.cpp index 7aebff63a..b6738ac2a 100644 --- a/test/testCore.cpp +++ b/test/testCore.cpp @@ -149,6 +149,16 @@ TEST(ParticleID, isNucleus) { EXPECT_FALSE(isNucleus(11)); } +TEST(ParticleMass, particleMass) { + //particleMass(int id) interfaces nuclearMass for nuclei + EXPECT_DOUBLE_EQ(nuclearMass(nucleusId(1,1)), particleMass(nucleusId(1,1))); + //particleMass(int id) for electron/positron, photon and neutrino + EXPECT_DOUBLE_EQ(mass_electron,particleMass(11)); + EXPECT_DOUBLE_EQ(mass_electron,particleMass(-11)); + EXPECT_DOUBLE_EQ(0.0,particleMass(22)); + EXPECT_DOUBLE_EQ(0.0,particleMass(14)); +} + TEST(HepPID, consistencyWithReferenceImplementation) { // Tests the performance improved version against the default one unsigned long testPID = rand() % 1000000000 + 1000000000; @@ -219,8 +229,14 @@ TEST(Candidate, addSecondary) { c.addSecondary(nucleusId(1,1), 200); c.addSecondary(nucleusId(1,1), 200, 5.); - Candidate s1 = *c.secondaries[0]; - Candidate s2 = *c.secondaries[1]; + c.addSecondary(11, 200); + c.addSecondary(14, 200); + c.addSecondary(22, 200); + Candidate s1 = *c.secondaries[0]; //proton + Candidate s2 = *c.secondaries[1]; //proton + Candidate s3 = *c.secondaries[2]; //electron + Candidate s4 = *c.secondaries[3]; //neutrino + Candidate s5 = *c.secondaries[4]; //photon EXPECT_EQ(nucleusId(1,1), s1.current.getId()); EXPECT_EQ(200, s1.current.getEnergy()); @@ -231,6 +247,9 @@ TEST(Candidate, addSecondary) { EXPECT_TRUE(Vector3d(1,2,3) == s1.created.getPosition()); EXPECT_TRUE(Vector3d(0,0,1) == s1.created.getDirection()); EXPECT_TRUE(s1.getTagOrigin() == "SEC"); + EXPECT_EQ(mass_electron,s3.current.getMass()); + EXPECT_EQ(0.0,s4.current.getMass()); + EXPECT_EQ(0.0,s5.current.getMass()); EXPECT_EQ(15., s2.getWeight()); } From 70c634dfb075c3254cd9f5aeaf0f7ad3d4e170df Mon Sep 17 00:00:00 2001 From: Jan-Niklas Bohnensack Date: Thu, 2 May 2024 15:21:42 +0200 Subject: [PATCH 23/45] Added names to omp critical statements --- include/crpropa/Referenced.h | 4 ++-- src/Candidate.cpp | 4 ++-- src/module/HDF5Output.cpp | 4 ++-- src/module/OutputShell.cpp | 6 +++--- src/module/ParticleCollector.cpp | 2 +- src/module/PhotoPionProduction.cpp | 2 +- src/module/PhotonOutput1D.cpp | 2 +- src/module/TextOutput.cpp | 2 +- src/module/Tools.cpp | 4 ++-- 9 files changed, 15 insertions(+), 15 deletions(-) diff --git a/include/crpropa/Referenced.h b/include/crpropa/Referenced.h index 4bede8331..e8f80ca78 100644 --- a/include/crpropa/Referenced.h +++ b/include/crpropa/Referenced.h @@ -47,7 +47,7 @@ class Referenced { #elif defined(__GNUC__) newRef = __sync_add_and_fetch(&_referenceCount, 1); #else - #pragma omp critical + #pragma omp critical(newRef) {newRef = _referenceCount++;} #endif return newRef; @@ -67,7 +67,7 @@ class Referenced { #elif defined(__GNUC__) newRef = __sync_sub_and_fetch(&_referenceCount, 1); #else - #pragma omp critical + #pragma omp critical(newRef) {newRef = _referenceCount--;} #endif diff --git a/src/Candidate.cpp b/src/Candidate.cpp index 8028d66a2..038805a38 100644 --- a/src/Candidate.cpp +++ b/src/Candidate.cpp @@ -20,7 +20,7 @@ Candidate::Candidate(int id, double E, Vector3d pos, Vector3d dir, double z, dou #elif defined(__GNUC__) {serialNumber = __sync_add_and_fetch(&nextSerialNumber, 1);} #else - #pragma omp critical + #pragma omp critical(serialNumber) {serialNumber = nextSerialNumber++;} #endif @@ -35,7 +35,7 @@ Candidate::Candidate(const ParticleState &state) : #elif defined(__GNUC__) {serialNumber = __sync_add_and_fetch(&nextSerialNumber, 1);} #else - #pragma omp critical + #pragma omp critical(serialNumber) {serialNumber = nextSerialNumber++;} #endif diff --git a/src/module/HDF5Output.cpp b/src/module/HDF5Output.cpp index 5dcc5768f..632fa1371 100644 --- a/src/module/HDF5Output.cpp +++ b/src/module/HDF5Output.cpp @@ -248,7 +248,7 @@ void HDF5Output::close() { } void HDF5Output::process(Candidate* candidate) const { - #pragma omp critical + #pragma omp critical(HDF5Output_access_file) { if (file == -1) // This is ugly, but necesary as otherwise the user has to manually open the @@ -316,7 +316,7 @@ void HDF5Output::process(Candidate* candidate) const { pos += v.copyToBuffer(&r.propertyBuffer[pos]); } - #pragma omp critical + #pragma omp critical(HDF5Output_access_file) { const_cast(this)->candidatesSinceFlush++; Output::process(candidate); diff --git a/src/module/OutputShell.cpp b/src/module/OutputShell.cpp index 87b67f8c9..5db27d7c1 100644 --- a/src/module/OutputShell.cpp +++ b/src/module/OutputShell.cpp @@ -6,7 +6,7 @@ namespace crpropa { void ShellOutput::process(Candidate* c) const { -#pragma omp critical +#pragma omp critical(ShellOutput) { std::cout << std::fixed << std::showpoint << std::setprecision(3) << std::setw(6); @@ -25,7 +25,7 @@ std::string ShellOutput::getDescription() const { } void ShellOutput1D::process(Candidate* c) const { -#pragma omp critical +#pragma omp critical(ShellOutput) { std::cout << std::fixed << std::showpoint << std::setprecision(3) << std::setw(6); @@ -43,7 +43,7 @@ std::string ShellOutput1D::getDescription() const { void ShellPropertyOutput::process(Candidate* c) const { Candidate::PropertyMap::const_iterator i = c->properties.begin(); -#pragma omp critical +#pragma omp critical(ShellOutput) { for ( ; i != c->properties.end(); i++) { std::cout << " " << i->first << ", " << i->second << std::endl; diff --git a/src/module/ParticleCollector.cpp b/src/module/ParticleCollector.cpp index e6f48d806..74e820680 100644 --- a/src/module/ParticleCollector.cpp +++ b/src/module/ParticleCollector.cpp @@ -21,7 +21,7 @@ ParticleCollector::ParticleCollector(const std::size_t nBuffer, const bool clone } void ParticleCollector::process(Candidate *c) const { -#pragma omp critical +#pragma omp critical(ModifiyContainer) { if(clone) container.push_back(c->clone(recursive)); diff --git a/src/module/PhotoPionProduction.cpp b/src/module/PhotoPionProduction.cpp index b8f6a7db2..aa48bfe3e 100644 --- a/src/module/PhotoPionProduction.cpp +++ b/src/module/PhotoPionProduction.cpp @@ -231,7 +231,7 @@ void PhotoPionProduction::performInteraction(Candidate *candidate, bool onProton int outPartID[2000]; int nParticles; -#pragma omp critical +#pragma omp critical(SophiaEvent) { sophiaevent_(nature, Ein, eps, outputEnergy, outPartID, nParticles); } diff --git a/src/module/PhotonOutput1D.cpp b/src/module/PhotonOutput1D.cpp index ec886aa4f..67a4b74aa 100644 --- a/src/module/PhotonOutput1D.cpp +++ b/src/module/PhotonOutput1D.cpp @@ -63,7 +63,7 @@ void PhotonOutput1D::process(Candidate *candidate) const { p += std::sprintf(buffer + p, "%8.4f\t", candidate->source.getEnergy() / EeV); p += std::sprintf(buffer + p, "%8.4f\n", candidate->source.getPosition().getR() / Mpc); -#pragma omp critical +#pragma omp critical(FileOutput) { out->write(buffer, p); } diff --git a/src/module/TextOutput.cpp b/src/module/TextOutput.cpp index 07bd5ea3c..e979c85dc 100644 --- a/src/module/TextOutput.cpp +++ b/src/module/TextOutput.cpp @@ -271,7 +271,7 @@ void TextOutput::process(Candidate *c) const { std::locale::global(old_locale); -#pragma omp critical +#pragma omp critical(FileOutput) { if (count == 0) printHeader(); diff --git a/src/module/Tools.cpp b/src/module/Tools.cpp index 852e4abc3..6abc4e378 100644 --- a/src/module/Tools.cpp +++ b/src/module/Tools.cpp @@ -40,7 +40,7 @@ void PerformanceModule::process(Candidate *candidate) const { times[i] = end - start; } -#pragma omp critical +#pragma omp critical(PerformanceModule) { for (size_t i = 0; i < modules.size(); i++) { _module_info &m = modules[i]; @@ -109,7 +109,7 @@ void EmissionMapFiller::setEmissionMap(EmissionMap *emissionMap) { void EmissionMapFiller::process(Candidate* candidate) const { if (emissionMap) { - #pragma omp critical + #pragma omp critical(EmissionMap) { emissionMap->fillMap(candidate->source); } From c43f5ca4b2bfbccd03b568b9ffe27e174ae8bf82 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Mon, 13 May 2024 15:53:11 +0200 Subject: [PATCH 24/45] update data version --- CMakeLists.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 1ea3fe40f..5431a940a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -308,7 +308,7 @@ endif(APPLE) # Download data files (interaction data, masses, decay data ...) # ---------------------------------------------------------------------------- OPTION(DOWNLOAD_DATA "Download CRPropa data files" ON) -set(CRPROPA_DATAFILE_VER "2024-03-11") +set(CRPROPA_DATAFILE_VER "2024-04-30") if(DOWNLOAD_DATA) message("-- Downloading data files from sciebo ~ 73 MB") file(DOWNLOAD From ba166b334a9343c7919a92fa0a7bcda19936fce7 Mon Sep 17 00:00:00 2001 From: Jan-Niklas Bohnensack Date: Mon, 13 May 2024 17:46:15 +0200 Subject: [PATCH 25/45] Fixed some critical names: small typo and HDF5Output_access_file to HDFOutput --- src/module/HDF5Output.cpp | 4 ++-- src/module/ParticleCollector.cpp | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/module/HDF5Output.cpp b/src/module/HDF5Output.cpp index 632fa1371..00ad3a3e2 100644 --- a/src/module/HDF5Output.cpp +++ b/src/module/HDF5Output.cpp @@ -248,7 +248,7 @@ void HDF5Output::close() { } void HDF5Output::process(Candidate* candidate) const { - #pragma omp critical(HDF5Output_access_file) + #pragma omp critical(HDFOutput) { if (file == -1) // This is ugly, but necesary as otherwise the user has to manually open the @@ -316,7 +316,7 @@ void HDF5Output::process(Candidate* candidate) const { pos += v.copyToBuffer(&r.propertyBuffer[pos]); } - #pragma omp critical(HDF5Output_access_file) + #pragma omp critical(HDFOutput) { const_cast(this)->candidatesSinceFlush++; Output::process(candidate); diff --git a/src/module/ParticleCollector.cpp b/src/module/ParticleCollector.cpp index 74e820680..f37d3779c 100644 --- a/src/module/ParticleCollector.cpp +++ b/src/module/ParticleCollector.cpp @@ -21,7 +21,7 @@ ParticleCollector::ParticleCollector(const std::size_t nBuffer, const bool clone } void ParticleCollector::process(Candidate *c) const { -#pragma omp critical(ModifiyContainer) +#pragma omp critical(ModifyContainer) { if(clone) container.push_back(c->clone(recursive)); From 4177607b400c1534aeec95bbb27dd8ade2947f12 Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Fri, 17 May 2024 13:01:51 +0200 Subject: [PATCH 26/45] changed order in performInteraction so that energy loss without secondary injection can be applied and no other calculations are done in that case, that should be not necessary --- src/module/EMPairProduction.cpp | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/src/module/EMPairProduction.cpp b/src/module/EMPairProduction.cpp index d57ecc1ae..2b5eed623 100644 --- a/src/module/EMPairProduction.cpp +++ b/src/module/EMPairProduction.cpp @@ -173,13 +173,17 @@ class PPSecondariesEnergyDistribution { }; void EMPairProduction::performInteraction(Candidate *candidate) const { - // scale particle energy instead of background photon energy - double z = candidate->getRedshift(); - double E = candidate->current.getEnergy() * (1 + z); + + // photon is lost after interacting + candidate->setActive(false); // check if secondary electron pair needs to be produced if (not haveElectrons) return; + + // scale particle energy instead of background photon energy + double z = candidate->getRedshift(); + double E = candidate->current.getEnergy() * (1 + z); // check if in tabulated energy range if (E < tabE.front() or (E > tabE.back())) @@ -203,9 +207,6 @@ void EMPairProduction::performInteraction(Candidate *candidate) const { if (not std::isfinite(Ee) || not std::isfinite(Ep)) return; - // photon is lost after interacting - candidate->setActive(false); - // sample random position along current step Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition()); // apply sampling From 4b27792b9159036988417cc7bc28a3c9d2518b16 Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Fri, 17 May 2024 13:05:45 +0200 Subject: [PATCH 27/45] taking out unnecessary if-statement --- src/module/EMDoublePairProduction.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/module/EMDoublePairProduction.cpp b/src/module/EMDoublePairProduction.cpp index 451081743..7477cf81a 100644 --- a/src/module/EMDoublePairProduction.cpp +++ b/src/module/EMDoublePairProduction.cpp @@ -78,7 +78,6 @@ void EMDoublePairProduction::performInteraction(Candidate *candidate) const { double f = Ee / E; - if (haveElectrons) { if (random.rand() < pow(1 - f, thinning)) { double w = 1. / pow(1 - f, thinning); candidate->addSecondary( 11, Ee / (1 + z), pos, w, interactionTag); @@ -87,7 +86,6 @@ void EMDoublePairProduction::performInteraction(Candidate *candidate) const { double w = 1. / pow(f, thinning); candidate->addSecondary(-11, Ee / (1 + z), pos, w, interactionTag); } - } } void EMDoublePairProduction::process(Candidate *candidate) const { From 14c783564f9b5521e4e54797b9ff62e7af9ee421 Mon Sep 17 00:00:00 2001 From: Leander Schlegel Date: Tue, 21 May 2024 14:41:11 +0200 Subject: [PATCH 28/45] small optimization for case of haveSecondaries=False, as pointed out by Julien --- src/module/EMInverseComptonScattering.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/module/EMInverseComptonScattering.cpp b/src/module/EMInverseComptonScattering.cpp index 55c7637b5..c15d689d6 100644 --- a/src/module/EMInverseComptonScattering.cpp +++ b/src/module/EMInverseComptonScattering.cpp @@ -189,9 +189,9 @@ void EMInverseComptonScattering::performInteraction(Candidate *candidate) const double Enew = distribution.sample(E, s); // add up-scattered photon - double Esecondary = E - Enew; - double f = Enew / E; if (havePhotons) { + double Esecondary = E - Enew; + double f = Enew / E; if (random.rand() < pow(1 - f, thinning)) { double w = 1. / pow(1 - f, thinning); Vector3d pos = random.randomInterpolatedPosition(candidate->previous.getPosition(), candidate->current.getPosition()); From ca66f943d014d2c0d4d6a73e3e7fdb2e47357b63 Mon Sep 17 00:00:00 2001 From: Michael Unger Date: Mon, 27 May 2024 16:42:39 +0200 Subject: [PATCH 29/45] first version --- CMakeLists.txt | 5 +- include/CRPropa.h | 1 + include/crpropa/magneticField/UF23Field.h | 153 ++++++ python/2_headers.i | 12 +- src/magneticField/UF23Field.cpp | 554 ++++++++++++++++++++++ test/testMagneticField.cpp | 21 +- 6 files changed, 731 insertions(+), 15 deletions(-) create mode 100644 include/crpropa/magneticField/UF23Field.h create mode 100644 src/magneticField/UF23Field.cpp diff --git a/CMakeLists.txt b/CMakeLists.txt index 5431a940a..43483efaf 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -313,7 +313,7 @@ if(DOWNLOAD_DATA) message("-- Downloading data files from sciebo ~ 73 MB") file(DOWNLOAD https://ruhr-uni-bochum.sciebo.de/public.php/webdav/data-${CRPROPA_DATAFILE_VER}.tar.gz-CHECKSUM - ${CMAKE_BINARY_DIR}/data-${CRPROPA_DATAFILE_VER}.tar.gz-CHECKSUM + ${CMAKE_BINARY_DIR}/data-${CRPROPA_DATAFILE_VER}.tar.gz-CHECKSUM USERPWD "3juW9sntQX2IWBS") file(STRINGS ${CMAKE_BINARY_DIR}/data-${CRPROPA_DATAFILE_VER}.tar.gz-CHECKSUM DATA_CHECKSUM LIMIT_COUNT 1 LENGTH_MINIMUM 32 LENGTH_MAXIMUM 32) file(DOWNLOAD @@ -401,6 +401,7 @@ add_library(crpropa SHARED src/magneticField/turbulentField/PlaneWaveTurbulence.cpp src/magneticField/turbulentField/SimpleGridTurbulence.cpp src/magneticField/TF17Field.cpp + src/magneticField/UF23Field.cpp src/magneticField/CMZField.cpp src/advectionField/AdvectionField.cpp src/massDistribution/ConstantDensity.cpp @@ -465,7 +466,7 @@ if(ENABLE_PYTHON AND Python_FOUND) endif(Python_Development_FOUND) - # use Python_INSTALL_PACKAGE_DIR if provided; otherwise, install in Python_SITELIB + # use Python_INSTALL_PACKAGE_DIR if provided; otherwise, install in Python_SITELIB set(Python_INSTALL_PACKAGE_DIR "${Python_SITELIB}" CACHE PATH "folder in which the python package is installed") message(STATUS " package install directory: ${Python_INSTALL_PACKAGE_DIR}") diff --git a/include/CRPropa.h b/include/CRPropa.h index abd06532a..bac540bb9 100644 --- a/include/CRPropa.h +++ b/include/CRPropa.h @@ -64,6 +64,7 @@ #include "crpropa/magneticField/PT11Field.h" #include "crpropa/magneticField/QuimbyMagneticField.h" #include "crpropa/magneticField/TF17Field.h" +#include "crpropa/magneticField/UF23Field.h" #include "crpropa/magneticField/CMZField.h" #include "crpropa/magneticField/turbulentField/GridTurbulence.h" #include "crpropa/magneticField/turbulentField/HelicalGridTurbulence.h" diff --git a/include/crpropa/magneticField/UF23Field.h b/include/crpropa/magneticField/UF23Field.h new file mode 100644 index 000000000..d60c1cda1 --- /dev/null +++ b/include/crpropa/magneticField/UF23Field.h @@ -0,0 +1,153 @@ +#ifndef _UF23Field_h_ +#define _UF23Field_h_ + +#include +#include "crpropa/magneticField/MagneticField.h" + +namespace crpropa { +/** + * \addtogroup MagneticFields + * @{ + */ + + +/** + @class UF23Field + @brief UF23Field Galactic magnetic field model + + Implements the eight coherent magnetic field models of UF23 + See: M. Unger and G.R. Farrar, arXiv:2311.12120 + + Assumes a galactocentric coordinate system with the Galactic center + at the origin, the x-axis pointing in the opposite direction of the + Sun, and the z-axis pointing towards Galactic North. + + */ + +class UF23Field : public MagneticField { +public: + /// model variations (see Tab.2 of UF23 paper) + enum ModelType { + base, + neCL, + expX, + spur, + cre10, + synCG, + twistX, + nebCor + }; + + +public: + /** + @brief constructor + @param mt model type (see Tab.2 of UF23 paper) + @param maxRadiusInKpc maximum radius of field in kpc + */ + UF23Field(const ModelType mt); + /// no default constructor + UF23Field() = delete; + + Vector3d getField(const Vector3d& pos) const; + +private: + + /** + @brief calculate coherent magnetic field at a given position + @param posInKpc position with components given in kpc + @return coherent field in microgauss + */ + Vector3d operator()(const Vector3d& posInKpc) const; + + /// model parameters, see Table 3 of UF23 paper + enum EPar { + eDiskB1 = 0, + eDiskB2, + eDiskB3, + eDiskH, + eDiskPhase1, + eDiskPhase2, + eDiskPhase3, + eDiskPitch, + eDiskW, + ePoloidalA, + ePoloidalB, + ePoloidalP, + ePoloidalR, + ePoloidalW, + ePoloidalZ, + ePoloidalXi, + eSpurCenter, + eSpurLength, + eSpurWidth, + eStriation, + eToroidalBN, + eToroidalBS, + eToroidalR, + eToroidalW, + eToroidalZ, + eTwistingTime, + eNpar + }; + + /// model type given in constructor + const ModelType fModelType; + /// maximum galacto-centric radius beyond which B=0 + const double fMaxRadiusSquared; + + // parameters are stored in array + double fParameters[eNpar] = { 0 }; + // references to parameters for convience + double& fDiskB1 = fParameters[eDiskB1]; + double& fDiskB2 = fParameters[eDiskB2]; + double& fDiskB3 = fParameters[eDiskB3]; + double& fDiskH = fParameters[eDiskH]; + double& fDiskPhase1 = fParameters[eDiskPhase1]; + double& fDiskPhase2 = fParameters[eDiskPhase2]; + double& fDiskPhase3 = fParameters[eDiskPhase3]; + double& fDiskPitch = fParameters[eDiskPitch]; + double& fDiskW = fParameters[eDiskW]; + double& fPoloidalA = fParameters[ePoloidalA]; + double& fPoloidalB = fParameters[ePoloidalB]; + double& fPoloidalP = fParameters[ePoloidalP]; + double& fPoloidalR = fParameters[ePoloidalR]; + double& fPoloidalW = fParameters[ePoloidalW]; + double& fPoloidalZ = fParameters[ePoloidalZ]; + double& fPoloidalXi = fParameters[ePoloidalXi]; + double& fSpurCenter = fParameters[eSpurCenter]; + double& fSpurLength = fParameters[eSpurLength]; + double& fSpurWidth = fParameters[eSpurWidth]; + double& fStriation = fParameters[eStriation]; + double& fToroidalBN = fParameters[eToroidalBN]; + double& fToroidalBS = fParameters[eToroidalBS]; + double& fToroidalR = fParameters[eToroidalR]; + double& fToroidalW = fParameters[eToroidalW]; + double& fToroidalZ = fParameters[eToroidalZ]; + double& fTwistingTime = fParameters[eTwistingTime]; + + // some pre-calculated derived parameter values + double fSinPitch = 0; + double fCosPitch = 0; + double fTanPitch = 0; + + /// major field components + Vector3d getDiskField(const Vector3d& pos) const; + Vector3d getHaloField(const Vector3d& pos) const; + + /// sub-components depending on model type + /// -- Sec. 5.2.2 + Vector3d getSpiralField(const double x, const double y, const double z) const; + /// -- Sec. 5.2.3 + Vector3d getSpurField(const double x, const double y, const double z) const; + /// -- Sec. 5.3.1 + Vector3d getToroidalHaloField(const double x, const double y, const double z) const; + /// -- Sec. 5.3.2 + Vector3d getPoloidalHaloField(const double x, const double y, const double z) const; + /// -- Sec. 5.3.3 + Vector3d getTwistedHaloField(const double x, const double y, const double z) const; + +}; +/** @} */ +} // namespace crpropa +#endif diff --git a/python/2_headers.i b/python/2_headers.i index 6aaad3ac7..d34665838 100644 --- a/python/2_headers.i +++ b/python/2_headers.i @@ -340,6 +340,7 @@ %include "crpropa/magneticField/PolarizedSingleModeMagneticField.h" %include "crpropa/magneticField/PT11Field.h" %include "crpropa/magneticField/TF17Field.h" +%include "crpropa/magneticField/UF23Field.h" %include "crpropa/magneticField/ArchimedeanSpiralField.h" %include "crpropa/magneticField/CMZField.h" %include "crpropa/magneticField/turbulentField/TurbulentField.h" @@ -433,7 +434,7 @@ crpropa::ModuleList::iterator _end) : cur(_cur), end(_end) { } - ModuleListIterator* __iter__() { + ModuleListIterator* __iter__() { return this; } crpropa::ModuleList::iterator cur; @@ -454,7 +455,7 @@ ModuleListIterator __iter__() { return ModuleListIterator($self->begin(), $self->end()); } - + crpropa::ref_ptr __getitem__(size_t i) { if (i >= $self->size()) { throw RangeError(); @@ -480,8 +481,8 @@ crpropa::ParticleCollector::iterator _end) : cur(_cur), end(_end) { } - ParticleCollectorIterator* __iter__() { - return this; + ParticleCollectorIterator* __iter__() { + return this; } crpropa::ParticleCollector::iterator cur; crpropa::ParticleCollector::iterator end; @@ -548,6 +549,3 @@ %template(StepLengthModifierRefPtr) crpropa::ref_ptr; %feature("director") crpropa::StepLengthModifier; %include "crpropa/module/Acceleration.h" - - - diff --git a/src/magneticField/UF23Field.cpp b/src/magneticField/UF23Field.cpp new file mode 100644 index 000000000..386849b40 --- /dev/null +++ b/src/magneticField/UF23Field.cpp @@ -0,0 +1,554 @@ +#include "crpropa/magneticField/UF23Field.h" + +#include +#include +#include +#include + +// local helper functions and constants +namespace uf23 { + + template + crpropa::Vector3d CylToCart(const T v, const double cosPhi, const double sinPhi) + { + return crpropa::Vector3d(v[0] * cosPhi - v[1] * sinPhi, + v[0] * sinPhi + v[1] * cosPhi, + v[2]); + } + + template + crpropa::Vector3d CartToCyl(const T v, const double cosPhi, const double sinPhi) + { + return crpropa::Vector3d(v[0] * cosPhi + v[1] * sinPhi, + -v[0] * sinPhi + v[1] * cosPhi, + v[2]); + } + + // logistic sigmoid function + inline + double + Sigmoid(const double x, const double x0, const double w) + { + return 1 / (1 + exp(-(x-x0)/w)); + } + + // angle between v0 = (cos(phi0), sin(phi0)) and v1 = (cos(phi1), sin(phi1)) + inline + double + DeltaPhi(const double phi0, const double phi1) + { + return acos(cos(phi1)*cos(phi0) + sin(phi1)*sin(phi0)); + } + + const double kPi = 3.1415926535897932384626; + const double kTwoPi = 2*kPi; + const double degree = kPi/180.; + const double kpc = 1; + const double microgauss = 1; + const double megayear = 1; + const double Gpc = 1e6*kpc; + const double pc = 1e-3*kpc; + const double second = megayear / (1e6*60*60*24*365.25); + const double kilometer = kpc / 3.0856775807e+16; +} + +namespace crpropa { +UF23Field::UF23Field(const ModelType mt) : + fModelType(mt), + fMaxRadiusSquared(pow(30*uf23::kpc, 2)) +{ + + // all but expX model have a-->\infty, Eq.(38) + fPoloidalA = 1 * Gpc; + + switch (fModelType) { + // --------------------------------------------- + case base: { + fDiskB1 = 1.0878565e+00 * uf23::microgauss; + fDiskB2 = 2.6605034e+00 * uf23::microgauss; + fDiskB3 = 3.1166311e+00 * uf23::microgauss; + fDiskH = 7.9408965e-01 * uf23::kpc; + fDiskPhase1 = 2.6316589e+02 * uf23::degree; + fDiskPhase2 = 9.7782269e+01 * uf23::degree; + fDiskPhase3 = 3.5112281e+01 * uf23::degree; + fDiskPitch = 1.0106900e+01 * uf23::degree; + fDiskW = 1.0720909e-01 * uf23::kpc; + fPoloidalB = 9.7775487e-01 * uf23::microgauss; + fPoloidalP = 1.4266186e+00 * uf23::kpc; + fPoloidalR = 7.2925417e+00 * uf23::kpc; + fPoloidalW = 1.1188158e-01 * uf23::kpc; + fPoloidalZ = 4.4597373e+00 * uf23::kpc; + fStriation = 3.4557571e-01; + fToroidalBN = 3.2556760e+00 * uf23::microgauss; + fToroidalBS = -3.0914569e+00 * uf23::microgauss; + fToroidalR = 1.0193815e+01 * uf23::kpc; + fToroidalW = 1.6936993e+00 * uf23::kpc; + fToroidalZ = 4.0242749e+00 * uf23::kpc; + break; + } + case cre10: { + // --------------------------------------------- + fDiskB1 = 1.2035697e+00 * uf23::microgauss; + fDiskB2 = 2.7478490e+00 * uf23::microgauss; + fDiskB3 = 3.2104342e+00 * uf23::microgauss; + fDiskH = 8.0844932e-01 * uf23::kpc; + fDiskPhase1 = 2.6515882e+02 * uf23::degree; + fDiskPhase2 = 9.8211313e+01 * uf23::degree; + fDiskPhase3 = 3.5944588e+01 * uf23::degree; + fDiskPitch = 1.0162759e+01 * uf23::degree; + fDiskW = 1.0824003e-01 * uf23::kpc; + fPoloidalB = 9.6938453e-01 * uf23::microgauss; + fPoloidalP = 1.4150957e+00 * uf23::kpc; + fPoloidalR = 7.2987296e+00 * uf23::kpc; + fPoloidalW = 1.0923051e-01 * uf23::kpc; + fPoloidalZ = 4.5748332e+00 * uf23::kpc; + fStriation = 2.4950386e-01; + fToroidalBN = 3.7308133e+00 * uf23::microgauss; + fToroidalBS = -3.5039958e+00 * uf23::microgauss; + fToroidalR = 1.0407507e+01 * uf23::kpc; + fToroidalW = 1.7398375e+00 * uf23::kpc; + fToroidalZ = 2.9272800e+00 * uf23::kpc; + break; + } + case nebCor: { + // --------------------------------------------- + fDiskB1 = 1.4081935e+00 * uf23::microgauss; + fDiskB2 = 3.5292400e+00 * uf23::microgauss; + fDiskB3 = 4.1290147e+00 * uf23::microgauss; + fDiskH = 8.1151971e-01 * uf23::kpc; + fDiskPhase1 = 2.6447529e+02 * uf23::degree; + fDiskPhase2 = 9.7572660e+01 * uf23::degree; + fDiskPhase3 = 3.6403798e+01 * uf23::degree; + fDiskPitch = 1.0151183e+01 * uf23::degree; + fDiskW = 1.1863734e-01 * uf23::kpc; + fPoloidalB = 1.3485916e+00 * uf23::microgauss; + fPoloidalP = 1.3414395e+00 * uf23::kpc; + fPoloidalR = 7.2473841e+00 * uf23::kpc; + fPoloidalW = 1.4318227e-01 * uf23::kpc; + fPoloidalZ = 4.8242603e+00 * uf23::kpc; + fStriation = 3.8610837e-10; + fToroidalBN = 4.6491142e+00 * uf23::microgauss; + fToroidalBS = -4.5006610e+00 * uf23::microgauss; + fToroidalR = 1.0205288e+01 * uf23::kpc; + fToroidalW = 1.7004868e+00 * uf23::kpc; + fToroidalZ = 3.5557767e+00 * uf23::kpc; + break; + } + case neCL: { + // --------------------------------------------- + fDiskB1 = 1.4259645e+00 * uf23::microgauss; + fDiskB2 = 1.3543223e+00 * uf23::microgauss; + fDiskB3 = 3.4390669e+00 * uf23::microgauss; + fDiskH = 6.7405199e-01 * uf23::kpc; + fDiskPhase1 = 1.9961898e+02 * uf23::degree; + fDiskPhase2 = 1.3541461e+02 * uf23::degree; + fDiskPhase3 = 6.4909767e+01 * uf23::degree; + fDiskPitch = 1.1867859e+01 * uf23::degree; + fDiskW = 6.1162799e-02 * uf23::kpc; + fPoloidalB = 9.8387831e-01 * uf23::microgauss; + fPoloidalP = 1.6773615e+00 * uf23::kpc; + fPoloidalR = 7.4084361e+00 * uf23::kpc; + fPoloidalW = 1.4168192e-01 * uf23::kpc; + fPoloidalZ = 3.6521188e+00 * uf23::kpc; + fStriation = 3.3600213e-01; + fToroidalBN = 2.6256593e+00 * uf23::microgauss; + fToroidalBS = -2.5699466e+00 * uf23::microgauss; + fToroidalR = 1.0134257e+01 * uf23::kpc; + fToroidalW = 1.1547728e+00 * uf23::kpc; + fToroidalZ = 4.5585463e+00 * uf23::kpc; + break; + } + case spur: { + // --------------------------------------------- + fDiskB1 = -4.2993328e+00 * uf23::microgauss; + fDiskH = 7.5019749e-01 * uf23::kpc; + fDiskPhase1 = 1.5589875e+02 * uf23::degree; + fDiskPitch = 1.2074432e+01 * uf23::degree; + fDiskW = 1.2263120e-01 * uf23::kpc; + fPoloidalB = 9.9302987e-01 * uf23::microgauss; + fPoloidalP = 1.3982374e+00 * uf23::kpc; + fPoloidalR = 7.1973387e+00 * uf23::kpc; + fPoloidalW = 1.2262244e-01 * uf23::kpc; + fPoloidalZ = 4.4853270e+00 * uf23::kpc; + fSpurCenter = 1.5718686e+02 * uf23::degree; + fSpurLength = 3.1839577e+01 * uf23::degree; + fSpurWidth = 1.0318114e+01 * uf23::degree; + fStriation = 3.3022369e-01; + fToroidalBN = 2.9286724e+00 * uf23::microgauss; + fToroidalBS = -2.5979895e+00 * uf23::microgauss; + fToroidalR = 9.7536425e+00 * uf23::kpc; + fToroidalW = 1.4210055e+00 * uf23::kpc; + fToroidalZ = 6.0941229e+00 * uf23::kpc; + break; + } + case synCG: { + // --------------------------------------------- + fDiskB1 = 8.1386878e-01 * uf23::microgauss; + fDiskB2 = 2.0586930e+00 * uf23::microgauss; + fDiskB3 = 2.9437335e+00 * uf23::microgauss; + fDiskH = 6.2172353e-01 * uf23::kpc; + fDiskPhase1 = 2.2988551e+02 * uf23::degree; + fDiskPhase2 = 9.7388282e+01 * uf23::degree; + fDiskPhase3 = 3.2927367e+01 * uf23::degree; + fDiskPitch = 9.9034844e+00 * uf23::degree; + fDiskW = 6.6517521e-02 * uf23::kpc; + fPoloidalB = 8.0883734e-01 * uf23::microgauss; + fPoloidalP = 1.5820957e+00 * uf23::kpc; + fPoloidalR = 7.4625235e+00 * uf23::kpc; + fPoloidalW = 1.5003765e-01 * uf23::kpc; + fPoloidalZ = 3.5338550e+00 * uf23::kpc; + fStriation = 6.3434763e-01; + fToroidalBN = 2.3991193e+00 * uf23::microgauss; + fToroidalBS = -2.0919944e+00 * uf23::microgauss; + fToroidalR = 9.4227834e+00 * uf23::kpc; + fToroidalW = 9.1608418e-01 * uf23::kpc; + fToroidalZ = 5.5844594e+00 * uf23::kpc; + break; + } + case twistX: { + // --------------------------------------------- + fDiskB1 = 1.3741995e+00 * uf23::microgauss; + fDiskB2 = 2.0089881e+00 * uf23::microgauss; + fDiskB3 = 1.5212463e+00 * uf23::microgauss; + fDiskH = 9.3806180e-01 * uf23::kpc; + fDiskPhase1 = 2.3560316e+02 * uf23::degree; + fDiskPhase2 = 1.0189856e+02 * uf23::degree; + fDiskPhase3 = 5.6187572e+01 * uf23::degree; + fDiskPitch = 1.2100979e+01 * uf23::degree; + fDiskW = 1.4933338e-01 * uf23::kpc; + fPoloidalB = 6.2793114e-01 * uf23::microgauss; + fPoloidalP = 2.3292519e+00 * uf23::kpc; + fPoloidalR = 7.9212358e+00 * uf23::kpc; + fPoloidalW = 2.9056201e-01 * uf23::kpc; + fPoloidalZ = 2.6274437e+00 * uf23::kpc; + fStriation = 7.7616317e-01; + fTwistingTime = 5.4733549e+01 * uf23::megayear; + break; + } + case expX: { + // --------------------------------------------- + fDiskB1 = 9.9258148e-01 * uf23::microgauss; + fDiskB2 = 2.1821124e+00 * uf23::microgauss; + fDiskB3 = 3.1197345e+00 * uf23::microgauss; + fDiskH = 7.1508681e-01 * uf23::kpc; + fDiskPhase1 = 2.4745741e+02 * uf23::degree; + fDiskPhase2 = 9.8578879e+01 * uf23::degree; + fDiskPhase3 = 3.4884485e+01 * uf23::degree; + fDiskPitch = 1.0027070e+01 * uf23::degree; + fDiskW = 9.8524736e-02 * uf23::kpc; + fPoloidalA = 6.1938701e+00 * uf23::kpc; + fPoloidalB = 5.8357990e+00 * uf23::microgauss; + fPoloidalP = 1.9510779e+00 * uf23::kpc; + fPoloidalR = 2.4994376e+00 * uf23::kpc; + // internally, xi is fitted and z = tan(xi)*a + fPoloidalXi = 2.0926122e+01 * uf23::degree; + fPoloidalZ = fPoloidalA*tan(fPoloidalXi); + fStriation = 5.1440500e-01; + fToroidalBN = 2.7077434e+00 * uf23::microgauss; + fToroidalBS = -2.5677104e+00 * uf23::microgauss; + fToroidalR = 1.0134022e+01 * uf23::kpc; + fToroidalW = 2.0956159e+00 * uf23::kpc; + fToroidalZ = 5.4564991e+00 * uf23::kpc; + break; + } + default: { + throw std::runtime_error("unknown field model"); + break; + } + } + + fSinPitch = sin(fDiskPitch); + fCosPitch = cos(fDiskPitch); + fTanPitch = tan(fDiskPitch); + +} + +Vector3d +UF23Field::getField(const Vector3d &position) + const +{ + Vector3d posInKpc = position / uf23::kpc; + return (this->operator()(posInKpc)) / uf23::microgauss * microgauss; +} + + +Vector3d +UF23Field::operator()(const Vector3d& posInKpc) + const +{ + const auto pos = posInKpc * uf23::kpc; + if (pos.getR2() > fMaxRadiusSquared) + return Vector3d(0, 0, 0); + else { + const auto diskField = getDiskField(pos); + const auto haloField = getHaloField(pos); + return (diskField + haloField) / uf23::microgauss; + } +} + +Vector3d +UF23Field::getDiskField(const Vector3d& pos) + const +{ + if (fModelType == spur) + return getSpurField(pos.x, pos.y, pos.z); + else + return getSpiralField(pos.x, pos.y, pos.z); +} + + +Vector3d +UF23Field::getHaloField(const Vector3d& pos) + const +{ + if (fModelType == twistX) + return getTwistedHaloField(pos.x, pos.y, pos.z); + else + return + getToroidalHaloField(pos.x, pos.y, pos.z) + + getPoloidalHaloField(pos.x, pos.y, pos.z); +} + + +Vector3d +UF23Field::getTwistedHaloField(const double x, const double y, const double z) + const +{ + const double r = sqrt(x*x + y*y); + const double cosPhi = r > std::numeric_limits::min() ? x / r : 1; + const double sinPhi = r > std::numeric_limits::min() ? y / r : 0; + + const Vector3d bXCart = getPoloidalHaloField(x, y, z); + const double bXCartTmp[3] = {bXCart.x, bXCart.y, bXCart.z}; + const Vector3d bXCyl = uf23::CartToCyl(bXCartTmp, cosPhi, sinPhi); + + const double bZ = bXCyl.z; + const double bR = bXCyl.x; + + double bPhi = 0; + + if (fTwistingTime != 0 && r != 0) { + // radial rotation curve parameters (fit to Reid et al 2014) + const double v0 = -240 * uf23::kilometer/uf23::second; + const double r0 = 1.6 * uf23::kpc; + // vertical gradient (Levine+08) + const double z0 = 10 * uf23::kpc; + + // Eq.(43) + const double fr = 1 - exp(-r/r0); + // Eq.(44) + const double t0 = exp(2*std::abs(z)/z0); + const double gz = 2 / (1 + t0); + + // Eq. (46) + const double signZ = z < 0 ? -1 : 1; + const double deltaZ = -signZ * v0 * fr / z0 * t0 * pow(gz, 2); + // Eq. (47) + const double deltaR = v0 * ((1-fr)/r0 - fr/r) * gz; + + // Eq.(45) + bPhi = (bZ * deltaZ + bR * deltaR) * fTwistingTime; + + } + const double bCylX[3] = {bR, bPhi , bZ}; + return uf23::CylToCart(bCylX, cosPhi, sinPhi); +} + +Vector3d +UF23Field::getToroidalHaloField(const double x, const double y, const double z) + const +{ + const double r2 = x*x + y*y; + const double r = sqrt(r2); + const double absZ = std::abs(z); + + const double b0 = z >= 0 ? fToroidalBN : fToroidalBS; + const double rh = fToroidalR; + const double z0 = fToroidalZ; + const double fwh = fToroidalW; + const double sigmoidR = uf23::Sigmoid(r, rh, fwh); + const double sigmoidZ = uf23::Sigmoid(absZ, fDiskH, fDiskW); + + // Eq. (21) + const double bPhi = b0 * (1. - sigmoidR) * sigmoidZ * exp(-absZ/z0); + + const double bCyl[3] = {0, bPhi, 0}; + const double cosPhi = r > std::numeric_limits::min() ? x / r : 1; + const double sinPhi = r > std::numeric_limits::min() ? y / r : 0; + return uf23::CylToCart(bCyl, cosPhi, sinPhi); +} + +Vector3d +UF23Field::getPoloidalHaloField(const double x, const double y, const double z) + const +{ + const double r2 = x*x + y*y; + const double r = sqrt(r2); + + const double c = pow(fPoloidalA/fPoloidalZ, fPoloidalP); + const double a0p = pow(fPoloidalA, fPoloidalP); + const double rp = pow(r, fPoloidalP); + const double abszp = pow(std::abs(z), fPoloidalP); + const double cabszp = c*abszp; + + /* + since $\sqrt{a^2 + b} - a$ is numerical unstable for $b\ll a$, + we use $(\sqrt{a^2 + b} - a) \frac{\sqrt{a^2 + b} + a}{\sqrt{a^2 + + b} + a} = \frac{b}{\sqrt{a^2 + b} + a}$} + */ + + const double t0 = a0p + cabszp - rp; + const double t1 = sqrt(pow(t0, 2) + 4*a0p*rp); + const double ap = 2*a0p*rp / (t1 + t0); + + double a = 0; + if (ap < 0) { + if (r > std::numeric_limits::min()) { + // this should never happen + throw std::runtime_error("ap = " + std::to_string(ap)); + } + else + a = 0; + } + else + a = pow(ap, 1/fPoloidalP); + + // Eq.(29) and Eq.(32) + const double radialDependence = + fModelType == expX ? + exp(-a/fPoloidalR) : + 1 - uf23::Sigmoid(a, fPoloidalR, fPoloidalW); + + // Eq.(28) + const double Bzz = fPoloidalB * radialDependence; + + // (r/a) + const double rOverA = 1 / pow(2*a0p / (t1 + t0), 1/fPoloidalP); + + // Eq.(35) for p=n + const double signZ = z < 0 ? -1 : 1; + const double Br = + Bzz * c * a / rOverA * signZ * pow(std::abs(z), fPoloidalP - 1) / t1; + + // Eq.(36) for p=n + const double Bz = Bzz * pow(rOverA, fPoloidalP-2) * (ap + a0p) / t1; + + if (r < std::numeric_limits::min()) + return Vector3d(0, 0, Bz); + else { + const double bCylX[3] = {Br, 0 , Bz}; + const double cosPhi = x / r; + const double sinPhi = y / r; + return uf23::CylToCart(bCylX, cosPhi, sinPhi); + } +} + +Vector3d +UF23Field::getSpurField(const double x, const double y, const double z) + const +{ + // reference approximately at solar radius + const double rRef = 8.2*uf23::kpc; + + // cylindrical coordinates + const double r2 = x*x + y*y; + const double r = sqrt(r2); + if (r < std::numeric_limits::min()) + return Vector3d(0, 0, 0); + + double phi = atan2(y, x); + if (phi < 0) + phi += uf23::kTwoPi; + + const double phiRef = fDiskPhase1; + int iBest = -2; + double bestDist = -1; + for (int i = -1; i <= 1; ++i) { + const double pphi = phi - phiRef + i*uf23::kTwoPi; + const double rr = rRef*exp(pphi * fTanPitch); + if (bestDist < 0 || std::abs(r-rr) < bestDist) { + bestDist = std::abs(r-rr); + iBest = i; + } + } + if (iBest == 0) { + const double phi0 = phi - log(r/rRef) / fTanPitch; + + // Eq. (16) + const double deltaPhi0 = uf23::DeltaPhi(phiRef, phi0); + const double delta = deltaPhi0 / fSpurWidth; + const double B = fDiskB1 * exp(-0.5*pow(delta, 2)); + + // Eq. (18) + const double wS = 5*uf23::degree; + const double phiC = fSpurCenter; + const double deltaPhiC = uf23::DeltaPhi(phiC, phi); + const double lC = fSpurLength; + const double gS = 1 - uf23::Sigmoid(std::abs(deltaPhiC), lC, wS); + + // Eq. (13) + const double hd = 1 - uf23::Sigmoid(std::abs(z), fDiskH, fDiskW); + + // Eq. (17) + const double bS = rRef/r * B * hd * gS; + const double bCyl[3] = {bS * fSinPitch, bS * fCosPitch, 0}; + const double cosPhi = x / r; + const double sinPhi = y / r; + return uf23::CylToCart(bCyl, cosPhi, sinPhi); + } + else + return Vector3d(0, 0, 0); + +} + +Vector3d +UF23Field::getSpiralField(const double x, const double y, const double z) + const +{ + // reference radius + const double rRef = 5*uf23::kpc; + // inner boundary of spiral field + const double rInner = 5*uf23::kpc; + const double wInner = 0.5*uf23::kpc; + // outer boundary of spiral field + const double rOuter = 20*uf23::kpc; + const double wOuter = 0.5*uf23::kpc; + + // cylindrical coordinates + const double r2 = x*x + y*y; + if (r2 == 0) + return Vector3d(0, 0, 0); + const double r = sqrt(r2); + const double phi = atan2(y, x); + + // Eq.(13) + const double hdz = 1 - uf23::Sigmoid(std::abs(z), fDiskH, fDiskW); + + // Eq.(14) times rRef divided by r + const double rFacI = uf23::Sigmoid(r, rInner, wInner); + const double rFacO = 1 - uf23::Sigmoid(r, rOuter, wOuter); + // (using lim r--> 0 (1-exp(-r^2))/r --> r - r^3/2 + ...) + const double rFac = r > 1e-5*uf23::pc ? (1-exp(-r*r)) / r : r * (1 - r2/2); + const double gdrTimesRrefByR = rRef * rFac * rFacO * rFacI; + + // Eq. (12) + const double phi0 = phi - log(r/rRef) / fTanPitch; + + // Eq. (10) + const double b = + fDiskB1 * cos(1 * (phi0 - fDiskPhase1)) + + fDiskB2 * cos(2 * (phi0 - fDiskPhase2)) + + fDiskB3 * cos(3 * (phi0 - fDiskPhase3)); + + // Eq. (11) + const double fac = hdz * gdrTimesRrefByR; + const double bCyl[3] = + { b * fac * fSinPitch, + b * fac * fCosPitch, + 0}; + + const double cosPhi = x / r; + const double sinPhi = y / r; + return uf23::CylToCart(bCyl, cosPhi, sinPhi); +} +} diff --git a/test/testMagneticField.cpp b/test/testMagneticField.cpp index 8528c2593..e5f7e6861 100644 --- a/test/testMagneticField.cpp +++ b/test/testMagneticField.cpp @@ -4,6 +4,7 @@ #include "crpropa/magneticField/CMZField.h" #include "crpropa/magneticField/PolarizedSingleModeMagneticField.h" #include "crpropa/magneticField/GalacticMagneticField.h" +#include "crpropa/magneticField/UF23Field.h" #include "crpropa/Grid.h" #include "crpropa/Units.h" #include "crpropa/Common.h" @@ -105,7 +106,7 @@ TEST(testPeriodicMagneticField, Exceptions) { TEST(testCMZMagneticField, SimpleTest) { ref_ptr field = new CMZField(); - + // check use-Values EXPECT_FALSE(field->getUseMCField()); EXPECT_TRUE(field->getUseICField()); @@ -125,7 +126,7 @@ TEST(testCMZMagneticField, SimpleTest) { TEST(testCMZMagneticField, TestICComponent) { ref_ptr field = new CMZField(); - Vector3d pos(10*pc,15*pc,-5*pc); + Vector3d pos(10*pc,15*pc,-5*pc); // check IC field at given position Vector3d bVec = field->getField(pos); @@ -136,8 +137,8 @@ TEST(testCMZMagneticField, TestICComponent) { } TEST(testCMZMagneticField, TestNTFField){ ref_ptr field = new CMZField(); - Vector3d pos(10*pc,15*pc,-5*pc); - + Vector3d pos(10*pc,15*pc,-5*pc); + // check NFTField at given position Vector3d bVec = field->getNTFField(pos); EXPECT_NEAR(bVec.getR(),1.692*muG, 1e-3*muG); @@ -147,7 +148,7 @@ TEST(testCMZMagneticField, TestNTFField){ } TEST(testCMZMagneticField, TestRaidoArcField){ ref_ptr field = new CMZField(); - Vector3d pos(10*pc,15*pc,-5*pc); + Vector3d pos(10*pc,15*pc,-5*pc); // check RadioArcField at given position Vector3d bVec = field->getRadioArcField(pos); @@ -160,7 +161,7 @@ TEST(testCMZMagneticField, TestRaidoArcField){ TEST(testCMZMagneticField, TestAzimutalComponent){ ref_ptr field = new CMZField(); Vector3d mid(12*pc, 9*pc, 20*pc); - Vector3d pos(9*pc, 10*pc, 25*pc); + Vector3d pos(9*pc, 10*pc, 25*pc); // simple Test for inner part Vector3d bVec = field->BAz(pos, mid, 100, 0.2, 60*pc); @@ -202,6 +203,14 @@ TEST(testLogarithmicSpiralField, SimpleTest) { EXPECT_NEAR(b.z, 0, 1E-10); } +TEST(testUF23Field, SimpleTest) { + ref_ptr field = new UF23Field(UF23Field::base); + Vector3d b = field->getField(Vector3d(8.5, 0, 0)*kpc); + EXPECT_NEAR(b.x, -1., 1E-2); + EXPECT_NEAR(b.y, 0, 1E-10); + EXPECT_NEAR(b.z, 0, 1E-10); +} + TEST(testPolarizedSingleModeMagneticField, SimpleTest) { PolarizedSingleModeMagneticField B(2, 4, 0.5, Vector3d(1,1,1), Vector3d(0,1,0), Vector3d(1,0,0), "amplitude", "polarization", "elliptical"); Vector3d b = B.getField(Vector3d(1,1,2)); From f658083c7296b5cd063dad52051ffe41af977e51 Mon Sep 17 00:00:00 2001 From: Michael Unger Date: Mon, 27 May 2024 17:13:08 +0200 Subject: [PATCH 30/45] units --- src/magneticField/UF23Field.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/magneticField/UF23Field.cpp b/src/magneticField/UF23Field.cpp index 386849b40..a23a12d51 100644 --- a/src/magneticField/UF23Field.cpp +++ b/src/magneticField/UF23Field.cpp @@ -267,7 +267,7 @@ Vector3d UF23Field::getField(const Vector3d &position) const { - Vector3d posInKpc = position / uf23::kpc; + Vector3d posInKpc = position / kpc; return (this->operator()(posInKpc)) / uf23::microgauss * microgauss; } From c8d8b3e4e6fee8ebce2708a1aef65add323e91fd Mon Sep 17 00:00:00 2001 From: Michael Unger Date: Mon, 27 May 2024 17:13:16 +0200 Subject: [PATCH 31/45] tests --- test/testMagneticField.cpp | 134 +++++++++++++++++++++++++++++++++++-- 1 file changed, 129 insertions(+), 5 deletions(-) diff --git a/test/testMagneticField.cpp b/test/testMagneticField.cpp index e5f7e6861..da735edc6 100644 --- a/test/testMagneticField.cpp +++ b/test/testMagneticField.cpp @@ -203,12 +203,136 @@ TEST(testLogarithmicSpiralField, SimpleTest) { EXPECT_NEAR(b.z, 0, 1E-10); } + +// UF23 reference values +std::vector> +getUF23ReferenceValues() +{ + using V = Vector3d; + std::vector> retVal; + retVal.push_back({ + V{-1.46860417e+00, 1.64555489e+00, 8.35702311e-01}, + V{0.00000000e+00, -4.22433497e-01, 1.83232985e-01}, + V{-3.00239177e-01, -2.97045767e-01, 1.83232985e-01}, + V{8.58382023e-04, 7.71891049e-03, 9.71705527e-01}, + V{-1.17276875e+00, -2.33013590e-01, 4.10798494e-01}, + V{2.63883569e-01, -8.79631081e-01, 5.54229961e-06}, + V{-1.71971907e-02, -2.00291358e-02, 4.16024875e-02}, + V{6.18960813e-01, -2.14437026e+00, 8.35702315e-01}, + V{-1.50883911e+00, 2.63874909e+00, 1.16578928e-02} + }); + retVal.push_back({ + V{-1.39447625e+00, 1.57135437e+00, 8.65163870e-01}, + V{0.00000000e+00, -4.44318027e-01, 1.54430718e-01}, + V{-3.15695875e-01, -3.12652066e-01, 1.54430718e-01}, + V{2.09678202e-03, 2.63832916e-03, 9.81077691e-01}, + V{-1.08603376e+00, -1.86359136e-01, 3.91730436e-01}, + V{2.11095801e-01, -7.04082667e-01, 8.86591950e-05}, + V{-1.38087843e-02, -1.52011002e-02, 3.06842086e-02}, + V{5.76543516e-01, -2.03544911e+00, 8.65163870e-01}, + V{-3.77778745e-01, 6.89644787e-01, 5.85347897e-02}, + }); + retVal.push_back({ + V{-1.04170166e+00, 1.93212739e+00, 2.95362499e+00}, + V{0.00000000e+00, -5.87995638e-01, 4.66925506e-01}, + V{-4.20802701e-01, -4.10291633e-01, 4.59557272e-01}, + V{7.79982996e-03, 1.50482351e-02, 5.50337531e+00}, + V{-1.34639246e+00, 6.80103301e-02, 8.60002649e-01}, + V{1.37242004e-01, -8.67085225e-01, 1.25106474e-01}, + V{-1.69325979e-02, -2.95454738e-02, 4.72616404e-02}, + V{4.53873303e-01, -2.03292501e+00, 9.95205454e-01}, + V{-1.30599234e+00, 2.25151057e+00, 2.56704152e-01}, + }); + retVal.push_back({ + V{-1.45840221e+00, 1.64227817e+00, 8.41586777e-01}, + V{0.00000000e+00, -6.98341816e-01, 1.84323895e-01}, + V{-4.95342500e-01, -4.92154113e-01, 1.84323895e-01}, + V{-5.27533653e-03, 1.48965596e-02, 9.86107885e-01}, + V{-1.47472798e+00, -3.33905274e-01, 4.11265918e-01}, + V{2.31202234e-01, -7.70722755e-01, 1.12129423e-05}, + V{-1.54200071e-02, -2.22012150e-02, 4.22733003e-02}, + V{5.92201401e-01, -2.10378256e+00, 8.41586782e-01}, + V{4.05057122e-03, -9.76673905e-03, 8.24321504e-03}, + }); + retVal.push_back({ + V{-1.50595160e+00, 1.67869437e+00, 8.29806168e-01}, + V{0.00000000e+00, -2.27289811e-01, 1.86869632e-01}, + V{-1.62291024e-01, -1.59076795e-01, 1.86869632e-01}, + V{6.71536463e-04, 7.88990042e-03, 9.63291786e-01}, + V{-9.35561196e-01, -1.55840707e-01, 4.13609050e-01}, + V{2.68120686e-01, -8.93743434e-01, 3.48927149e-06}, + V{-1.88291055e-02, -1.94245715e-02, 4.29970299e-02}, + V{6.50804557e-01, -2.18817590e+00, 8.29806172e-01}, + V{-1.58450595e+00, 2.77817014e+00, 1.10336683e-02}, + }); + retVal.push_back({ + V{-1.33098823e+00, 1.49556466e+00, 6.88642986e-01}, + V{0.00000000e+00, -4.99342453e-01, 1.16143813e-01}, + V{-3.54225500e-01, -3.51947350e-01, 1.16143813e-01}, + V{2.14352986e-03, 3.57971370e-03, 8.05219599e-01}, + V{-1.15136627e+00, -2.48536546e-01, 2.95713475e-01}, + V{1.18057505e-01, -3.98308301e-01, 9.11299352e-04}, + V{-1.06899006e-02, -1.12335952e-02, 2.33358311e-02}, + V{5.61264936e-01, -1.94601963e+00, 6.88642987e-01}, + V{-1.18200258e+00, 2.01179003e+00, 8.02453884e-02}, + }); + retVal.push_back({ + V{-3.65508814e-01, 4.74456797e-01, 5.76165841e-01}, + V{0.00000000e+00, 0.00000000e+00, 6.36668108e-02}, + V{-3.68784336e-03, -2.20689056e-03, 6.36668108e-02}, + V{-5.03208784e-02, 5.09887480e-02, 6.27665021e-01}, + V{-4.04821314e-01, -1.01426396e-02, 2.06022291e-01}, + V{-2.34287239e-02, -9.72536117e-02, 2.80624948e-02}, + V{-4.42698169e-03, -6.23429869e-03, 1.07555956e-02}, + V{3.25022555e-01, -1.18950549e+00, 5.76163734e-01}, + V{-8.65217092e-01, 1.85270104e+00, 3.73913202e-01}, + }); + retVal.push_back({ + V{-1.92580231e+00, 2.17134243e+00, 1.13723929e+00}, + V{0.00000000e+00, -4.73261099e-01, 2.65974345e-01}, + V{-3.36780079e-01, -3.32368900e-01, 2.65974345e-01}, + V{-5.24558924e-04, 1.51886238e-02, 1.33757258e+00}, + V{-1.47213976e+00, -2.82203258e-01, 5.71920142e-01}, + V{3.54206333e-01, -1.18108962e+00, 1.00077423e-04}, + V{-2.67268842e-02, -2.88588605e-02, 6.38364561e-02}, + V{7.90570955e-01, -2.84039611e+00, 1.13723931e+00}, + V{-1.97316856e+00, 3.44153600e+00, 3.20266742e-02}, + }); + return retVal; +} + + TEST(testUF23Field, SimpleTest) { - ref_ptr field = new UF23Field(UF23Field::base); - Vector3d b = field->getField(Vector3d(8.5, 0, 0)*kpc); - EXPECT_NEAR(b.x, -1., 1E-2); - EXPECT_NEAR(b.y, 0, 1E-10); - EXPECT_NEAR(b.z, 0, 1E-10); + const std::vector models = + { + UF23Field::base, UF23Field::neCL, UF23Field::expX, UF23Field::spur, + UF23Field::cre10, UF23Field::synCG, UF23Field::twistX, UF23Field::nebCor + }; + + using V = Vector3d; + const std::vector testPositions = + { + V{1, 1, 1}, V{0, 0, -8}, V{0.1, -0.1, -8}, V{0.1, 0.1, 0.1}, V{-1, 3, 4}, + V{-10, -3, 2}, V{-10, -10, 20}, V{-4, -2, 1}, V{6, 5, -0.1} + }; + + const std::vector> referenceValues = + getUF23ReferenceValues(); + + const double precision = 1e-6; + + for (unsigned int i = 0; i < models.size(); ++i) { + const auto& model = models[i]; + const UF23Field uf23Field(model); + for (unsigned int j = 0; j < testPositions.size(); ++j) { + const auto& position = testPositions[j]; + const auto val = uf23Field.getField(position*kpc); + const auto& refVal = referenceValues[i][j] * microgauss; + EXPECT_NEAR(val.x, refVal.x, precision); + EXPECT_NEAR(val.y, refVal.y, precision); + EXPECT_NEAR(val.z, refVal.z, precision); + } + } } TEST(testPolarizedSingleModeMagneticField, SimpleTest) { From fba3a8c809612b11c6f1d1f5e5b42b69fa5a64b6 Mon Sep 17 00:00:00 2001 From: Michael Unger Date: Mon, 27 May 2024 17:43:02 +0200 Subject: [PATCH 32/45] example of how to initialize UF23 field (commented) --- .../galactic_backtracking/galactic_backtracking.ipynb | 1 + 1 file changed, 1 insertion(+) diff --git a/doc/pages/example_notebooks/galactic_backtracking/galactic_backtracking.ipynb b/doc/pages/example_notebooks/galactic_backtracking/galactic_backtracking.ipynb index 2058d32c1..cef88981a 100644 --- a/doc/pages/example_notebooks/galactic_backtracking/galactic_backtracking.ipynb +++ b/doc/pages/example_notebooks/galactic_backtracking/galactic_backtracking.ipynb @@ -38,6 +38,7 @@ "\n", "# magnetic field setup\n", "B = JF12Field()\n", + "#B = UF23Field(UF23Field.base) # options: base,neCL,expX,spur,cre10,synCG,twistX,nebCor \n", "#seed = 691342\n", "#B.randomStriated(seed)\n", "#B.randomTurbulent(seed)\n", From 20a618f121f3eaafd806b8e3e1a6e3fa8a5dc831 Mon Sep 17 00:00:00 2001 From: Lukas Merten Date: Fri, 31 May 2024 17:34:29 +0200 Subject: [PATCH 33/45] Update CHANGELOG.md EBL Finke model was introduced newly and is not deprecated. --- CHANGELOG.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4d7d0ccc3..ed7d14f33 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,12 +6,12 @@ * Fixed wrong mass inheritance for secondaries other than nuclei or electron/positron ### New features: - * Added new backwards-compatible function particleMass that returns particle mass also for non-nuclei + * Added new backwards-compatible function particleMass that returns particle mass also for non-nuclei + * EBL model from Finke et al. 2022 ### Interface changes: ### Features that are deprecated and will be removed after this release - * EBL model from Finke et al. 2022 ### Removed features * AMRMagneticField - underlying library (saga) is no longer supported. From 7d4d84d6957f1d5937cd76494ec9076c3ff5c0ab Mon Sep 17 00:00:00 2001 From: Lukas Merten Date: Mon, 3 Jun 2024 13:11:26 +0200 Subject: [PATCH 34/45] Fixed typo --- doc/pages/Code-Coverage.md | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/pages/Code-Coverage.md b/doc/pages/Code-Coverage.md index 8621353a5..4ea6e2dac 100644 --- a/doc/pages/Code-Coverage.md +++ b/doc/pages/Code-Coverage.md @@ -17,5 +17,5 @@ make coverage ``` The final report is in ```~/build/coverageReport/index.html``` -### coverage report of the current master branch -The coverage report of the current master branch can be accesed `by clicking here `_ now. \ No newline at end of file +### Coverage report of the current master branch +The coverage report of the current master branch can be accesed `by clicking here `_ now. From 8fcce26d239de256f81d343390bffe548a0eb644 Mon Sep 17 00:00:00 2001 From: Michael Unger Date: Mon, 3 Jun 2024 13:40:25 +0200 Subject: [PATCH 35/45] Lukas' suggestions --- CHANGELOG.md | 27 ++++++++++++----------- include/crpropa/magneticField/UF23Field.h | 2 +- src/magneticField/UF23Field.cpp | 4 ++++ 3 files changed, 19 insertions(+), 14 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4d7d0ccc3..e3801fd19 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,19 +1,20 @@ ## CRPropa vNext ### Bug fixes: - * Fixed sign for exponential decay of magn. field strength with Galactic height in LogarithmicSpiralField - * Fixed r term in source distribution for SNR and Pulsar + * Fixed sign for exponential decay of magn. field strength with Galactic height in LogarithmicSpiralField + * Fixed r term in source distribution for SNR and Pulsar * Fixed wrong mass inheritance for secondaries other than nuclei or electron/positron ### New features: - * Added new backwards-compatible function particleMass that returns particle mass also for non-nuclei + * Added new backwards-compatible function particleMass that returns particle mass also for non-nuclei + * Added the new Galactic magnetic field models from Unger&Farrar arXiv:2311.12120 ### Interface changes: ### Features that are deprecated and will be removed after this release * EBL model from Finke et al. 2022 -### Removed features +### Removed features * AMRMagneticField - underlying library (saga) is no longer supported. * ObserverPoint: Use Observer1D instead. @@ -42,8 +43,8 @@ * ObserverPoint will be renamed into Observer1D. * AMRMagneticField - underlying library (saga) is no longer supported. -### Removed features -* External extensions DINT and Eleca, which can be replaced with the +### Removed features +* External extensions DINT and Eleca, which can be replaced with the EM*-modules combined with the thinning option for reasonable computation times. @@ -52,7 +53,7 @@ * grplinst * monopole * ROOTOutputPlugin - + ## CRPropa 3.2 @@ -60,12 +61,12 @@ * Fix of reflective boundary condition for scalar- and vectorgrids that showed asymmetry and discontinuities (See issue [#361]). * Fix in EMTripletPairProduction -* Fix of the data files of the Hackstein EGMF models as well as the +* Fix of the data files of the Hackstein EGMF models as well as the corresponding example notebook. * Fix of axis normalization of getRotated in Vector3.h. * Fix of secondary spectra in electromagnetic interactions (EM*-modules), issue [#334] and pull request [#15] in crpropa-data. -* Fix weight inheritance for secondary particles; they are created with +* Fix weight inheritance for secondary particles; they are created with their parents weights as intial weights now. ### New features: @@ -75,15 +76,15 @@ and vectorgrids. * Add the new PolarizedSingleModeMagneticField class for polarized/ helical single mode magnetic field models. -* Add a source feature for targeted emission, following the +* Add a source feature for targeted emission, following the von-Mises-Fisher distribution -* Updates in SNR and pulsar source distributions +* Updates in SNR and pulsar source distributions ### Interface changes: -* Plane wave and grid turbulence models use same parameter convention now +* Plane wave and grid turbulence models use same parameter convention now ### Features that are deprecated and will be removed after this release -* External extensions DINT and Eleca, which can be replaced with the +* External extensions DINT and Eleca, which can be replaced with the EM*-modules combined with the thinning option for reasonable computation times. diff --git a/include/crpropa/magneticField/UF23Field.h b/include/crpropa/magneticField/UF23Field.h index d60c1cda1..462ed3142 100644 --- a/include/crpropa/magneticField/UF23Field.h +++ b/include/crpropa/magneticField/UF23Field.h @@ -114,7 +114,7 @@ class UF23Field : public MagneticField { double& fPoloidalR = fParameters[ePoloidalR]; double& fPoloidalW = fParameters[ePoloidalW]; double& fPoloidalZ = fParameters[ePoloidalZ]; - double& fPoloidalXi = fParameters[ePoloidalXi]; + double& fPoloidalXi = fParameters[ePoloidalXi]; double& fSpurCenter = fParameters[eSpurCenter]; double& fSpurLength = fParameters[eSpurLength]; double& fSpurWidth = fParameters[eSpurWidth]; diff --git a/src/magneticField/UF23Field.cpp b/src/magneticField/UF23Field.cpp index a23a12d51..6a65b1b80 100644 --- a/src/magneticField/UF23Field.cpp +++ b/src/magneticField/UF23Field.cpp @@ -40,6 +40,10 @@ namespace uf23 { return acos(cos(phi1)*cos(phi0) + sin(phi1)*sin(phi0)); } + // Interal units used in this code. + // Convert to crpropa with e.g. uf23::kpc / crpropa::kpc. + // The conversion is, however, only needed in the single non-private + // getField() method, all other functions use uf23 units. const double kPi = 3.1415926535897932384626; const double kTwoPi = 2*kPi; const double degree = kPi/180.; From a1adcde084f90baef1e83b3c8a9cc42c51271c47 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Julien=20D=C3=B6rner?= Date: Tue, 11 Jun 2024 16:55:10 +0200 Subject: [PATCH 36/45] update error messages. --- src/GridTools.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/GridTools.cpp b/src/GridTools.cpp index a930a7f6f..41e46ca51 100644 --- a/src/GridTools.cpp +++ b/src/GridTools.cpp @@ -282,7 +282,7 @@ ref_ptr loadGrid3fFromTxt(std::string filename, double c) { std::string name, type; ss >> name >> name >> name >> type; if (type != "Grid3f") - throw std::runtime_error("try to load Grid3f, but Gridproperties assume grid type " + type); + throw std::runtime_error("Tried to load Grid3f, but Gridproperties assume grid type " + type); // grid origin double x, y, z; @@ -376,7 +376,7 @@ ref_ptr loadGrid1fFromTxt(std::string filename, double c) { std::string name, type; ss >> name >> name >> name >> type; if (type != "Grid1f") - throw std::runtime_error("try to load Grid1f, but Gridproperties assume grid type " + type); + throw std::runtime_error("Tried to load Grid1f, but Gridproperties assume grid type " + type); // grid origin double x, y, z; From 34d36f385581cf48c1e1b03e54fed598afc607a1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Julien=20D=C3=B6rner?= Date: Wed, 3 Jul 2024 12:11:48 +0200 Subject: [PATCH 37/45] fix numpy version to 1.26.4 --- .github/workflows/test_examples.yml | 3 +-- doc/pages/example_notebooks/requirements.txt | 2 +- 2 files changed, 2 insertions(+), 3 deletions(-) diff --git a/.github/workflows/test_examples.yml b/.github/workflows/test_examples.yml index f1edf5776..67d49fd4c 100644 --- a/.github/workflows/test_examples.yml +++ b/.github/workflows/test_examples.yml @@ -21,10 +21,9 @@ jobs: - name: Preinstall run: | sudo apt-get update - sudo apt-get install libmuparser-dev python3 python3-dev python3-numpy python3-setuptools python-setuptools libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov + sudo apt-get install libmuparser-dev python3 python3-dev python3-setuptools python-setuptools libhdf5-serial-dev libomp5 libomp-dev libfftw3-dev libcfitsio-dev lcov pip3 install -r doc/pages/example_notebooks/requirements.txt # load requrements for notebooks pip3 install --upgrade Pygments - pip3 install --upgrade numpy - name: Set up the build env: CXX: ${{ matrix.config.cxx }} diff --git a/doc/pages/example_notebooks/requirements.txt b/doc/pages/example_notebooks/requirements.txt index de0d4c0fd..9c7facc62 100644 --- a/doc/pages/example_notebooks/requirements.txt +++ b/doc/pages/example_notebooks/requirements.txt @@ -1,5 +1,5 @@ # collection of all packages used in the analyis of the example notebooks. This is used for the automatic test of the notebooks -numpy +numpy==1.26.4 matplotlib pandas healpy From 892ec5b672fc3143b250f5273bab2c3e3b90d393 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Julien=20D=C3=B6rner?= Date: Wed, 3 Jul 2024 14:55:41 +0200 Subject: [PATCH 38/45] add missing include for memory --- src/magneticField/turbulentField/PlaneWaveTurbulence.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp b/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp index 1622e4067..47d2e46aa 100644 --- a/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp +++ b/src/magneticField/turbulentField/PlaneWaveTurbulence.cpp @@ -59,6 +59,7 @@ #ifdef ENABLE_FAST_WAVES #include +#include #endif namespace crpropa { From ea2352224505a9361cc3d393d04b71c7d2ea276c Mon Sep 17 00:00:00 2001 From: Michael Unger Date: Thu, 15 Aug 2024 14:49:33 -0400 Subject: [PATCH 39/45] update reference --- include/crpropa/magneticField/UF23Field.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/crpropa/magneticField/UF23Field.h b/include/crpropa/magneticField/UF23Field.h index 462ed3142..388afd5c9 100644 --- a/include/crpropa/magneticField/UF23Field.h +++ b/include/crpropa/magneticField/UF23Field.h @@ -16,7 +16,7 @@ namespace crpropa { @brief UF23Field Galactic magnetic field model Implements the eight coherent magnetic field models of UF23 - See: M. Unger and G.R. Farrar, arXiv:2311.12120 + See: M. Unger and G.R. Farrar, Astrophys.J. 970 (2024) 95, arXiv:2311.12120 Assumes a galactocentric coordinate system with the Galactic center at the origin, the x-axis pointing in the opposite direction of the From 6f5c62f90758d6872b9e12ca9f9aa2c047e3bf7a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Wed, 28 Aug 2024 08:06:32 +0200 Subject: [PATCH 40/45] add setThinning in constructor --- src/module/SynchrotronRadiation.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/module/SynchrotronRadiation.cpp b/src/module/SynchrotronRadiation.cpp index 3e002f67d..b096ed955 100644 --- a/src/module/SynchrotronRadiation.cpp +++ b/src/module/SynchrotronRadiation.cpp @@ -16,6 +16,7 @@ SynchrotronRadiation::SynchrotronRadiation(ref_ptr field, bool ha setLimit(limit); setSecondaryThreshold(1e6 * eV); setMaximumSamples(nSamples); + setThinning(thinning); } SynchrotronRadiation::SynchrotronRadiation(double Brms, bool havePhotons, double thinning, int nSamples, double limit) { @@ -25,6 +26,7 @@ SynchrotronRadiation::SynchrotronRadiation(double Brms, bool havePhotons, double setLimit(limit); setSecondaryThreshold(1e6 * eV); setMaximumSamples(nSamples); + setThinning(thinning); } void SynchrotronRadiation::setField(ref_ptr f) { From bf4fb6f52661ad97c79db901d896ac8d29c712a5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Wed, 28 Aug 2024 08:28:52 +0200 Subject: [PATCH 41/45] add simple test for SynchrotronRadiation --- test/testInteraction.cpp | 94 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 94 insertions(+) diff --git a/test/testInteraction.cpp b/test/testInteraction.cpp index f2fe49dbf..3c6f9777d 100644 --- a/test/testInteraction.cpp +++ b/test/testInteraction.cpp @@ -1144,6 +1144,100 @@ TEST(SynchrotronRadiation, interactionTag) { EXPECT_TRUE(s.getInteractionTag() == "myTag"); } +TEST(SynchrotronRadiation, simpleTestRMS) { + // test initialisation with B_rms + + // check default values + SynchrotronRadiation sync; + + EXPECT_EQ(sync.getBrms(), 0); + EXPECT_FALSE(sync.getHavePhotons()); + EXPECT_EQ(sync.getThinning(), 0); + EXPECT_EQ(sync.getLimit(), 0.1); + EXPECT_EQ(sync.getMaximumSamples(), 0); + EXPECT_EQ(sync.getSecondaryThreshold(), 1 * MeV); + + // init with custom values + double b = 1 * muG; + double thinning = 0.23; + int samples = 4; + double limit = 0.123; + SynchrotronRadiation sync2(b, true, thinning, samples, limit); + + EXPECT_EQ(sync.getBrms(), b); + EXPECT_TRUE(sync.getHavePhotons()); + EXPECT_EQ(sync.getThinning(), thinning); + EXPECT_EQ(sync.getLimit(), limit); + EXPECT_EQ(sync.getMaximumSamples(), samples); + EXPECT_EQ(sync.getSecondaryThreshold(), 1 * MeV); +} + +TEST(SynchrotronRadiation, simpleTestField) { + // test initialisation with field + + // check default values + Vector3d b(0, 0, 1 * muG); + ref_ptr field = new UniformMagneticField(b); + SynchrotronRadiation sync(field); + + EXPECT_EQ(sync.getBrms(), 0); + EXPECT_FALSE(sync.getHavePhotons()); + EXPECT_EQ(sync.getThinning(), 0); + EXPECT_EQ(sync.getLimit(), 0.1); + EXPECT_EQ(sync.getMaximumSamples(), 0); + EXPECT_EQ(sync.getSecondaryThreshold(), 1 * MeV); + Vector3d fieldAtPosition = sync.getField() -> getField(Vector3d(1, 2 , 3)); + EXPECT_EQ(fieldAtPosition.getR(), b.getR()); + + // init with custom values + double thinning = 0.23; + int samples = 4; + double limit = 0.123; + SynchrotronRadiation sync2(field, true, thinning, samples, limit); + + EXPECT_EQ(sync.getBrms(), 0); + EXPECT_TRUE(sync.getHavePhotons()); + EXPECT_EQ(sync.getThinning(), thinning); + EXPECT_EQ(sync.getLimit(), limit); + EXPECT_EQ(sync.getMaximumSamples(), samples); + EXPECT_EQ(sync.getSecondaryThreshold(), 1 * MeV); + Vector3d fieldAtPosition = sync.getField() -> getField(Vector3d(1, 2 , 3)); + EXPECT_EQ(fieldAtPosition.getR(), b.getR()); +} + +TEST(SynchrotronRadiation, getSetFunctions) { + SynchrotronRadiation sync; + + // have photons + sync.setHavePhotons(true); + EXPECT_TRUE(sync.getHavePhotons()); + + // Brms + sync.setBrms(5 * muG); + EXPECT_EQ(sync.getBrms(), 5 * muG); + + // thinning + sync.setThinning(0.345); + EXPECT_EQ(sync.getThinning(), 0.345); + + // limit + sync.setLimit(0.234); + EXPECT_EQ(sync.getLimit(), 0.234); + + // max samples + sync.setMaximumSamples(12345); + EXPECT_EQ(sync.getMaximumSamples(), 12345); + + // field + Vector3d b(1,2,3); + ref_ptr field = new UniformMagneticField(b); + sync.setField(field); + EXPECT_TRUE(field == sync.getField()); // same pointer + + // secondary threshold + sync.setSecondaryThreshold(1 * eV); + EXPECT_EQ(sync.getSecondaryThreshold(), 1 * eV); +} int main(int argc, char **argv) { ::testing::InitGoogleTest(&argc, argv); From 826dc2425b88205a5f49e6cbdf8c0933f039167d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Wed, 28 Aug 2024 09:09:42 +0200 Subject: [PATCH 42/45] add test for energy loss --- test/testInteraction.cpp | 75 +++++++++++++++++++++++++++++++++------- 1 file changed, 62 insertions(+), 13 deletions(-) diff --git a/test/testInteraction.cpp b/test/testInteraction.cpp index 3c6f9777d..7d937ad05 100644 --- a/test/testInteraction.cpp +++ b/test/testInteraction.cpp @@ -1164,12 +1164,12 @@ TEST(SynchrotronRadiation, simpleTestRMS) { double limit = 0.123; SynchrotronRadiation sync2(b, true, thinning, samples, limit); - EXPECT_EQ(sync.getBrms(), b); - EXPECT_TRUE(sync.getHavePhotons()); - EXPECT_EQ(sync.getThinning(), thinning); - EXPECT_EQ(sync.getLimit(), limit); - EXPECT_EQ(sync.getMaximumSamples(), samples); - EXPECT_EQ(sync.getSecondaryThreshold(), 1 * MeV); + EXPECT_EQ(sync2.getBrms(), b); + EXPECT_TRUE(sync2.getHavePhotons()); + EXPECT_EQ(sync2.getThinning(), thinning); + EXPECT_EQ(sync2.getLimit(), limit); + EXPECT_EQ(sync2.getMaximumSamples(), samples); + EXPECT_EQ(sync2.getSecondaryThreshold(), 1 * MeV); } TEST(SynchrotronRadiation, simpleTestField) { @@ -1195,13 +1195,13 @@ TEST(SynchrotronRadiation, simpleTestField) { double limit = 0.123; SynchrotronRadiation sync2(field, true, thinning, samples, limit); - EXPECT_EQ(sync.getBrms(), 0); - EXPECT_TRUE(sync.getHavePhotons()); - EXPECT_EQ(sync.getThinning(), thinning); - EXPECT_EQ(sync.getLimit(), limit); - EXPECT_EQ(sync.getMaximumSamples(), samples); - EXPECT_EQ(sync.getSecondaryThreshold(), 1 * MeV); - Vector3d fieldAtPosition = sync.getField() -> getField(Vector3d(1, 2 , 3)); + EXPECT_EQ(sync2.getBrms(), 0); + EXPECT_TRUE(sync2.getHavePhotons()); + EXPECT_EQ(sync2.getThinning(), thinning); + EXPECT_EQ(sync2.getLimit(), limit); + EXPECT_EQ(sync2.getMaximumSamples(), samples); + EXPECT_EQ(sync2.getSecondaryThreshold(), 1 * MeV); + fieldAtPosition = sync2.getField() -> getField(Vector3d(1, 2 , 3)); EXPECT_EQ(fieldAtPosition.getR(), b.getR()); } @@ -1239,6 +1239,55 @@ TEST(SynchrotronRadiation, getSetFunctions) { EXPECT_EQ(sync.getSecondaryThreshold(), 1 * eV); } +TEST(SynchrotronRadiation, energyLoss) { + double brms = 1 * muG; + double step = 1 * kpc; + SynchrotronRadiation sync(brms, false); + + double dE, lf, Rg, dEdx; + Candidate c(11); + c.setCurrentStep(step); + c.setNextStep(step); + double charge = eplus; + + // 1 GeV + c.current.setEnergy(1 * GeV); + lf = c.current.getLorentzFactor(); + Rg = 1 * GeV / charge / c_light / (brms * sqrt(2. / 3) ); // factor 2/3 for avg magnetic field direction. + dEdx = 1. / 6 / M_PI / epsilon0 * pow(lf * lf - 1, 2) * pow(charge / Rg, 2); // Jackson p. 770 (14.31) + dE = dEdx * step; + sync.process(&c); + EXPECT_NEAR(1 * GeV - c.current.getEnergy(), dE, 0.01 * dE); + + // 100 GeV + c.current.setEnergy(100 * GeV); + lf = c.current.getLorentzFactor(); + Rg = 100 * GeV / charge / c_light / (brms * sqrt(2. / 3) ); // factor 2/3 for avg magnetic field direction. + dEdx = 1. / 6 / M_PI / epsilon0 * pow(lf * lf - 1, 2) * pow(charge / Rg, 2); // Jackson p. 770 (14.31) + dE = dEdx * step; + sync.process(&c); + EXPECT_NEAR(100 * GeV - c.current.getEnergy(), dE, 0.01 * dE); + + // 10 TeV + c.current.setEnergy(10 * TeV); + lf = c.current.getLorentzFactor(); + Rg = 10 * TeV / charge / c_light / (brms * sqrt(2. / 3) ); // factor 2/3 for avg magnetic field direction. + dEdx = 1. / 6 / M_PI / epsilon0 * pow(lf * lf - 1, 2) * pow(charge / Rg, 2); // Jackson p. 770 (14.31) + dE = dEdx * step; + sync.process(&c); + EXPECT_NEAR(10 * TeV - c.current.getEnergy(), dE, 0.01 * dE); + + // 1 PeV + c.current.setEnergy(1 * PeV); + lf = c.current.getLorentzFactor(); + Rg = 1 * PeV / charge / c_light / (brms * sqrt(2. / 3) ); // factor 2/3 for avg magnetic field direction. + dEdx = 1. / 6 / M_PI / epsilon0 * pow(lf * lf - 1, 2) * pow(charge / Rg, 2); // Jackson p. 770 (14.31) + dE = dEdx * step; + sync.process(&c); + EXPECT_NEAR(1 * PeV - c.current.getEnergy(), dE, 0.01 * dE); +} + + int main(int argc, char **argv) { ::testing::InitGoogleTest(&argc, argv); return RUN_ALL_TESTS(); From 5246f37ec6e3acf4a307e2cdef66376875e790d5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?JulienD=C3=B6rner?= Date: Wed, 28 Aug 2024 09:49:23 +0200 Subject: [PATCH 43/45] add test for avg photon energy --- test/testInteraction.cpp | 26 ++++++++++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/test/testInteraction.cpp b/test/testInteraction.cpp index 7d937ad05..0da78c795 100644 --- a/test/testInteraction.cpp +++ b/test/testInteraction.cpp @@ -1287,6 +1287,32 @@ TEST(SynchrotronRadiation, energyLoss) { EXPECT_NEAR(1 * PeV - c.current.getEnergy(), dE, 0.01 * dE); } +TEST(SynchrotronRadiation, PhotonEnergy) { + double brms = 1 * muG; + SynchrotronRadiation sync(brms, true); + sync.setSecondaryThreshold(0.); // allow all secondaries for testing + + double E = 1 * TeV; + Candidate c(11, E); + c.setCurrentStep(10 * pc); + c.setNextStep(10 * pc); + + double lf = c.current.getLorentzFactor(); + double Rg = E / eplus / c_light / (brms * sqrt(2. / 3) ); // factor 2/3 for avg magnetic field direction. + double Ecrit = 3. / 4 * h_planck / M_PI * c_light * pow(lf, 3) / Rg; + + sync.process(&c); + EXPECT_TRUE(c.secondaries.size() > 0); // must have secondaries + + // check avg energy of the secondary photons + double Esec = 0; + for (size_t i = 0; i < c.secondaries.size(); i++) { + Esec += c.secondaries[i] -> current.getEnergy(); + } + Esec /= c.secondaries.size(); + + EXPECT_NEAR(Esec, Ecrit, Ecrit); +} int main(int argc, char **argv) { ::testing::InitGoogleTest(&argc, argv); From 976d5a5204d28201669e520885b531eab4d5abc6 Mon Sep 17 00:00:00 2001 From: JulienDoerner <32195256+JulienDoerner@users.noreply.github.com> Date: Wed, 28 Aug 2024 10:16:44 +0200 Subject: [PATCH 44/45] Update testing_OSX.yml Move to gfortran-14. (see supported versions https://github.com/actions/runner-images/blob/main/images/macos/macos-14-Readme.md) --- .github/workflows/testing_OSX.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/testing_OSX.yml b/.github/workflows/testing_OSX.yml index ffc39046f..cd0eef5af 100644 --- a/.github/workflows/testing_OSX.yml +++ b/.github/workflows/testing_OSX.yml @@ -11,7 +11,7 @@ jobs: os: macos-14 cxx: "clang++" cc: "clang" - fc: "gfortran-11" + fc: "gfortran-14" swig_builtin: "On" #uses swig 4.0.2 py: "/usr/bin/python3" steps: From 69a7e09c156bfded9a595753aa38aba88eeaf206 Mon Sep 17 00:00:00 2001 From: JulienDoerner <32195256+JulienDoerner@users.noreply.github.com> Date: Wed, 28 Aug 2024 10:21:58 +0200 Subject: [PATCH 45/45] fix numpy version to 1.26 --- .github/workflows/testing_OSX.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.github/workflows/testing_OSX.yml b/.github/workflows/testing_OSX.yml index cd0eef5af..925b85c03 100644 --- a/.github/workflows/testing_OSX.yml +++ b/.github/workflows/testing_OSX.yml @@ -19,7 +19,8 @@ jobs: uses: actions/checkout@v4 - name: Preinstall run: | - brew install hdf5 fftw cfitsio muparser libomp numpy swig + brew install hdf5 fftw cfitsio muparser libomp swig + pip install numpy==1.26 - name: Set up the build env: CXX: ${{ matrix.config.cxx }}