MutateAssign.hpp
1 // Distributed under the MIT License.
2 // See LICENSE.txt for details.
3 
4 #pragma once
5 
6 #include <utility>
7 
9 #include "Utilities/Gsl.hpp"
10 #include "Utilities/TMPL.hpp"
11 
12 namespace Initialization {
13 namespace detail {
14 template <typename... MutateTags, typename BoxTags, typename... Args>
15 SPECTRE_ALWAYS_INLINE constexpr void mutate_assign_impl(
16  // NOLINTNEXTLINE(readability-avoid-const-params-in-decls)
17  const gsl::not_null<db::DataBox<BoxTags>*> box,
18  tmpl::list<MutateTags...> /*meta*/, Args&&... args) noexcept {
19  static_assert(sizeof...(MutateTags) == sizeof...(args),
20  "The number of arguments passed to `mutate_assign` must be "
21  "equal to the number of tags passed.");
22  // NOLINTNEXTLINE(modernize-avoid-c-arrays)
23  db::mutate<MutateTags...>(box, [&args...](const auto... box_args) noexcept {
24  // silence unused capture warnings when there are zero args.
25  // This function still gets instantiated despite the `static_assert` in the
26  // parent function.
27  EXPAND_PACK_LEFT_TO_RIGHT((void)args);
28  // NOLINTNEXTLINE(cppcoreguidelines-pro-bounds-array-to-pointer-decay)
29  EXPAND_PACK_LEFT_TO_RIGHT((*box_args = std::forward<Args>(args)));
30  });
31 }
32 } // namespace detail
33 
34 /*!
35  * \ingroup DataBoxGroup
36  * \brief Perform a mutation to the \ref DataBoxGroup `box`, assigning the
37  * `args` to the tags in `MutateTagList` in order.
38  */
39 template <typename MutateTagList, typename BoxTags, typename... Args>
41  // NOLINTNEXTLINE(readability-avoid-const-params-in-decls)
42  const gsl::not_null<db::DataBox<BoxTags>*> box, Args&&... args) noexcept {
43  static_assert(
44  tmpl::size<MutateTagList>::value > 0,
45  "At least one tag must be passed to `Initialization::mutate_assign`, but "
46  "received 0 tags to mutate.");
47  detail::mutate_assign_impl(box, MutateTagList{}, std::forward<Args>(args)...);
48 }
49 } // namespace Initialization
EXPAND_PACK_LEFT_TO_RIGHT
#define EXPAND_PACK_LEFT_TO_RIGHT(...)
Expand a parameter pack evaluating the terms from left to right.
Definition: TMPL.hpp:563
utility
db::MutateTags
tmpl::flatten< tmpl::list< Tags... > > MutateTags
List of Tags to mutate in the DataBox.
Definition: DataBox.hpp:992
db::mutate
void mutate(const gsl::not_null< DataBox< TagList > * > box, Invokable &&invokable, Args &&... args) noexcept
Allows changing the state of one or more non-computed elements in the DataBox.
Definition: DataBox.hpp:859
Initialization::mutate_assign
constexpr void mutate_assign(const gsl::not_null< db::DataBox< BoxTags > * > box, Args &&... args) noexcept
Perform a mutation to the DataBox box, assigning the args to the tags in MutateTagList in order.
Definition: MutateAssign.hpp:40
DataBox.hpp
SPECTRE_ALWAYS_INLINE
#define SPECTRE_ALWAYS_INLINE
Definition: ForceInline.hpp:16
Gsl.hpp
TMPL.hpp
gsl::not_null
Require a pointer to not be a nullptr
Definition: Gsl.hpp:183