From 9d7da3cd76f49fe46e895cae78fad64d5f37f637 Mon Sep 17 00:00:00 2001 From: Stephane Del Pino <stephane.delpino44@gmail.com> Date: Thu, 4 Apr 2019 19:23:23 +0200 Subject: [PATCH] Continue clean-up: more template factorization --- src/mesh/Connectivity.hpp | 9 +- src/mesh/ConnectivityDispatcher.cpp | 183 ++++++++++++++-------------- src/mesh/ConnectivityDispatcher.hpp | 14 ++- 3 files changed, 109 insertions(+), 97 deletions(-) diff --git a/src/mesh/Connectivity.hpp b/src/mesh/Connectivity.hpp index b6ce4b429..23a13a78d 100644 --- a/src/mesh/Connectivity.hpp +++ b/src/mesh/Connectivity.hpp @@ -47,9 +47,12 @@ class ConnectivityDescriptor public: std::vector<std::vector<unsigned int>> cell_to_node_vector; -#warning should be set in 2d +#warning should be set in 2d only std::vector<std::vector<unsigned int>> cell_to_face_vector; - // std::vector<std::vector<unsigned int>> face_to_cell_vector; + +#warning should be set in 3d only + // std::vector<std::vector<unsigned int>> cell_to_edge_vector; + std::vector<std::vector<unsigned int>> face_to_node_vector; template <typename ItemOfItemT> @@ -59,7 +62,7 @@ class ConnectivityDescriptor return cell_to_node_vector; } else if constexpr (std::is_same_v<ItemOfItemT,FaceOfCell>) { return cell_to_face_vector; - } else if constexpr (std::is_same_v<ItemOfItemT,NodeOfCell>) { + } else if constexpr (std::is_same_v<ItemOfItemT,NodeOfFace>) { return face_to_node_vector; } else { static_assert(is_false_v<ItemOfItemT>, "Unexpected item of item type"); diff --git a/src/mesh/ConnectivityDispatcher.cpp b/src/mesh/ConnectivityDispatcher.cpp index 88b2238cb..8406ca9e2 100644 --- a/src/mesh/ConnectivityDispatcher.cpp +++ b/src/mesh/ConnectivityDispatcher.cpp @@ -46,6 +46,20 @@ ConnectivityDispatcher<Dimension>::_buildNewOwner() } } +template <int Dimension> +template <ItemType item_type> +void ConnectivityDispatcher<Dimension>:: +_buildItemToExchangeLists() +{ + this->_buildItemListToSend<item_type>(); + this->_buildNumberOfItemToExchange<item_type>(); + + if constexpr (item_type == ItemType::cell) { + this->_buildCellNumberIdMap(); + } + this->_buildRecvItemIdCorrespondanceByProc<item_type>(); +} + template <int Dimension> template <ItemType item_type> void @@ -116,17 +130,22 @@ ConnectivityDispatcher<Dimension>::_buildItemListToSend() } template <int Dimension> -Array<const unsigned int> -ConnectivityDispatcher<Dimension>::_buildNbCellToSend() +template <ItemType item_type> +void +ConnectivityDispatcher<Dimension>::_buildNumberOfItemToExchange() { - const auto& item_list_to_send_by_proc = this->_dispatchedInfo<ItemType::cell>().m_list_to_send_by_proc; - Array<unsigned int> nb_cell_to_send_by_proc(parallel::size()); + const auto& item_list_to_send_by_proc = this->_dispatchedInfo<item_type>().m_list_to_send_by_proc; + Array<unsigned int> nb_item_to_send_by_proc(parallel::size()); for (size_t i=0; i<parallel::size(); ++i) { - nb_cell_to_send_by_proc[i] = item_list_to_send_by_proc[i].size(); + nb_item_to_send_by_proc[i] = item_list_to_send_by_proc[i].size(); } - return nb_cell_to_send_by_proc; + this->_dispatchedInfo<item_type>().m_list_to_send_size_by_proc = nb_item_to_send_by_proc; + + this->_dispatchedInfo<item_type>().m_list_to_recv_size_by_proc + = parallel::allToAll(nb_item_to_send_by_proc); } + template <int Dimension> template<typename DataType, ItemType item_type, typename ConnectivityPtr> void @@ -307,6 +326,42 @@ _getRecvItemSubItemNumberingByProc(const std::vector<Array<const int>>& recv_num return const_recv_item_sub_item_numbering_by_proc; } +template <int Dimension> +template <typename ItemOfItemT> +void +ConnectivityDispatcher<Dimension>:: +_buildItemToItemDescriptor() +{ + constexpr ItemType item_type = ItemOfItemT::item_type; + constexpr ItemType sub_item_type = ItemOfItemT::sub_item_type; + + const auto& item_list_to_recv_size_by_proc = + this->_dispatchedInfo<item_type>().m_list_to_recv_size_by_proc; + + const auto& recv_number_of_item_per_item_by_proc = + this->_dispatchedInfo<ItemOfItemT>().m_recv_number_of_item_per_item_by_proc; + + const auto& sub_item_number_id_map = + this->_dispatchedInfo<sub_item_type>().m_number_to_id_map; + + const auto& recv_item_of_item_numbers_by_proc = + this->_dispatchedInfo<ItemOfItemT>().m_recv_item_of_item_numbers_by_proc; + + for (size_t i_rank=0; i_rank < parallel::size(); ++i_rank) { + int l=0; + for (size_t i=0; i<item_list_to_recv_size_by_proc[i_rank]; ++i) { + std::vector<unsigned int> sub_item_vector; + for (int k=0; k<recv_number_of_item_per_item_by_proc[i_rank][i]; ++k) { + const auto& searched_sub_item_id = + sub_item_number_id_map.find(recv_item_of_item_numbers_by_proc[i_rank][l++]); + Assert(searched_sub_item_id != sub_item_number_id_map.end()); + sub_item_vector.push_back(searched_sub_item_id->second); + } + m_new_descriptor.itemOfItemVector<ItemOfItemT>().emplace_back(sub_item_vector); + } + } +} + template <int Dimension> template <ItemType item_type> void @@ -359,74 +414,40 @@ ConnectivityDispatcher<Dimension>::_dispatchFaces() this->_dispatchedInfo<FaceOfCell>().m_recv_number_of_item_per_item_by_proc = _getRecvNumberOfSubItemPerItemByProc<FaceOfCell>(); - const auto& recv_number_of_face_per_cell_by_proc = - this->_dispatchedInfo<FaceOfCell>().m_recv_number_of_item_per_item_by_proc; - - std::vector<Array<const int>> recv_cell_face_numbering_by_proc - = this->_getRecvItemSubItemNumberingByProc<FaceOfCell>(recv_number_of_face_per_cell_by_proc); - - this->_buildSubItemNumberToIdMap<FaceOfCell>(recv_cell_face_numbering_by_proc); + { + const auto& recv_number_of_face_per_cell_by_proc = + this->_dispatchedInfo<FaceOfCell>().m_recv_number_of_item_per_item_by_proc; - const std::unordered_map<int, int>& face_number_id_map = - this->_dispatchedInfo<ItemType::face>().m_number_to_id_map; + std::vector<Array<const int>>& recv_cell_face_numbering_by_proc + = this->_dispatchedInfo<FaceOfCell>().m_recv_item_of_item_numbers_by_proc; - this->_buildItemListToSend<ItemType::face>(); + recv_cell_face_numbering_by_proc = + this->_getRecvItemSubItemNumberingByProc<FaceOfCell>(recv_number_of_face_per_cell_by_proc); -#warning this patterns repeats for each item type. Should be factorized - Array<unsigned int> nb_face_to_send_by_proc(parallel::size()); - for (size_t i_rank=0; i_rank<parallel::size(); ++i_rank) { - nb_face_to_send_by_proc[i_rank] = m_dispatched_face_info.m_list_to_send_by_proc[i_rank].size(); + this->_buildSubItemNumberToIdMap<FaceOfCell>(recv_cell_face_numbering_by_proc); } - this->_dispatchedInfo<ItemType::face>().m_list_to_recv_size_by_proc - = parallel::allToAll(nb_face_to_send_by_proc); - this->_buildRecvItemIdCorrespondanceByProc<ItemType::face>(); + this->_buildItemToExchangeLists<ItemType::face>(); + this->_gatherFrom(m_connectivity.template number<ItemType::face>(), m_new_descriptor.face_number_vector); - { - const auto& cell_list_to_recv_size_by_proc = - this->_dispatchedInfo<ItemType::cell>().m_list_to_recv_size_by_proc; - const auto& recv_number_of_face_per_cell_by_proc = - this->_dispatchedInfo<FaceOfCell>().m_recv_number_of_item_per_item_by_proc; - - for (size_t i_rank=0; i_rank < parallel::size(); ++i_rank) { - int l=0; - for (size_t i=0; i<cell_list_to_recv_size_by_proc[i_rank]; ++i) { - std::vector<unsigned int> face_vector; - for (int k=0; k<recv_number_of_face_per_cell_by_proc[i_rank][i]; ++k) { - const auto& searched_face_id = face_number_id_map.find(recv_cell_face_numbering_by_proc[i_rank][l++]); - Assert(searched_face_id != face_number_id_map.end()); - face_vector.push_back(searched_face_id->second); - } - m_new_descriptor.itemOfItemVector<FaceOfCell>().emplace_back(face_vector); - } - } - } + this->_buildItemToItemDescriptor<FaceOfCell>(); this->_gatherFrom(m_connectivity.cellFaceIsReversed(), m_new_descriptor.cell_face_is_reversed_vector); this->_gatherFrom(this->_dispatchedInfo<ItemType::face>().m_new_owner, m_new_descriptor.face_owner_vector); { - std::vector<Array<const int>> recv_number_of_node_per_face_by_proc = + auto& recv_number_of_node_per_face_by_proc = + this->_dispatchedInfo<NodeOfFace>().m_recv_number_of_item_per_item_by_proc; + + recv_number_of_node_per_face_by_proc = _getRecvNumberOfSubItemPerItemByProc<NodeOfFace>(); - std::vector<Array<const int>> recv_face_node_numbering_by_proc + this->_dispatchedInfo<NodeOfFace>().m_recv_item_of_item_numbers_by_proc = this->_getRecvItemSubItemNumberingByProc<NodeOfFace>(recv_number_of_node_per_face_by_proc); - const auto& node_number_id_map = this->_dispatchedInfo<ItemType::node>().m_number_to_id_map; - for (size_t i_rank=0; i_rank < parallel::size(); ++i_rank) { - int l=0; - for (size_t i=0; i<recv_number_of_node_per_face_by_proc[i_rank].size(); ++i) { - std::vector<unsigned int> node_vector; - for (int k=0; k<recv_number_of_node_per_face_by_proc[i_rank][i]; ++k) { - const auto& searched_node_id = node_number_id_map.find(recv_face_node_numbering_by_proc[i_rank][l++]); - Assert(searched_node_id != node_number_id_map.end()); - node_vector.push_back(searched_node_id->second); - } - m_new_descriptor.face_to_node_vector.emplace_back(node_vector); - } - } + this->_buildItemToItemDescriptor<NodeOfFace>(); } // Getting references @@ -536,8 +557,11 @@ ConnectivityDispatcher<Dimension>::_dispatchFaces() } } + const auto& nb_face_to_send_by_proc = + this->_dispatchedInfo<ItemType::face>().m_list_to_send_size_by_proc; const auto& send_face_id_by_proc = m_dispatched_face_info.m_list_to_send_by_proc; std::vector<Array<const block_type>> send_face_refs_by_proc(parallel::size()); + for (size_t i_rank=0; i_rank<parallel::size(); ++i_rank) { Array<block_type> send_face_refs(nb_face_to_send_by_proc[i_rank]); const Array<const FaceId> send_face_id = send_face_id_by_proc[i_rank]; @@ -598,32 +622,25 @@ ConnectivityDispatcher<Dimension>::ConnectivityDispatcher(const ConnectivityType // this->_buildNewOwner<ItemType::edge>(); this->_buildNewOwner<ItemType::node>(); - this->_buildItemListToSend<ItemType::cell>(); - this->_dispatchedInfo<ItemType::cell>().m_list_to_recv_size_by_proc - = parallel::allToAll(this->_buildNbCellToSend()); + this->_buildItemToExchangeLists<ItemType::cell>(); - this->_buildCellNumberIdMap(); + auto& recv_number_of_node_per_cell_by_proc= + this->_dispatchedInfo<NodeOfCell>().m_recv_number_of_item_per_item_by_proc; - const std::vector<Array<const int>> recv_number_of_node_per_cell_by_proc + recv_number_of_node_per_cell_by_proc = this->_getRecvNumberOfSubItemPerItemByProc<NodeOfCell>(); - const std::vector<Array<const int>> recv_cell_node_numbering_by_proc + auto& recv_cell_node_numbering_by_proc = + this->_dispatchedInfo<NodeOfCell>().m_recv_item_of_item_numbers_by_proc; + + recv_cell_node_numbering_by_proc = this->_getRecvItemSubItemNumberingByProc<NodeOfCell>(recv_number_of_node_per_cell_by_proc); - this->_buildRecvItemIdCorrespondanceByProc<ItemType::cell>(); this->_gatherFrom(m_connectivity.template number<ItemType::cell>(), m_new_descriptor.cell_number_vector); this->_buildSubItemNumberToIdMap<NodeOfCell>(recv_cell_node_numbering_by_proc); - this->_buildItemListToSend<ItemType::node>(); - Array<unsigned int> nb_node_to_send_by_proc(parallel::size()); - for (size_t i_rank=0; i_rank<parallel::size(); ++i_rank) { - nb_node_to_send_by_proc[i_rank] = m_dispatched_node_info.m_list_to_send_by_proc[i_rank].size(); - } - this->_dispatchedInfo<ItemType::node>().m_list_to_recv_size_by_proc - = parallel::allToAll(nb_node_to_send_by_proc); - - this->_buildRecvItemIdCorrespondanceByProc<ItemType::node>(); + this->_buildItemToExchangeLists<ItemType::node>(); // Fill new descriptor this->_gatherFrom(m_connectivity.cellType(), m_new_descriptor.cell_type_vector); @@ -632,24 +649,8 @@ ConnectivityDispatcher<Dimension>::ConnectivityDispatcher(const ConnectivityType this->_gatherFrom(m_connectivity.template number<ItemType::node>(), m_new_descriptor.node_number_vector); this->_gatherFrom(this->_dispatchedInfo<ItemType::node>().m_new_owner, m_new_descriptor.node_owner_vector); - { // build cells connectivity - const auto& cell_list_to_recv_size_by_proc = - this->_dispatchedInfo<ItemType::cell>().m_list_to_recv_size_by_proc; - - const auto& node_number_id_map = this->_dispatchedInfo<ItemType::node>().m_number_to_id_map; - for (size_t i_rank=0; i_rank < parallel::size(); ++i_rank) { - int l=0; - for (size_t i=0; i<cell_list_to_recv_size_by_proc[i_rank]; ++i) { - std::vector<unsigned int> node_vector; - for (int k=0; k<recv_number_of_node_per_cell_by_proc[i_rank][i]; ++k) { - const auto& searched_node_id = node_number_id_map.find(recv_cell_node_numbering_by_proc[i_rank][l++]); - Assert(searched_node_id != node_number_id_map.end()); - node_vector.push_back(searched_node_id->second); - } - m_new_descriptor.cell_to_node_vector.emplace_back(node_vector); - } - } - } + this->_buildItemToItemDescriptor<NodeOfCell>(); + this->_dispatchFaces(); m_dispatched_connectivity = ConnectivityType::build(m_new_descriptor); diff --git a/src/mesh/ConnectivityDispatcher.hpp b/src/mesh/ConnectivityDispatcher.hpp index 43dd2e75f..a893c8151 100644 --- a/src/mesh/ConnectivityDispatcher.hpp +++ b/src/mesh/ConnectivityDispatcher.hpp @@ -23,8 +23,8 @@ class ConnectivityDispatcher { using ItemId = ItemIdT<item_type>; ItemValue<const int, item_type> m_new_owner; + Array<const unsigned int> m_list_to_send_size_by_proc; std::vector<Array<const ItemId>> m_list_to_send_by_proc; -#warning is m_list_to_recv_size_by_proc really necessary? Array<const unsigned int> m_list_to_recv_size_by_proc; std::unordered_map<int, int> m_number_to_id_map; std::vector<Array<const ItemId>> m_recv_id_correspondance_by_proc; @@ -69,6 +69,7 @@ class ConnectivityDispatcher struct DispatchedItemOfItemInfo { std::vector<Array<const int>> m_recv_number_of_item_per_item_by_proc; + std::vector<Array<const int>> m_recv_item_of_item_numbers_by_proc; }; DispatchedItemOfItemInfo<NodeOfCell> m_dispatched_node_of_cell_info; @@ -159,13 +160,20 @@ class ConnectivityDispatcher template <ItemType item_type> void _buildItemListToSend(); - Array<const unsigned int> _buildNbCellToSend(); - void _buildCellNumberIdMap(); template <typename ItemOfItemT> void _buildSubItemNumberToIdMap(const std::vector<Array<const int>>& recv_cell_node_number_by_proc); + template <ItemType item_type> + void _buildItemToExchangeLists(); + + template <ItemType item_type> + void _buildNumberOfItemToExchange(); + + template <typename ItemOfItemT> + void _buildItemToItemDescriptor(); + void _dispatchFaces(); template<typename DataType, ItemType item_type, typename ConnectivityPtr> -- GitLab