diff --git a/CMakeLists_files.cmake b/CMakeLists_files.cmake index d09e6ae60..170197c02 100644 --- a/CMakeLists_files.cmake +++ b/CMakeLists_files.cmake @@ -54,6 +54,7 @@ list (APPEND MAIN_SOURCE_FILES opm/grid/UnstructuredGrid.c opm/grid/grid_equal.cpp opm/grid/utility/compressedToCartesian.cpp + opm/grid/utility/cartesianToCompressed.cpp opm/grid/utility/StopWatch.cpp opm/grid/utility/WachspressCoord.cpp ) @@ -100,6 +101,7 @@ list (APPEND TEST_SOURCE_FILES tests/test_repairzcorn.cpp tests/test_sparsetable.cpp tests/test_quadratures.cpp + tests/test_compressed_cartesian_mapping.cpp ) if(HAVE_ECL_INPUT) @@ -204,6 +206,7 @@ list (APPEND PUBLIC_HEADER_FILES opm/grid/transmissibility/TransTpfa_impl.hpp opm/grid/utility/CompressedPropertyAccess.hpp opm/grid/utility/compressedToCartesian.hpp + opm/grid/utility/cartesianToCompressed.hpp opm/grid/utility/extractPvtTableIndex.hpp opm/grid/utility/RegionMapping.hpp opm/grid/utility/SparseTable.hpp diff --git a/opm/grid/utility/cartesianToCompressed.cpp b/opm/grid/utility/cartesianToCompressed.cpp new file mode 100644 index 000000000..526a79467 --- /dev/null +++ b/opm/grid/utility/cartesianToCompressed.cpp @@ -0,0 +1,53 @@ +/* + Copyright 2018 SINTEF Digital, Mathematics & Cybernetics. + + This file is part of the Open Porous Media project (OPM). + + OPM is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OPM is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with OPM. If not, see . +*/ + + +#include + +namespace Opm +{ + + // Construct explicit mapping from local cartesian to active/compressed + // indices, either based on global_cell or as { 0, 1, 2, ....} if null. + // \param[in] num_cartesian_cells The number of cartesian cells. + // \param[in] global_cell Either null, or an array of size num_cells. + // \return A unordered_map containing the mapping from local cartesian + // to active/compressed, + // or the map { {0, 0}, {1, 1}, ... , {num_cells - 1, num_cells - 1} } + // if global_cell was null. + std::unordered_map cartesianToCompressed(const int num_cells, + const int* global_cell) + { + std::unordered_map retval; + retval.max_load_factor(0.9); + retval.reserve(num_cells); + if (global_cell) { + for (int i = 0; i < num_cells; ++i) { + retval.insert({global_cell[i], i}); + } + } else { + for (int i = 0; i < num_cells; ++i) { + retval.insert({i, i}); + } + } + return retval; + } + + +} // namespace Opm diff --git a/opm/grid/utility/cartesianToCompressed.hpp b/opm/grid/utility/cartesianToCompressed.hpp new file mode 100644 index 000000000..58f89362c --- /dev/null +++ b/opm/grid/utility/cartesianToCompressed.hpp @@ -0,0 +1,41 @@ +/* + Copyright 2018 SINTEF Digital, Mathematics & Cybernetics. + + This file is part of the Open Porous Media project (OPM). + + OPM is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OPM is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with OPM. If not, see . +*/ + +#ifndef OPM_CARTESIANTOCOMPRESSED_HEADER_INCLUDED +#define OPM_CARTESIANTOCOMPRESSED_HEADER_INCLUDED + +#include + +namespace Opm +{ + + // Construct explicit mapping from local cartesian to active/compressed + // indices, either based on global_cell or as { 0, 1, 2, ....} if null. + // \param[in] num_cartesian_cells The number of cartesian cells. + // \param[in] global_cell Either null, or an array of size num_cells. + // \return A unordered_map containing the mapping from local cartesian + // to active/compressed, + // or the map { {0, 0}, {1, 1}, ... , {num_cells - 1, num_cells - 1} } + // if global_cell was null. + std::unordered_map cartesianToCompressed(const int num_cells, + const int* global_cell); + +} // namespace Opm + +#endif // OPM_CARTESIANTOCOMPRESSED_HEADER_INCLUDED diff --git a/tests/test_compressed_cartesian_mapping.cpp b/tests/test_compressed_cartesian_mapping.cpp new file mode 100644 index 000000000..da003c440 --- /dev/null +++ b/tests/test_compressed_cartesian_mapping.cpp @@ -0,0 +1,71 @@ +/* + Copyright 2018 SINTEF ICT, Applied Mathematics. + + This file is part of the Open Porous Media project (OPM). + + OPM is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OPM is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with OPM. If not, see . +*/ + +#include + +#define BOOST_TEST_MODULE mappingTest + +#include + +#include +#include + +BOOST_AUTO_TEST_CASE(mapping) +{ + const std::vector global_cell{0, 1, 2, 3, 5, 6, 8, 9}; + const int num_cells = global_cell.size(); + + const std::unordered_map cartesian_to_compressed = + Opm::cartesianToCompressed(num_cells, global_cell.data()); + + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(0), 0); + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(1), 1); + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(2), 2); + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(3), 3); + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(5), 4); + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(6), 5); + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(8), 6); + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(9), 7); + + const int non_existing_index = 1829; + BOOST_CHECK_THROW(cartesian_to_compressed.at(non_existing_index), std::out_of_range); + + const std::vector compressed_to_cartesian = Opm::compressedToCartesian(num_cells, global_cell.data()); + + BOOST_CHECK_EQUAL_COLLECTIONS(compressed_to_cartesian.begin(), compressed_to_cartesian.end(), + global_cell.begin(), global_cell.end()); +} + +BOOST_AUTO_TEST_CASE(nullmapping) +{ + const int num_cells = 30; + + const std::unordered_map cartesian_to_compressed = + Opm::cartesianToCompressed(num_cells, nullptr); + + for (int i = 0; i < num_cells; ++i) { + BOOST_CHECK_EQUAL(cartesian_to_compressed.at(i), i); + } + + const std::vector compressed_to_cartesian = Opm::compressedToCartesian(num_cells, nullptr); + + for (int i = 0; i < num_cells; ++i) { + BOOST_CHECK_EQUAL(compressed_to_cartesian[i], i); + } +}