LCOV - code coverage report
Current view: top level - src/utils - location_maps.C (source / functions) Hit Total Coverage
Test: libMesh/libmesh: #4640 (c5f9f0) with base a68dd6 Lines: 37 55 67.3 %
Date: 2026-11-02 23:02:27 Functions: 6 12 50.0 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : // The libMesh Finite Element Library.
       2             : // Copyright (C) 2002-2026 Benjamin S. Kirk, John W. Peterson, Roy H. Stogner
       3             : 
       4             : // This library is free software; you can redistribute it and/or
       5             : // modify it under the terms of the GNU Lesser General Public
       6             : // License as published by the Free Software Foundation; either
       7             : // version 2.1 of the License, or (at your option) any later version.
       8             : 
       9             : // This library 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 GNU
      12             : // Lesser General Public License for more details.
      13             : 
      14             : // You should have received a copy of the GNU Lesser General Public
      15             : // License along with this library; if not, write to the Free Software
      16             : // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
      17             : 
      18             : 
      19             : 
      20             : // Local Includes
      21             : #include "libmesh/elem.h"
      22             : #include "libmesh/libmesh_logging.h"
      23             : #include "libmesh/location_maps.h"
      24             : #include "libmesh/mesh_base.h"
      25             : #include "libmesh/mesh_tools.h"
      26             : #include "libmesh/node.h"
      27             : #include "libmesh/parallel.h"
      28             : 
      29             : // C++ Includes
      30             : #include <limits>
      31             : #include <utility>
      32             : 
      33             : namespace
      34             : {
      35             : using libMesh::Real;
      36             : 
      37             : // 10 bits per coordinate, to work with 32+ bit machines
      38             : const unsigned int chunkmax = 1024;
      39             : const Real chunkfloat = 1024.0;
      40             : }
      41             : 
      42             : 
      43             : 
      44             : namespace libMesh
      45             : {
      46             : 
      47             : template <typename T>
      48          71 : void LocationMap<T>::init(MeshBase & mesh)
      49             : {
      50             :   // This function must be run on all processors at once
      51             :   // for non-serial meshes
      52          71 :   if (!mesh.is_serial())
      53           0 :     libmesh_parallel_only(mesh.comm());
      54             : 
      55           6 :   LOG_SCOPE("init()", "LocationMap");
      56             : 
      57             :   // Clear the old map
      58           2 :   _map.clear();
      59             : 
      60             :   // Cache a bounding box
      61          71 :   _bbox = MeshTools::create_nodal_bounding_box(mesh);
      62             : 
      63          71 :   this->fill(mesh);
      64          71 : }
      65             : 
      66             : 
      67             : 
      68             : template <typename T>
      69       17360 : void LocationMap<T>::insert(T & t)
      70             : {
      71       17360 :   this->_map.emplace(this->key(this->point_of(t)), &t);
      72       17360 : }
      73             : 
      74             : 
      75             : 
      76             : template <>
      77       43848 : Point LocationMap<Node>::point_of(const Node & node) const
      78             : {
      79       43848 :   return node;
      80             : }
      81             : 
      82             : 
      83             : 
      84             : template <>
      85           0 : Point LocationMap<Elem>::point_of(const Elem & elem) const
      86             : {
      87           0 :   return elem.vertex_average();
      88             : }
      89             : 
      90             : 
      91             : 
      92             : template <typename T>
      93       13244 : T * LocationMap<T>::find(const Point & p,
      94             :                          const Real tol)
      95             : {
      96        1029 :   LOG_SCOPE("find()", "LocationMap");
      97             : 
      98             :   // Look for a likely key in the multimap
      99       13244 :   unsigned int pointkey = this->key(p);
     100             : 
     101             :   // Look for the exact key first
     102       13244 :   for (const auto & pr : as_range(_map.equal_range(pointkey)))
     103       13587 :     if (p.absolute_fuzzy_equals(this->point_of(*(pr.second)), tol))
     104       13244 :       return pr.second;
     105             : 
     106             :   // Look for neighboring bins' keys next
     107           0 :   for (int xoffset = -1; xoffset != 2; ++xoffset)
     108             :     {
     109           0 :       for (int yoffset = -1; yoffset != 2; ++yoffset)
     110             :         {
     111           0 :           for (int zoffset = -1; zoffset != 2; ++zoffset)
     112             :             {
     113           0 :               auto key_pos = _map.equal_range(pointkey +
     114           0 :                                               xoffset*chunkmax*chunkmax +
     115           0 :                                               yoffset*chunkmax +
     116           0 :                                               zoffset);
     117           0 :               for (const auto & pr : as_range(key_pos))
     118           0 :                 if (p.absolute_fuzzy_equals(this->point_of(*(pr.second)), tol))
     119           0 :                   return pr.second;
     120             :             }
     121             :         }
     122             :     }
     123             : 
     124           0 :   return nullptr;
     125             : }
     126             : 
     127             : 
     128             : 
     129             : template <typename T>
     130       30604 : unsigned int LocationMap<T>::key(const Point & p)
     131             : {
     132        1029 :   Real xscaled = 0., yscaled = 0., zscaled = 0.;
     133             : 
     134       30604 :   const Real deltax = _bbox.max()(0) - _bbox.min()(0);
     135             : 
     136       30604 :   if (std::abs(deltax) > TOLERANCE)
     137       30604 :     xscaled = (p(0) - _bbox.min()(0))/deltax;
     138             : 
     139             :   // Only check y-coords if libmesh is compiled with LIBMESH_DIM>1
     140             : #if LIBMESH_DIM > 1
     141       30604 :   const Real deltay = _bbox.max()(1) - _bbox.min()(1);
     142             : 
     143       30604 :   if (std::abs(deltay) > TOLERANCE)
     144       30604 :     yscaled = (p(1) - _bbox.min()(1))/deltay;
     145             : #endif
     146             : 
     147             :   // Only check z-coords if libmesh is compiled with LIBMESH_DIM>2
     148             : #if LIBMESH_DIM > 2
     149       30604 :   const Real deltaz = _bbox.max()(2) - _bbox.min()(2);
     150             : 
     151       30604 :   if (std::abs(deltaz) > TOLERANCE)
     152       30604 :     zscaled = (p(2) - _bbox.min()(2))/deltaz;
     153             : #endif
     154             : 
     155       30604 :   unsigned int n0 = static_cast<unsigned int> (chunkfloat * xscaled),
     156       30604 :     n1 = static_cast<unsigned int> (chunkfloat * yscaled),
     157       30604 :     n2 = static_cast<unsigned int> (chunkfloat * zscaled);
     158             : 
     159       30604 :   return chunkmax*chunkmax*n0 + chunkmax*n1 + n2;
     160             : }
     161             : 
     162             : 
     163             : 
     164             : template <>
     165          71 : void LocationMap<Node>::fill(MeshBase & mesh)
     166             : {
     167             :   // Populate the nodes map
     168       33488 :   for (auto & node : mesh.node_ptr_range())
     169       17427 :     this->insert(*node);
     170          71 : }
     171             : 
     172             : 
     173             : 
     174             : template <>
     175           0 : void LocationMap<Elem>::fill(MeshBase & mesh)
     176             : {
     177             :   // Populate the elem map
     178           0 :   for (auto & elem : mesh.active_element_ptr_range())
     179           0 :     this->insert(*elem);
     180           0 : }
     181             : 
     182             : 
     183             : 
     184             : template class LIBMESH_EXPORT LocationMap<Elem>;
     185             : template class LIBMESH_EXPORT LocationMap<Node>;
     186             : 
     187             : } // namespace libMesh

Generated by: LCOV version 1.14