Skip to content

Conversation

@tretre91
Copy link
Member

This PR adds the SplineBuilder3D and SplineEvaluator3D classes to handle 3D splines. Some 3D spline tests are also added.
In its current state, Hermite boundary conditions are not handled. Also, the API for the SplineBuilder3D will certainly need to be modified (we currently take as arguments the derivatives on the faces and the cross derivatives on the corners, but we might also want the cross derivatives on the edges).

@codecov
Copy link

codecov bot commented Sep 30, 2025

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 91.88%. Comparing base (fc6a29e) to head (75cc670).
⚠️ Report is 2 commits behind head on main.

Additional details and impacted files
@@            Coverage Diff             @@
##             main     #925      +/-   ##
==========================================
- Coverage   92.63%   91.88%   -0.75%     
==========================================
  Files          55       57       +2     
  Lines        2673     2834     +161     
  Branches      839      925      +86     
==========================================
+ Hits         2476     2604     +128     
- Misses        112      136      +24     
- Partials       85       94       +9     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@tpadioleau tpadioleau force-pushed the multid_splines branch 2 times, most recently from 3774590 to ec69b64 Compare October 2, 2025 13:05
@tretre91 tretre91 mentioned this pull request Oct 3, 2025
@tpadioleau tpadioleau marked this pull request as ready for review October 3, 2025 16:30

/// @brief The type of the SplineBuilder used by this class to spline-approximate the third-dimension-derivatives along second dimension.
using builder_deriv_type2 = ddc::
SplineBuilder<ExecSpace, MemorySpace, BSpline2, DDimI2, BcLower2, BcUpper2, Solver>;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's introduce the types builder_deriv_type1 and builder_deriv_type2 in the PR that handles the boundary conditions.

builder_type2 m_spline_builder2;
builder_type3 m_spline_builder3;
builder_deriv_type1 m_spline_builder_deriv1;
builder_deriv_type2 m_spline_builder_deriv2;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Similarly m_spline_builder_deriv1 and m_spline_builder_deriv2 could be introduced later.

Maybe by not introducing unnecessary variables at this stage, we will also understand better the Spline codebase.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

While we are at this, we could also note down small adjustments to be made in spline_builder_2d.hpp:

    builder_type1 m_spline_builder1;
    builder_deriv_type1 m_spline_builder_deriv1;
    builder_type2 m_spline_builder2;

can be:

    builder_type1 m_spline_builder1;
    builder_type2 m_spline_builder2;
    builder_deriv_type1 m_spline_builder_deriv1;

using batched_derivs_domain_type3 = ddc::replace_dim_of_t<
BatchedInterpolationDDom,
interpolation_discrete_dimension_type3,
deriv_type3>;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

These types are again needed only in ddc::BoundCond::HERMITE. We could keep them here if it is too much work to retain only the PERIODIC related stuff. I see that the corresponding variables are annotated as [[maybe_unused]].

Also, here and in spline_builder_2d.hpp why cannot the definition of batched_derivs_domain_type1 have the same form as batched_derivs_domain_type2? Like the following:

    template <
            class BatchedInterpolationDDom,
            class = std::enable_if_t<ddc::is_discrete_domain_v<BatchedInterpolationDDom>>>
    using batched_derivs_domain_type1 = ddc::replace_dim_of_t<
            BatchedInterpolationDDom,
            interpolation_discrete_dimension_type1,
            deriv_type1>;

endforeach()
endforeach()

foreach(BC "BC_PERIODIC" "BC_GREVILLE") # "BC_HERMITE")
Copy link
Member

@science-enthusiast science-enthusiast Oct 8, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just like commenting out BC_HERMITE here, let us see whether we can comment out or remove BC_HERMITE related stuff in all places in CMake and C++ logic. Removing all the #if defined(BC_HERMITE) should be at least easy.

, m_spline_builder_deriv1(interpolation_domain)
, m_spline_builder_deriv2(interpolation_domain)
{
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here and in spline_builder_2d.hpp is this constructor ever called directly or is it always called in a delegated manner by the following constructor?

* @param x An rvalue to another SplineBuilder.
* @return A reference to this object.
*/
SplineBuilder3D& operator=(SplineBuilder3D&& x) = default;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here and in spline_builder_2d.hpp, the explicitly declared default destructor could be removed. Also, the order can be changed. Explicitly marking both the copy operations as deleted, followed by the defaulted move operations. We could also add a comment that this is a move only type. The dummy variable x is also not needed anywhere.

{
assert(interpolation_domain() == interpolation_domain_type(batched_interpolation_domain));
return batched_interpolation_domain;
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here and in spline_builder_2d.hpp, we could rename this function template as copy_batched_interpolation_domain.

Also, I am not where this being used.

*
* @param batched_interpolation_domain The whole domain on which the interpolation points are defined.
*
* @return The domain for the interpolation mesh.
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here and in spline_builder_2d.hpp, the return type could be worded as The whole domain for ....

m_spline_builder2(spline2, spline1.span_cview());

// Spline3-approximate spline2
m_spline_builder3(spline, spline2.span_cview());
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we have a separate PR where we call SplineBuilder followed by SplineBuilder2D? We will have a SplineBuilder2D member etc, in that implementation. That approach will help with nD approach.


LowerExtrapolationRule3 m_lower_extrap_rule_3;

UpperExtrapolationRule3 m_upper_extrap_rule_3;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The extra lines inbetween can be removed.

ddc::ChunkSpan<
double const,
spline_domain_type,
Kokkos::layout_right,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we define an alias (e.g., spline_layout) for Kokkos::layout_right and use it everywhere?

* @param x An rvalue to another SplineEvaluator.
* @return A reference to this object.
*/
SplineEvaluator3D& operator=(SplineEvaluator3D&& x) = default;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can follow the rule of zero and not define any of them in a defaulted manner.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not necessary imo.

template <
class Layout1,
class Layout2,
class Layout3,
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In the comments can we say, why we are giving the flexibility of three separate Layouts?

* @return The derivative of the spline function at the desired coordinate.
*/
template <class Layout, class... CoordsDims>
KOKKOS_FUNCTION double deriv_1_and_3(
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Shall we move the definition of deriv_1_3 between deriv_1_and_2 and deriv_2_and_3? If we can follow an order in which we list tuples of dimensions, it will help with recursive implementation.

Or 1_2 followed by 2_3 followed by 3_1 (not 1_3, even though there is no technical difference between 1_3 and 3_1).

|| (std::is_same_v<
InterestDim2,
typename evaluation_discrete_dimension_type1::continuous_dimension_type>
&& std::is_same_v<InterestDim1, continuous_dimension_type3>));
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In these static asserts there is no opportunity to compare with typename evaluation_discrete_dimension_type3::continuous_dimension_type, is that ok?

The same situation is already there in deriv2 in spline_evaluator_2d.hpp. It will be good to understand more about this.

InterestDim2,
typename evaluation_discrete_dimension_type1::continuous_dimension_type>
&& std::is_same_v<InterestDim3, continuous_dimension_type2>
&& std::is_same_v<InterestDim1, continuous_dimension_type3>));
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Again, the order can be changed. (1, 2, 3) followed by (2, 3, 1) then (3, 1, 2).

Comment on lines +478 to +479
template <class Layout, class BatchedInterpolationDDom>
void operator()(
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are different layouts tested?
This may be an additional implementation of this issue:
#886

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think so, this PR is the 3D extension of the 2D classes, based on the same tests without Hermite boundary conditions.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In that case the template parameter Layout should probably be removed given that it is probably broken anyway

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I was not aware of this issue, but if it is present in 2D, it will also be present in #929 since we settled on a recursive approach using 1D and 2D builders for the 3D builder

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't know what is the best approach for now. I think currently only layout_right is working fine so if you prefer that the API reflects this we can do a quick fix.

We are starting to play with StridedDiscreteDomain, we think that other layouts will be needed but not clear yet.

tpadioleau
tpadioleau previously approved these changes Oct 10, 2025
@tpadioleau
Copy link
Member

As discussed, @science-enthusiast please open an issue listing all your comments so that they can be addressed on all builders/evaluators.

@tpadioleau tpadioleau merged commit deae66e into CExA-project:main Oct 10, 2025
82 of 83 checks passed
@tretre91 tretre91 deleted the multid_splines branch November 3, 2025 14:36
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants