SimiLie
Loading...
Searching...
No Matches
codifferential.hpp
1// SPDX-FileCopyrightText: 2024 Baptiste Legouix
2// SPDX-License-Identifier: MIT
3
4#pragma once
5
6#include <ddc/ddc.hpp>
7
8#include <similie/exterior/hodge_star.hpp>
9#include <similie/misc/macros.hpp>
10#include <similie/misc/specialization.hpp>
11#include <similie/tensor/character.hpp>
12#include <similie/tensor/tensor_impl.hpp>
13
14#include <Kokkos_StdAlgorithms.hpp>
15
16#include "cochain.hpp"
17#include "cosimplex.hpp"
18
19
20namespace sil {
21
22namespace exterior {
23
24namespace detail {
25
26template <class T>
27struct CodifferentialType;
28
29template <
30 std::size_t K,
31 class... Tag,
32 class ElementType,
33 class LayoutStridedPolicy1,
34 class LayoutStridedPolicy2,
35 class ExecSpace>
36struct CodifferentialType<
37 Cochain<Chain<Simplex<K, Tag...>, LayoutStridedPolicy1, ExecSpace>,
38 ElementType,
39 LayoutStridedPolicy2>>
40{
41 using type = Cosimplex<Simplex<K - 1, Tag...>, ElementType>;
42};
43
44} // namespace detail
45
46template <misc::Specialization<Cochain> CochainType>
47using codifferential_t = typename detail::CodifferentialType<CochainType>::type;
48
49namespace detail {
50
51template <class TagToRemoveFromCochain, class CochainTag>
52struct CodifferentialIndex;
53
54template <tensor::TensorNatIndex TagToRemoveFromCochain, tensor::TensorNatIndex CochainTag>
55 requires(CochainTag::rank() == 1 && std::is_same_v<TagToRemoveFromCochain, CochainTag>)
56struct CodifferentialIndex<TagToRemoveFromCochain, CochainTag>
57{
59};
60
61template <tensor::TensorNatIndex TagToRemoveFromCochain, tensor::TensorNatIndex Tag>
62struct CodifferentialIndex<
63 TagToRemoveFromCochain,
64 tensor::TensorAntisymmetricIndex<TagToRemoveFromCochain, Tag>>
65{
66 using type = Tag;
67};
68
69template <tensor::TensorNatIndex TagToRemoveFromCochain, tensor::TensorNatIndex... Tag>
70 requires(sizeof...(Tag) > 1)
71struct CodifferentialIndex<
72 TagToRemoveFromCochain,
74{
75 using type = tensor::TensorAntisymmetricIndex<Tag...>;
76};
77
78} // namespace detail
79
80template <class TagToRemoveFromCochain, class CochainTag>
82 typename detail::CodifferentialIndex<TagToRemoveFromCochain, CochainTag>::type;
83
84namespace detail {
85
86template <
87 tensor::TensorNatIndex TagToRemoveFromCochain,
88 tensor::TensorIndex CochainTag,
90struct CodifferentialTensorType;
91
92template <
93 tensor::TensorNatIndex TagToRemoveFromCochain,
94 tensor::TensorIndex CochainIndex,
95 class ElementType,
96 class... DDim,
97 class SupportType,
98 class MemorySpace>
99struct CodifferentialTensorType<
100 TagToRemoveFromCochain,
101 CochainIndex,
102 tensor::Tensor<ElementType, ddc::DiscreteDomain<DDim...>, SupportType, MemorySpace>>
103{
104 static_assert(ddc::type_seq_contains_v<
105 ddc::detail::TypeSeq<CochainIndex>,
106 ddc::detail::TypeSeq<DDim...>>);
107 using type = tensor::Tensor<
108 ElementType,
109 ddc::replace_dim_of_t<
110 ddc::DiscreteDomain<DDim...>,
111 CochainIndex,
113 SupportType,
114 MemorySpace>;
115};
116
117} // namespace detail
118
119template <
120 tensor::TensorNatIndex TagToRemoveFromCochain,
121 tensor::TensorIndex CochainTag,
123using codifferential_tensor_t = typename detail::
124 CodifferentialTensorType<TagToRemoveFromCochain, CochainTag, TensorType>::type;
125
126namespace detail {
127
128template <std::size_t I, class T>
129struct CodifferentialDummyIndex : tensor::uncharacterize_t<T>
130{
131};
132
133template <class Ids, class T>
134struct CodifferentialDummyIndexSeq_;
135
136template <std::size_t... Id, class T>
137struct CodifferentialDummyIndexSeq_<std::index_sequence<Id...>, T>
138{
139 using type = ddc::detail::TypeSeq<tensor::Covariant<CodifferentialDummyIndex<Id, T>>...>;
140};
141
142template <std::size_t EndId, class T>
143struct CodifferentialDummyIndexSeq;
144
145template <std::size_t EndId, class T>
146 requires(EndId == 0)
147struct CodifferentialDummyIndexSeq<EndId, T>
148{
149 using type = ddc::detail::TypeSeq<>;
150};
151
152template <std::size_t EndId, class T>
153 requires(EndId > 0)
154struct CodifferentialDummyIndexSeq<EndId, T>
155{
156 using type = typename CodifferentialDummyIndexSeq_<std::make_index_sequence<EndId>, T>::type;
157};
158
159} // namespace detail
160
161template <
162 tensor::TensorIndex MetricIndex,
163 tensor::TensorNatIndex TagToRemoveFromCochain,
164 tensor::TensorIndex CochainTag,
167 class ExecSpace>
169 ExecSpace const& exec_space,
171 codifferential_tensor,
172 TensorType tensor,
173 MetricType inv_metric)
174{
177 using NuLowSeq = typename detail::CodifferentialDummyIndexSeq<
178 TagToRemoveFromCochain::size() - CochainTag::rank(),
179 TagToRemoveFromCochain>::type;
180 using RhoLowSeq = ddc::type_seq_merge_t<ddc::detail::TypeSeq<TagToRemoveFromCochain>, NuLowSeq>;
181 using RhoUpSeq = tensor::upper_t<RhoLowSeq>;
182 using SigmaLowSeq = ddc::type_seq_remove_t<
184 ddc::detail::TypeSeq<TagToRemoveFromCochain>>;
185
188
189 // Hodge star
190 [[maybe_unused]] sil::tensor::tensor_accessor_for_domain_t<HodgeStarDomain> hodge_star_accessor;
191 ddc::cartesian_prod_t<typename MetricType::non_indices_domain_t, HodgeStarDomain>
192 hodge_star_dom(inv_metric.non_indices_domain(), hodge_star_accessor.domain());
193 ddc::Chunk hodge_star_alloc(
194 hodge_star_dom,
195 ddc::KokkosAllocator<double, typename ExecSpace::memory_space>());
196 sil::tensor::Tensor hodge_star(hodge_star_alloc);
197
200 MuUpSeq,
201 NuLowSeq>(exec_space, hodge_star, inv_metric);
202
203 // Dual tensor
204 [[maybe_unused]] tensor::TensorAccessor<
206 dual_tensor_accessor;
207 ddc::cartesian_prod_t<
208 typename TensorType::non_indices_domain_t,
209 ddc::DiscreteDomain<
211 dual_tensor_dom(tensor.non_indices_domain(), dual_tensor_accessor.domain());
212 ddc::Chunk dual_tensor_alloc(
213 dual_tensor_dom,
214 ddc::KokkosAllocator<double, typename ExecSpace::memory_space>());
215 sil::tensor::Tensor dual_tensor(dual_tensor_alloc);
216
217 SIMILIE_DEBUG_LOG("similie_compute_dual_tensor");
218 ddc::parallel_for_each(
219 "similie_compute_dual_tensor",
220 exec_space,
221 dual_tensor.non_indices_domain(),
222 KOKKOS_LAMBDA(typename TensorType::non_indices_domain_t::discrete_element_type elem) {
223 sil::tensor::tensor_prod(dual_tensor[elem], tensor[elem], hodge_star[elem]);
224 });
225
226 // Dual codifferential
227 [[maybe_unused]] tensor::TensorAccessor<
229 dual_codifferential_accessor;
230 ddc::cartesian_prod_t<
231 typename TensorType::non_indices_domain_t,
232 ddc::DiscreteDomain<
234 dual_codifferential_dom(
235 tensor.non_indices_domain(),
236 dual_codifferential_accessor.domain());
237 ddc::Chunk dual_codifferential_alloc(
238 dual_codifferential_dom,
239 ddc::KokkosAllocator<double, typename ExecSpace::memory_space>());
240 sil::tensor::Tensor dual_codifferential(dual_codifferential_alloc);
242 TagToRemoveFromCochain,
245 NuLowSeq>>(exec_space, dual_codifferential, dual_tensor);
246
247 // Hodge star 2
249 hodge_star_accessor2;
250 ddc::cartesian_prod_t<typename MetricType::non_indices_domain_t, HodgeStarDomain2>
251 hodge_star_dom2(inv_metric.non_indices_domain(), hodge_star_accessor2.domain());
252 ddc::Chunk hodge_star_alloc2(
253 hodge_star_dom2,
254 ddc::KokkosAllocator<double, typename ExecSpace::memory_space>());
255 sil::tensor::Tensor hodge_star2(hodge_star_alloc2);
256
259 RhoUpSeq,
260 SigmaLowSeq>(exec_space, hodge_star2, inv_metric);
261
262 // Codifferential
263 SIMILIE_DEBUG_LOG("similie_compute_codifferential");
264 ddc::parallel_for_each(
265 "similie_compute_codifferential",
266 exec_space,
267 codifferential_tensor.non_indices_domain(),
268 KOKKOS_LAMBDA(typename TensorType::non_indices_domain_t::discrete_element_type elem) {
270 codifferential_tensor[elem],
271 dual_codifferential[elem],
272 hodge_star2[elem]);
273 if constexpr (
274 (TagToRemoveFromCochain::size() * (CochainTag::rank() + 1) + 1) % 2 == 1) {
275 codifferential_tensor[elem] *= -1;
276 }
277 });
278
279 return codifferential_tensor;
280}
281
282} // namespace exterior
283
284} // namespace sil
HodgeStarType fill_hodge_star(ExecSpace const &exec_space, HodgeStarType hodge_star, MetricDeterminantType metric_determinant, MetricProdType metric_prod)
Cochain(ChainType, TensorType) -> Cochain< ChainType, typename TensorType::value_type, ddc::detail::mdspan_to_kokkos_layout_t< typename TensorType::layout_type > >
Simplex(ddc::DiscreteElement< Tag... >, ddc::DiscreteVector< T... >) -> Simplex< sizeof...(T), Tag... >
typename detail:: CodifferentialTensorType< TagToRemoveFromCochain, CochainTag, TensorType >::type codifferential_tensor_t
Chain(Head, Tail...) -> Chain< typename Head::value_type, typename Head::array_layout, typename Head::memory_space >
ddc::detail::convert_type_seq_to_discrete_domain_t< ddc::type_seq_merge_t< ddc::detail::TypeSeq< misc::convert_type_seq_to_t< tensor::TensorFullIndex, Indices1 > >, std::conditional_t<(ddc::type_seq_size_v< Indices2 >==0), ddc::detail::TypeSeq<>, ddc::detail::TypeSeq< misc::convert_type_seq_to_t< tensor::TensorAntisymmetricIndex, Indices2 > > > > > hodge_star_domain_t
coboundary_tensor_t< TagToAddToCochain, CochainTag, TensorType > deriv(ExecSpace const &exec_space, coboundary_tensor_t< TagToAddToCochain, CochainTag, TensorType > coboundary_tensor, TensorType tensor)
typename detail::CodifferentialIndex< TagToRemoveFromCochain, CochainTag >::type codifferential_index_t
codifferential_tensor_t< TagToRemoveFromCochain, CochainTag, TensorType > codifferential(ExecSpace const &exec_space, codifferential_tensor_t< TagToRemoveFromCochain, CochainTag, TensorType > codifferential_tensor, TensorType tensor, MetricType inv_metric)
typename detail::CodifferentialType< CochainType >::type codifferential_t
typename detail::ConvertTypeSeqTo< T, Seq >::type convert_type_seq_to_t
Tensor(ddc::Chunk< ElementType, SupportType, Allocator >) -> Tensor< ElementType, SupportType, Kokkos::layout_right, typename Allocator::memory_space >
detail::Upper< T >::type upper_t
Tensor< ElementType, ddc::DiscreteDomain< ProdDDim... >, LayoutStridedPolicy, MemorySpace > tensor_prod(Tensor< ElementType, ddc::DiscreteDomain< ProdDDim... >, LayoutStridedPolicy, MemorySpace > prod_tensor, Tensor< ElementType, ddc::DiscreteDomain< DDim1... >, LayoutStridedPolicy, MemorySpace > tensor1, Tensor< ElementType, ddc::DiscreteDomain< DDim2... >, LayoutStridedPolicy, MemorySpace > tensor2)
detail::Uncharacterize< Index >::type uncharacterize_t
detail::Lower< T >::type lower_t
Definition character.hpp:80
bool constexpr is_covariant_v
detail::TensorAccessorForDomain< Dom >::type tensor_accessor_for_domain_t
The top-level namespace of SimiLie.
Definition csr.hpp:15