Line data Source code
1 1 : // Distributed under the MIT License.
2 : // See LICENSE.txt for details.
3 :
4 : /// \file
5 : /// Defines functions lagrange_polynomial
6 :
7 : #pragma once
8 :
9 : #include <iterator>
10 :
11 : #include "Utilities/ErrorHandling/Assert.hpp"
12 :
13 : /// Evaluate the jth Lagrange interpolating polynomial with the given
14 : /// control points where j is the index of index_point.
15 : template <typename Iterator>
16 1 : double lagrange_polynomial(const Iterator& index_point,
17 : double x,
18 : const Iterator& control_points_begin,
19 : const Iterator& control_points_end) {
20 : ASSERT(control_points_begin != control_points_end, "No control points");
21 :
22 : const double x_j = *index_point;
23 : double result = 1.;
24 : for (auto m_it = control_points_begin; m_it != control_points_end; ++m_it) {
25 : if (m_it == index_point) { continue; }
26 : const double x_m = *m_it;
27 : result *= (x_m - x) / (x_m - x_j);
28 : }
29 : return result;
30 : }
31 :
32 : /// Evaluate the jth (zero-indexed) Lagrange interpolating polynomial
33 : /// with the given control points.
34 : template <typename Iterator>
35 1 : double lagrange_polynomial(size_t j, double x,
36 : const Iterator& control_points_begin,
37 : const Iterator& control_points_end) {
38 : const auto j_diff =
39 : static_cast<typename std::iterator_traits<Iterator>::difference_type>(j);
40 : ASSERT(j_diff < std::distance(control_points_begin, control_points_end),
41 : "Polynomial number out of range " << j << " > "
42 : << (std::distance(control_points_begin, control_points_end) - 1));
43 : return lagrange_polynomial(std::next(control_points_begin, j_diff),
44 : x, control_points_begin, control_points_end);
45 : }
|