11 #ifndef BEMBEL_SRC_SPLINE_BEZIEREXTRACTION_HPP_
12 #define BEMBEL_SRC_SPLINE_BEZIEREXTRACTION_HPP_
24 const std::vector<T> &y_knots,
25 const std::vector<T> &x_unique_knots,
26 const std::vector<T> &y_unique_knots,
27 const int polynomial_degree_x,
28 const int polynomial_degree_y) noexcept {
33 constexpr
double sparseTol = 0.001;
35 const int size_phi_x = (x_unique_knots.size() - 1) * polynomial_degree_x;
36 const int size_phi_y = (y_unique_knots.size() - 1) * polynomial_degree_y;
37 const int size_phi = size_phi_x * size_phi_y;
38 const int size_psi_x = x_knots.size() - polynomial_degree_x;
39 const int size_psi_y = y_knots.size() - polynomial_degree_y;
40 const int size_psi = size_psi_x * size_psi_y;
43 const auto xmask = MakeInterpolationMask(polynomial_degree_x);
44 const auto ymaks = MakeInterpolationMask(polynomial_degree_y);
49 assert(((
int)(xmask.size() * (x_unique_knots.size() - 1))) == size_phi_x);
50 assert(((
int)(xpoint.size())) == size_phi_x);
51 assert(((
int)(ypoint.size())) == size_phi_y);
53 Eigen::Matrix<T, -1, -1> tempsolver =
54 Eigen::Matrix<T, -1, -1>::Zero(size_phi, size_phi);
56 double *coefficients_x =
new double[polynomial_degree_x];
57 double *coefficients_y =
new double[polynomial_degree_y];
59 for (
int i = 0; i < polynomial_degree_x; i++) coefficients_x[i] = 0;
61 for (
int i = 0; i < polynomial_degree_y; i++) coefficients_y[i] = 0;
63 auto BezBasis = [](std::vector<double> uniq,
int deg,
int pos,
double pt,
65 std::div_t loc = std::div(pos, deg);
66 if (pt > uniq[loc.quot + 1] || pt < uniq[loc.quot]) {
70 double out = Bembel::Basis::ShapeFunctionHandler::evalCoef(
71 deg - 1, coef, Rescale(pt, uniq[loc.quot], uniq[loc.quot + 1]));
79 for (
int iy = 0; iy < size_phi_y; iy++) {
80 for (
int ix = 0; ix < size_phi_x; ix++) {
81 for (
int y = 0; y < size_phi_y; y++) {
82 for (
int x = 0; x < size_phi_x; x++) {
83 tempsolver(y * size_phi_x + x, ix * size_phi_y + iy) =
84 BezBasis(x_unique_knots, polynomial_degree_x, ix, xpoint[x],
86 BezBasis(y_unique_knots, polynomial_degree_y, iy, ypoint[y],
93 delete[] coefficients_x;
94 delete[] coefficients_y;
96 Eigen::FullPivLU<Eigen::Matrix<double, -1, -1>> lu_decomp(tempsolver);
97 assert(lu_decomp.rank() == size_phi);
99 Eigen::Matrix<T, -1, -1> solve = tempsolver.inverse();
101 Eigen::Matrix<T, -1, -1> Proj(size_phi, size_psi);
102 Eigen::Matrix<T, -1, -1> unit =
103 Eigen::Matrix<T, -1, -1>::Zero(size_psi_y, size_psi_x);
106 for (
int i = 0; i < size_psi_x; i++)
107 for (
int j = 0; j < size_psi_y; j++) {
109 Eigen::Matrix<T, -1, 1> smallBase =
111 Proj.col(i * size_psi_y + j) = (solve * smallBase).transpose();
115 return (Proj.sparseView()).pruned(sparseTol);
std::vector< T > MakeInterpolationPoints(const std::vector< T > &uniq, const std::vector< T > &mask) noexcept
Creates a T-vector of equidistant itnerpolation points for a given knot vector without any repetition...
Eigen::SparseMatrix< T > MakeProjection(const std::vector< T > &x_knots, const std::vector< T > &y_knots, const std::vector< T > &x_unique_knots, const std::vector< T > &y_unique_knots, const int polynomial_degree_x, const int polynomial_degree_y) noexcept
implements Bezier extraction via the solution of an interpolation problem.
Eigen::Matrix< T, -1, -1 > DeBoorTP(Eigen::Matrix< T, -1, -1 > const &control_points, std::vector< double > const &knots_x, std::vector< double > const &knots_y, std::vector< double > const &evaluation_points_x, std::vector< double > const &evaluation_points_y) noexcept
Simple TP Bsplines.
Eigen::Matrix< T, -1, 1 > Unroll(const Eigen::Matrix< T, -1, -1 > &input_matrix) noexcept
Tiny helper functions.
Routines for the evalutation of pointwise errors.