Skip to content
Snippets Groups Projects

Reduce memory use and allocations for some connectivity descriptors

2 files
+ 312
1
Compare changes
  • Side-by-side
  • Inline

Files

+ 111
100
#include <mesh/Connectivity.hpp>
#include <mesh/ConnectivityDescriptor.hpp>
#include <mesh/ItemValueUtils.hpp>
#include <utils/Messenger.hpp>
#include <map>
@@ -31,17 +32,10 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
m_cell_type = cell_type;
}
{
WeakCellValue<int> cell_number(*this);
cell_number = convert_to_array(descriptor.cell_number_vector);
m_cell_number = cell_number;
}
m_cell_number = WeakCellValue<int>(*this, convert_to_array(descriptor.cell_number_vector));
{
WeakNodeValue<int> node_number(*this);
node_number = convert_to_array(descriptor.node_number_vector);
m_node_number = node_number;
}
Array node_number_array = convert_to_array(descriptor.node_number_vector);
m_node_number = WeakNodeValue<int>(*this, node_number_array);
{
WeakCellValue<int> cell_global_index(*this);
@@ -51,11 +45,7 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
m_cell_global_index = cell_global_index;
}
{
WeakCellValue<int> cell_owner(*this);
cell_owner = convert_to_array(descriptor.cell_owner_vector);
m_cell_owner = cell_owner;
}
m_cell_owner = WeakCellValue<int>(*this, convert_to_array(descriptor.cell_owner_vector));
{
const int rank = parallel::rank();
@@ -65,15 +55,13 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
m_cell_is_owned = cell_is_owned;
}
{
WeakNodeValue<int> node_owner(*this);
node_owner = convert_to_array(descriptor.node_owner_vector);
m_node_owner = node_owner;
}
Array node_owner_array = convert_to_array(descriptor.node_owner_vector);
m_node_owner = WeakNodeValue<int>{*this, node_owner_array};
Array<bool> node_is_owned_array(this->numberOfNodes());
{
const int rank = parallel::rank();
WeakNodeValue<bool> node_is_owned(*this);
WeakNodeValue<bool> node_is_owned(*this, node_is_owned_array);
parallel_for(
this->numberOfNodes(), PUGS_LAMBDA(NodeId r) { node_is_owned[r] = (m_node_owner[r] == rank); });
m_node_is_owned = node_is_owned;
@@ -84,46 +72,14 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
if constexpr (Dimension == 1) {
// faces are similar to nodes
{
WeakFaceValue<int> face_number(*this);
face_number = convert_to_array(descriptor.node_number_vector);
m_face_number = face_number;
}
{
WeakFaceValue<int> face_owner(*this);
face_owner = convert_to_array(descriptor.node_owner_vector);
m_face_owner = face_owner;
}
{
const int rank = parallel::rank();
WeakFaceValue<bool> face_is_owned(*this);
parallel_for(
this->numberOfFaces(), PUGS_LAMBDA(FaceId l) { face_is_owned[l] = (m_face_owner[l] == rank); });
m_face_is_owned = face_is_owned;
}
m_face_number = WeakFaceValue<int>(*this, node_number_array);
m_face_owner = WeakFaceValue<int>(*this, node_owner_array);
m_face_is_owned = WeakFaceValue<bool>(*this, node_is_owned_array);
// edges are similar to nodes
{
WeakEdgeValue<int> edge_number(*this);
edge_number = convert_to_array(descriptor.node_number_vector);
m_edge_number = edge_number;
}
{
WeakEdgeValue<int> edge_owner(*this);
edge_owner = convert_to_array(descriptor.node_owner_vector);
m_edge_owner = edge_owner;
}
{
const int rank = parallel::rank();
WeakEdgeValue<bool> edge_is_owned(*this);
parallel_for(
this->numberOfEdges(), PUGS_LAMBDA(EdgeId l) { edge_is_owned[l] = (m_edge_owner[l] == rank); });
m_edge_is_owned = edge_is_owned;
}
m_edge_number = WeakEdgeValue<int>(*this, node_number_array);
m_edge_owner = WeakEdgeValue<int>(*this, node_owner_array);
m_edge_is_owned = WeakEdgeValue<bool>(*this, node_is_owned_array);
} else {
m_item_to_item_matrix[itemTId(ItemType::face)][itemTId(ItemType::node)] = descriptor.face_to_node_vector;
@@ -140,21 +96,16 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
m_cell_face_is_reversed = cell_face_is_reversed;
}
{
WeakFaceValue<int> face_number(*this);
face_number = convert_to_array(descriptor.face_number_vector);
m_face_number = face_number;
}
Array face_number_array = convert_to_array(descriptor.face_number_vector);
m_face_number = WeakFaceValue<int>(*this, face_number_array);
{
WeakFaceValue<int> face_owner(*this);
face_owner = convert_to_array(descriptor.face_owner_vector);
m_face_owner = face_owner;
}
Array face_owner_array = convert_to_array(descriptor.face_owner_vector);
m_face_owner = WeakFaceValue<int>(*this, face_owner_array);
Array<bool> face_is_owned_array(this->numberOfFaces());
{
const int rank = parallel::rank();
WeakFaceValue<bool> face_is_owned(*this);
WeakFaceValue<bool> face_is_owned(*this, face_is_owned_array);
parallel_for(
this->numberOfFaces(), PUGS_LAMBDA(FaceId l) { face_is_owned[l] = (m_face_owner[l] == rank); });
m_face_is_owned = face_is_owned;
@@ -164,25 +115,9 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
if constexpr (Dimension == 2) {
// edges are similar to faces
{
WeakEdgeValue<int> edge_number(*this);
edge_number = convert_to_array(descriptor.face_number_vector);
m_edge_number = edge_number;
}
{
WeakEdgeValue<int> edge_owner(*this);
edge_owner = convert_to_array(descriptor.face_owner_vector);
m_edge_owner = edge_owner;
}
{
const int rank = parallel::rank();
WeakEdgeValue<bool> edge_is_owned(*this);
parallel_for(
this->numberOfEdges(), PUGS_LAMBDA(EdgeId l) { edge_is_owned[l] = (m_edge_owner[l] == rank); });
m_edge_is_owned = edge_is_owned;
}
m_edge_number = WeakEdgeValue<int>(*this, face_number_array);
m_edge_owner = WeakEdgeValue<int>(*this, face_owner_array);
m_edge_is_owned = WeakEdgeValue<bool>(*this, face_is_owned_array);
} else {
m_item_to_item_matrix[itemTId(ItemType::edge)][itemTId(ItemType::node)] = descriptor.edge_to_node_vector;
@@ -202,17 +137,8 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
m_face_edge_is_reversed = face_edge_is_reversed;
}
{
WeakEdgeValue<int> edge_number(*this);
edge_number = convert_to_array(descriptor.edge_number_vector);
m_edge_number = edge_number;
}
{
WeakEdgeValue<int> edge_owner(*this);
edge_owner = convert_to_array(descriptor.edge_owner_vector);
m_edge_owner = edge_owner;
}
m_edge_number = WeakEdgeValue<int>(*this, convert_to_array(descriptor.edge_number_vector));
m_edge_owner = WeakEdgeValue<int>(*this, convert_to_array(descriptor.edge_owner_vector));
{
const int rank = parallel::rank();
@@ -227,6 +153,91 @@ Connectivity<Dimension>::_buildFrom(const ConnectivityDescriptor& descriptor)
}
}
template <size_t Dimension>
void
Connectivity<Dimension>::_buildIsBoundaryFace() const
{
Array<bool> is_face_boundary_array(this->numberOfFaces());
WeakFaceValue<bool> is_boundary_face(*this, is_face_boundary_array);
const auto& face_to_cell_matrix = this->faceToCellMatrix();
const auto& face_is_owned = this->faceIsOwned();
parallel_for(
this->numberOfFaces(), PUGS_LAMBDA(const FaceId face_id) {
is_boundary_face[face_id] = face_is_owned[face_id] and (face_to_cell_matrix[face_id].size() == 1);
});
synchronize(is_boundary_face);
const_cast<WeakFaceValue<const bool>&>(m_is_boundary_face) = is_boundary_face;
if constexpr (Dimension <= 2) {
const_cast<WeakEdgeValue<const bool>&>(m_is_boundary_edge) = WeakEdgeValue<bool>(*this, is_face_boundary_array);
if constexpr (Dimension == 1) {
const_cast<WeakNodeValue<const bool>&>(m_is_boundary_node) = WeakNodeValue<bool>(*this, is_face_boundary_array);
} else {
static_assert(Dimension == 2, "unexpected dimension");
}
}
}
template <size_t Dimension>
void
Connectivity<Dimension>::_buildIsBoundaryEdge() const
{
if constexpr (Dimension < 3) {
this->_buildIsBoundaryFace();
} else {
auto is_boundary_face = this->isBoundaryFace();
WeakEdgeValue<bool> is_boundary_edge(*this);
is_boundary_edge.fill(false);
const auto& face_to_edge_matrix = this->faceToEdgeMatrix();
for (FaceId face_id = 0; face_id < this->numberOfFaces(); ++face_id) {
if (is_boundary_face[face_id]) {
auto face_edge = face_to_edge_matrix[face_id];
for (size_t i_edge = 0; i_edge < face_edge.size(); ++i_edge) {
is_boundary_edge[face_edge[i_edge]] = true;
}
}
}
synchronize(is_boundary_edge);
const_cast<WeakEdgeValue<const bool>&>(m_is_boundary_edge) = is_boundary_edge;
}
}
template <size_t Dimension>
void
Connectivity<Dimension>::_buildIsBoundaryNode() const
{
if constexpr (Dimension == 1) {
this->_buildIsBoundaryFace();
} else {
auto is_boundary_face = this->isBoundaryFace();
WeakNodeValue<bool> is_boundary_node(*this);
is_boundary_node.fill(false);
const auto& face_to_node_matrix = this->faceToNodeMatrix();
for (FaceId face_id = 0; face_id < this->numberOfFaces(); ++face_id) {
if (is_boundary_face[face_id]) {
auto face_nodes = face_to_node_matrix[face_id];
for (size_t i_node = 0; i_node < face_nodes.size(); ++i_node) {
is_boundary_node[face_nodes[i_node]] = true;
}
}
}
synchronize(is_boundary_node);
const_cast<WeakNodeValue<const bool>&>(m_is_boundary_node) = is_boundary_node;
}
}
template void Connectivity<1>::_buildIsBoundaryFace() const;
template void Connectivity<2>::_buildIsBoundaryFace() const;
template void Connectivity<3>::_buildIsBoundaryFace() const;
template void Connectivity<1>::_buildIsBoundaryEdge() const;
template void Connectivity<2>::_buildIsBoundaryEdge() const;
template void Connectivity<3>::_buildIsBoundaryEdge() const;
template void Connectivity<1>::_buildIsBoundaryNode() const;
template void Connectivity<2>::_buildIsBoundaryNode() const;
template void Connectivity<3>::_buildIsBoundaryNode() const;
template Connectivity<1>::Connectivity();
template Connectivity<2>::Connectivity();
template Connectivity<3>::Connectivity();
Loading