SpECTRE Documentation Coverage Report
Current view: top level - Domain - Domain.hpp Hit Total Coverage
Commit: 1f2210958b4f38fdc0400907ee7c6d5af5111418 Lines: 7 25 28.0 %
Date: 2025-12-05 05:03:31
Legend: Lines: hit not hit

          Line data    Source code
       1           1 : // Distributed under the MIT License.
       2             : // See LICENSE.txt for details.
       3             : 
       4             : /// \file
       5             : /// Defines class template Domain.
       6             : 
       7             : #pragma once
       8             : 
       9             : #include <array>
      10             : #include <cstddef>
      11             : #include <iosfwd>
      12             : #include <memory>
      13             : #include <string>
      14             : #include <unordered_map>
      15             : #include <unordered_set>
      16             : #include <vector>
      17             : 
      18             : #include "Domain/Block.hpp"
      19             : #include "Domain/DomainHelpers.hpp"
      20             : #include "Domain/ExcisionSphere.hpp"
      21             : #include "Utilities/ConstantExpressions.hpp"
      22             : 
      23             : namespace Frame {
      24             : struct BlockLogical;
      25             : }  // namespace Frame
      26             : namespace PUP {
      27             : class er;
      28             : }  // namespace PUP
      29             : /// \cond
      30             : namespace domain {
      31             : template <typename SourceFrame, typename TargetFrame, size_t Dim>
      32             : class CoordinateMapBase;
      33             : }  // namespace domain
      34             : /// \endcond
      35             : 
      36             : /*!
      37             :  * \brief Holds entities related to the computational domain.
      38             :  */
      39             : namespace domain {}
      40             : 
      41             : /*!
      42             :  * \ingroup ComputationalDomainGroup
      43             :  * \brief A wrapper around a vector of Blocks that represent the computational
      44             :  * domain.
      45             :  *
      46             :  * ### Serialization and versioning
      47             :  *
      48             :  * The domain will be serialized and written to output files so it can be used
      49             :  * for interpolations, as are `domain::FunctionOfTime` classes. To be able to
      50             :  * read in domains written by older versions of the code the `pup` function in
      51             :  * this class and all `pup` functions it invokes support lightweight versioning.
      52             :  * A `version` integer is written alongside the data when serializing, and read
      53             :  * back in when deserializing. Increment the version number every time you make
      54             :  * changes to the `pup` function. Retain support for unpacking data written by
      55             :  * previous versions whenever possible. When adding a new field to serialize,
      56             :  * you can simply pack/unpack the new field only for newer versions like this:
      57             :  *
      58             :  * ```cpp
      59             :  * void pup(PUP::er& p) {
      60             :  *   size_t version = 1;  // Incremented from 0 to 1
      61             :  *   p | version;
      62             :  *   if (version >= 0) {
      63             :  *     p | some_data_;
      64             :  *   }
      65             :  *   if (version >= 1) {
      66             :  *     p | added_data_;
      67             :  *   } else if (p.isUnpacking()) {
      68             :  *     // You may have to initialize added_data_ here if default-construction
      69             :  *     // isn't sufficient.
      70             :  *   }
      71             :  * }
      72             :  * ```
      73             :  *
      74             :  * When removing or changing a field, make sure to deserialize old data
      75             :  * consistent with how it was written:
      76             :  *
      77             :  * ```cpp
      78             :  * void pup(PUP::er& p) {
      79             :  *   size_t version = 2;  // Incremented from 1 to 2
      80             :  *   p | version;
      81             :  *   if (version < 2) {
      82             :  *     // The field some_data_ was changed in version 2
      83             :  *     OldDataType old_some_data_;
      84             :  *     p | old_some_data_;
      85             :  *     // Possibly use the old deserialized data to initialize the changed field
      86             :  *     some_data_ = old_some_data_ * 2.;
      87             :  *   } else {
      88             :  *     p | some_data_;
      89             :  *   }
      90             :  *   // ...
      91             :  * }
      92             :  * ```
      93             :  *
      94             :  * Make sure that all data types you serialize in the `pup` function also
      95             :  * support versioning. Also make sure to keep all factory-creatable classes
      96             :  * registered that were written by old versions of the code.
      97             :  */
      98             : template <size_t VolumeDim>
      99           1 : class Domain {
     100             :  public:
     101             :   /// \brief Create a Domain from its blocks
     102             :   ///
     103             :   /// \param blocks each Block of the domain.
     104             :   /// \param excision_spheres Any ExcisionSphere%s in the domain.
     105             :   /// \param block_groups Labels to refer to groups of blocks. The groups can
     106             :   ///        overlap, and they don't have to cover all blocks in the domain.
     107             :   ///        The groups can be used to refer to multiple blocks at once.
     108           1 :   explicit Domain(
     109             :       std::vector<Block<VolumeDim>> blocks,
     110             :       std::unordered_map<std::string, ExcisionSphere<VolumeDim>>
     111             :           excision_spheres = {},
     112             :       std::unordered_map<std::string, std::unordered_set<std::string>>
     113             :           block_groups = {});
     114             : 
     115             :   /*!
     116             :    * \brief Create a Domain using CoordinateMaps to encode the Orientations.
     117             :    * This constructor does not support periodic boundary conditions.
     118             :    *
     119             :    * \details A constructor that does not require the user to provide a corner
     120             :    * numbering scheme. Constructs a global corner numbering for each pair
     121             :    * of abutting Blocks from their maps alone. The numbering is used to
     122             :    * set up the corresponding Orientation, and then is discarded; the
     123             :    * next pair of blocks uses a new global corner numbering, and so on,
     124             :    * until all pairs of abutting Blocks have had their Orientations
     125             :    * determined. For more information on setting up domains, see the
     126             :    * [domain creation tutorial](\ref tutorial_domain_creation).
     127             :    *
     128             :    * \param maps The BlockLogical -> Inertial coordinate map for each block.
     129             :    * \param excision_spheres Any ExcisionSphere%s in the domain.
     130             :    * \param block_names A human-readable name for every block, or empty if no
     131             :    * block names have been chosen (yet).
     132             :    * \param block_groups Labels to refer to groups of blocks. The groups can
     133             :    * overlap, and they don't have to cover all blocks in the domain. The groups
     134             :    * can be used to refer to multiple blocks at once.
     135             :    */
     136           1 :   explicit Domain(
     137             :       std::vector<std::unique_ptr<domain::CoordinateMapBase<
     138             :           Frame::BlockLogical, Frame::Inertial, VolumeDim>>>
     139             :           maps,
     140             :       std::unordered_map<std::string, ExcisionSphere<VolumeDim>>
     141             :           excision_spheres = {},
     142             :       std::vector<std::string> block_names = {},
     143             :       std::unordered_map<std::string, std::unordered_set<std::string>>
     144             :           block_groups = {});
     145             : 
     146             :   /*!
     147             :    * \brief Create a Domain using a corner numbering scheme to encode the
     148             :    * Orientations
     149             :    *
     150             :    * \see [domain creation tutorial](@ref tutorial_domain_creation)
     151             :    *
     152             :    * \param maps The BlockLogical -> Inertial coordinate map for each block.
     153             :    * \param corners_of_all_blocks The corner numbering for each block's corners
     154             :    * according to the global corner number scheme. The details of the corner
     155             :    * numbering scheme are described in the
     156             :    * [tutorial](@ref tutorial_orientations).
     157             :    * \param identifications Used to impose periodic boundary conditions on the
     158             :    * domain. To identify faces, `identifications` should contain the PairOfFaces
     159             :    * containing the corners of each pair of faces that you wish to identify with
     160             :    * one another. The number of `identifications` must be even.
     161             :    * \param excision_spheres Any ExcisionSphere%s in the domain.
     162             :    * \param block_names A human-readable name for every block, or empty if no
     163             :    * block names have been chosen (yet).
     164             :    * \param block_groups Labels to refer to groups of blocks. The groups can
     165             :    * overlap, and they don't have to cover all blocks in the domain. The groups
     166             :    * can be used to refer to multiple blocks at once.
     167             :    */
     168           1 :   Domain(std::vector<std::unique_ptr<domain::CoordinateMapBase<
     169             :              Frame::BlockLogical, Frame::Inertial, VolumeDim>>>
     170             :              maps,
     171             :          const std::vector<std::array<size_t, two_to_the(VolumeDim)>>&
     172             :              corners_of_all_blocks,
     173             :          const std::vector<PairOfFaces>& identifications = {},
     174             :          std::unordered_map<std::string, ExcisionSphere<VolumeDim>>
     175             :              excision_spheres = {},
     176             :          std::vector<std::string> block_names = {},
     177             :          std::unordered_map<std::string, std::unordered_set<std::string>>
     178             :              block_groups = {});
     179             : 
     180           0 :   Domain() = default;
     181           0 :   ~Domain() = default;
     182           0 :   Domain(const Domain&) = delete;
     183           0 :   Domain(Domain&&) = default;
     184           0 :   Domain<VolumeDim>& operator=(const Domain<VolumeDim>&) = delete;
     185           0 :   Domain<VolumeDim>& operator=(Domain<VolumeDim>&&) = default;
     186             : 
     187           0 :   void inject_time_dependent_map_for_block(
     188             :       size_t block_id,
     189             :       std::unique_ptr<
     190             :           domain::CoordinateMapBase<Frame::Grid, Frame::Inertial, VolumeDim>>
     191             :           moving_mesh_grid_to_inertial_map,
     192             :       std::unique_ptr<
     193             :           domain::CoordinateMapBase<Frame::Grid, Frame::Distorted, VolumeDim>>
     194             :           moving_mesh_grid_to_distorted_map = nullptr,
     195             :       std::unique_ptr<domain::CoordinateMapBase<Frame::Distorted,
     196             :                                                 Frame::Inertial, VolumeDim>>
     197             :           moving_mesh_distorted_to_inertial_map = nullptr);
     198             : 
     199           0 :   void inject_time_dependent_map_for_excision_sphere(
     200             :       const std::string& excision_sphere_name,
     201             :       std::unique_ptr<
     202             :           domain::CoordinateMapBase<Frame::Grid, Frame::Inertial, VolumeDim>>
     203             :           moving_mesh_grid_to_inertial_map);
     204             : 
     205           0 :   const std::vector<Block<VolumeDim>>& blocks() const { return blocks_; }
     206             : 
     207           0 :   bool is_time_dependent() const;
     208             : 
     209             :   const std::unordered_map<std::string, ExcisionSphere<VolumeDim>>&
     210           0 :   excision_spheres() const {
     211             :     return excision_spheres_;
     212             :   }
     213             : 
     214             :   /// Labels to refer to groups of blocks. The groups can overlap, and they
     215             :   /// don't have to cover all blocks in the domain. The groups can be used to
     216             :   /// refer to multiple blocks at once.
     217             :   const std::unordered_map<std::string, std::unordered_set<std::string>>&
     218           1 :   block_groups() const {
     219             :     return block_groups_;
     220             :   }
     221             : 
     222             :   /// The block names in the current domain.
     223           1 :   std::vector<std::string> block_names() const;
     224             : 
     225             :   // NOLINTNEXTLINE(google-runtime-references)
     226           0 :   void pup(PUP::er& p);
     227             : 
     228             :  private:
     229           0 :   std::vector<Block<VolumeDim>> blocks_{};
     230             :   std::unordered_map<std::string, ExcisionSphere<VolumeDim>>
     231           0 :       excision_spheres_{};
     232             :   std::unordered_map<std::string, std::unordered_set<std::string>>
     233           0 :       block_groups_{};
     234             : };
     235             : 
     236             : template <size_t VolumeDim>
     237           0 : bool operator==(const Domain<VolumeDim>& lhs, const Domain<VolumeDim>& rhs);
     238             : 
     239             : template <size_t VolumeDim>
     240           0 : bool operator!=(const Domain<VolumeDim>& lhs, const Domain<VolumeDim>& rhs);
     241             : 
     242             : template <size_t VolumeDim>
     243           0 : std::ostream& operator<<(std::ostream& os, const Domain<VolumeDim>& d);

Generated by: LCOV version 1.14