7#ifndef DUNE_FUNCTIONS_ANALYTICFUNCTIONS_POLYNOMIAL_HH
8#define DUNE_FUNCTIONS_ANALYTICFUNCTIONS_POLYNOMIAL_HH
11#include <initializer_list>
15#include <dune/common/hybridutilities.hh>
24 template<
class K,
class Allocator>
25 auto polynomialDerivativeCoefficients(
const std::vector<K, Allocator>& coefficients) {
26 if (coefficients.size()==0)
27 return std::vector<K, Allocator>();
28 std::vector<K, Allocator> dpCoefficients(coefficients.size()-1);
29 for (
size_t i=1; i<coefficients.size(); ++i)
30 dpCoefficients[i-1] = coefficients[i]*K(i);
31 return dpCoefficients;
36 template<
class K, std::
size_t n>
37 auto polynomialDerivativeCoefficients(
const std::array<K, n>& coefficients) {
42 std::array<K, n-1> dpCoefficients;
43 for (
size_t i=1; i<coefficients.size(); ++i)
44 dpCoefficients[i-1] = coefficients[i]*K(i);
45 return dpCoefficients;
54 template<
class I, I i0, I... i,
class J, J j0, J... j>
55 auto polynomialDerivativeCoefficientsHelper(std::integer_sequence<I, i0, i...>, std::integer_sequence<J, j0, j...>) {
56 return std::integer_sequence<I, i*I(j)...>();
61 template<
class I, I... i>
62 auto polynomialDerivativeCoefficients(std::integer_sequence<I, i...> coefficients) {
63 if constexpr (
sizeof...(i)==0)
66 return polynomialDerivativeCoefficientsHelper(coefficients, std::make_index_sequence<
sizeof...(i)>());
72 auto polynomialDerivativeCoefficients(
const std::tuple<T...>& coefficients) {
73 if constexpr (
sizeof...(T)==0)
83 auto mult = Dune::Hybrid::hybridFunctor(std::multiplies());
84 return Dune::unpackIntegerSequence([&](
auto... i) {
85 using signed_type = std::conditional_t<std::is_same_v<std::size_t, long unsigned int>,
86 long signed int,
signed int>;
87 return std::tuple(mult(std::get<i+1>(coefficients),
88 std::integral_constant<signed_type, (signed_type)(i+1)>()) ...);
89 }, std::make_index_sequence<
sizeof...(T)-1>());
123template<
class K,
class C=std::vector<K>>
127 struct IsIntegerSequence :
public std::false_type {};
129 template<
class I, I... i>
130 struct IsIntegerSequence<std::integer_sequence<I, i...>> :
public std::true_type {};
141 template <
typename Coefficient>
142 static void add(K& y,
const Coefficient &c)
144 if constexpr (!IsIntegralConstant<Coefficient>::value)
180 using namespace Dune::Indices;
182 auto n = Dune::Hybrid::size(coefficients_);
186 return Hybrid::ifElse(Hybrid::equal_to(n, _0),
193 K y = Hybrid::elementAt(coefficients_, Hybrid::minus(
id(n), _1) );
194 Dune::Hybrid::forEach(Dune::range(Hybrid::minus(
id(n), _1) ), [&](
auto i)
198 add(y,Hybrid::elementAt(coefficients_, Hybrid::minus(Hybrid::minus(
id(n),_2), i)));
207 if constexpr (IsIntegerSequence<Coefficients>::value)
224 auto derivativeCoefficients = Impl::polynomialDerivativeCoefficients(p.
coefficients());
225 using DerivativeCoefficients =
decltype(derivativeCoefficients);
232 return coefficients_;
244template<
class K, std::
size_t n>
247template<
class K, K... ci>
267template<
class K,
class Coefficients>
282template<
class K,
class C>
friend auto derivative(const Polynomial &p)
Obtain derivative of Polynomial function.
Definition polynomial.hh:222
Definition monomialset.hh:19
Definition monomialset.hh:19
Polynomial(std::vector< K >) -> Polynomial< K, std::vector< K > >
auto makePolynomial(Coefficients coefficients)
Create Polynomial.
Definition polynomial.hh:268
A univariate polynomial implementation.
Definition polynomial.hh:125
Polynomial()=default
Default constructor.
K operator()(const K &x) const
Evaluate polynomial using the Horner scheme.
Definition polynomial.hh:178
C Coefficients
The type of the stored coefficient container.
Definition polynomial.hh:156
const Coefficients & coefficients() const
Obtain reference to coefficient vector.
Definition polynomial.hh:230
Polynomial(Coefficients coefficients)
Create from container of coefficients.
Definition polynomial.hh:169
bool operator==(const Polynomial &other) const
Comparison of coefficients.
Definition polynomial.hh:205