Splines_Module

Classes

struct  Eigen::SplineFitting< SplineType >
 Spline fitting methods. More...
 
struct  Eigen::SplineTraits< Spline< Scalar_, Dim_, Degree_ >, Dynamic >
 Compile-time attributes of the Spline class for Dynamic degree. More...
 
struct  Eigen::SplineTraits< Spline< Scalar_, Dim_, Degree_ >, _DerivativeOrder >
 Compile-time attributes of the Spline class for fixed degree. More...
 
class  Eigen::Spline< Scalar_, Dim_, Degree_ >
 A class representing multi-dimensional spline curves. More...
 

Functions

template<typename KnotVectorType >
void Eigen::KnotAveraging (const KnotVectorType &parameters, DenseIndex degree, KnotVectorType &knots)
 Computes knot averages. More...
 
template<typename KnotVectorType , typename ParameterVectorType , typename IndexArray >
void Eigen::KnotAveragingWithDerivatives (const ParameterVectorType &parameters, const unsigned int degree, const IndexArray &derivativeIndices, KnotVectorType &knots)
 Computes knot averages when derivative constraints are present. Note that this is a technical interpretation of the referenced article since the algorithm contained therein is incorrect as written. More...
 
template<typename PointArrayType , typename KnotVectorType >
void Eigen::ChordLengths (const PointArrayType &pts, KnotVectorType &chord_lengths)
 Computes chord length parameters which are required for spline interpolation. More...
 

Detailed Description

Function Documentation

◆ ChordLengths()

template<typename PointArrayType , typename KnotVectorType >
void Eigen::ChordLengths ( const PointArrayType &  pts,
KnotVectorType &  chord_lengths 
)

Computes chord length parameters which are required for spline interpolation.

Parameters
[in]ptsThe data points to which a spline should be fit.
[out]chord_lengthsThe resulting chord length vector.
See also
Les Piegl and Wayne Tiller, The NURBS book (2nd ed.), 1997, 9.2.1 Global Curve Interpolation to Point Data
171  {
172  typedef typename KnotVectorType::Scalar Scalar;
173 
174  const DenseIndex n = pts.cols();
175 
176  // 1. compute the column-wise norms
177  chord_lengths.resize(pts.cols());
178  chord_lengths[0] = 0;
179  chord_lengths.rightCols(n - 1) =
180  (pts.array().leftCols(n - 1) - pts.array().rightCols(n - 1)).matrix().colwise().norm();
181 
182  // 2. compute the partial sums
183  std::partial_sum(chord_lengths.data(), chord_lengths.data() + n, chord_lengths.data());
184 
185  // 3. normalize the data
186  chord_lengths /= chord_lengths(n - 1);
187  chord_lengths(n - 1) = Scalar(1);
188 }
const unsigned n
Definition: CG3DPackingUnitTest.cpp:11
SCALAR Scalar
Definition: bench_gemm.cpp:45
Eigen::Map< Eigen::Matrix< T, Eigen::Dynamic, Eigen::Dynamic, Eigen::ColMajor >, 0, Eigen::OuterStride<> > matrix(T *data, int rows, int cols, int stride)
Definition: common.h:85
EIGEN_DEFAULT_DENSE_INDEX_TYPE DenseIndex
Definition: Meta.h:75

References matrix(), and n.

Referenced by check_global_interpolation2d(), check_global_interpolation_with_derivatives2d(), Eigen::SplineFitting< SplineType >::Interpolate(), and Eigen::SplineFitting< SplineType >::InterpolateWithDerivatives().

◆ KnotAveraging()

template<typename KnotVectorType >
void Eigen::KnotAveraging ( const KnotVectorType &  parameters,
DenseIndex  degree,
KnotVectorType &  knots 
)

Computes knot averages.

The knots are computed as

\begin{align*} u_0 & = \hdots = u_p = 0 \\ u_{m-p} & = \hdots = u_{m} = 1 \\ u_{j+p} & = \frac{1}{p}\sum_{i=j}^{j+p-1}\bar{u}_i \quad\quad j=1,\hdots,n-p \end{align*}

where \(p\) is the degree and \(m+1\) the number knots of the desired interpolating spline.

Parameters
[in]parametersThe input parameters. During interpolation one for each data point.
[in]degreeThe spline degree which is used during the interpolation.
[out]knotsThe output knot vector.
See also
Les Piegl and Wayne Tiller, The NURBS book (2nd ed.), 1997, 9.2.1 Global Curve Interpolation to Point Data
47  {
48  knots.resize(parameters.size() + degree + 1);
49 
50  for (DenseIndex j = 1; j < parameters.size() - degree; ++j) knots(j + degree) = parameters.segment(j, degree).mean();
51 
52  knots.segment(0, degree + 1) = KnotVectorType::Zero(degree + 1);
53  knots.segment(knots.size() - degree - 1, degree + 1) = KnotVectorType::Ones(degree + 1);
54 }
const Mdouble degree
Definition: ExtendedMath.h:32
double Zero
Definition: pseudosolid_node_update_elements.cc:35
std::ptrdiff_t j
Definition: tut_arithmetic_redux_minmax.cpp:2

References constants::degree, j, and oomph::PseudoSolidHelper::Zero.

Referenced by Eigen::SplineFitting< SplineType >::Interpolate(), and Eigen::KnotAveragingWithDerivatives().

◆ KnotAveragingWithDerivatives()

template<typename KnotVectorType , typename ParameterVectorType , typename IndexArray >
void Eigen::KnotAveragingWithDerivatives ( const ParameterVectorType &  parameters,
const unsigned int  degree,
const IndexArray &  derivativeIndices,
KnotVectorType &  knots 
)

Computes knot averages when derivative constraints are present. Note that this is a technical interpretation of the referenced article since the algorithm contained therein is incorrect as written.

Parameters
[in]parametersThe parameters at which the interpolation B-Spline will intersect the given interpolation points. The parameters are assumed to be a non-decreasing sequence.
[in]degreeThe degree of the interpolating B-Spline. This must be greater than zero.
[in]derivativeIndicesThe indices corresponding to parameters at which there are derivative constraints. The indices are assumed to be a non-decreasing sequence.
[out]knotsThe calculated knot vector. These will be returned as a non-decreasing sequence
See also
Les A. Piegl, Khairan Rajab, Volha Smarodzinana. 2008. Curve interpolation with directional constraints for engineering design. Engineering with Computers
79  {
80  typedef typename ParameterVectorType::Scalar Scalar;
81 
82  DenseIndex numParameters = parameters.size();
83  DenseIndex numDerivatives = derivativeIndices.size();
84 
85  if (numDerivatives < 1) {
86  KnotAveraging(parameters, degree, knots);
87  return;
88  }
89 
90  DenseIndex startIndex;
91  DenseIndex endIndex;
92 
93  DenseIndex numInternalDerivatives = numDerivatives;
94 
95  if (derivativeIndices[0] == 0) {
96  startIndex = 0;
97  --numInternalDerivatives;
98  } else {
99  startIndex = 1;
100  }
101  if (derivativeIndices[numDerivatives - 1] == numParameters - 1) {
102  endIndex = numParameters - degree;
103  --numInternalDerivatives;
104  } else {
105  endIndex = numParameters - degree - 1;
106  }
107 
108  // There are (endIndex - startIndex + 1) knots obtained from the averaging
109  // and 2 for the first and last parameters.
110  DenseIndex numAverageKnots = endIndex - startIndex + 3;
111  KnotVectorType averageKnots(numAverageKnots);
112  averageKnots[0] = parameters[0];
113 
114  int newKnotIndex = 0;
115  for (DenseIndex i = startIndex; i <= endIndex; ++i)
116  averageKnots[++newKnotIndex] = parameters.segment(i, degree).mean();
117  averageKnots[++newKnotIndex] = parameters[numParameters - 1];
118 
119  newKnotIndex = -1;
120 
121  ParameterVectorType temporaryParameters(numParameters + 1);
122  KnotVectorType derivativeKnots(numInternalDerivatives);
123  for (DenseIndex i = 0; i < numAverageKnots - 1; ++i) {
124  temporaryParameters[0] = averageKnots[i];
125  ParameterVectorType parameterIndices(numParameters);
126  int temporaryParameterIndex = 1;
127  for (DenseIndex j = 0; j < numParameters; ++j) {
128  Scalar parameter = parameters[j];
129  if (parameter >= averageKnots[i] && parameter < averageKnots[i + 1]) {
130  parameterIndices[temporaryParameterIndex] = j;
131  temporaryParameters[temporaryParameterIndex++] = parameter;
132  }
133  }
134  temporaryParameters[temporaryParameterIndex] = averageKnots[i + 1];
135 
136  for (int j = 0; j <= temporaryParameterIndex - 2; ++j) {
137  for (DenseIndex k = 0; k < derivativeIndices.size(); ++k) {
138  if (parameterIndices[j + 1] == derivativeIndices[k] && parameterIndices[j + 1] != 0 &&
139  parameterIndices[j + 1] != numParameters - 1) {
140  derivativeKnots[++newKnotIndex] = temporaryParameters.segment(j, 3).mean();
141  break;
142  }
143  }
144  }
145  }
146 
147  KnotVectorType temporaryKnots(averageKnots.size() + derivativeKnots.size());
148 
149  std::merge(averageKnots.data(), averageKnots.data() + averageKnots.size(), derivativeKnots.data(),
150  derivativeKnots.data() + derivativeKnots.size(), temporaryKnots.data());
151 
152  // Number of knots (one for each point and derivative) plus spline order.
153  DenseIndex numKnots = numParameters + numDerivatives + degree + 1;
154  knots.resize(numKnots);
155 
156  knots.head(degree).fill(temporaryKnots[0]);
157  knots.tail(degree).fill(temporaryKnots.template tail<1>()[0]);
158  knots.segment(degree, temporaryKnots.size()) = temporaryKnots;
159 }
int i
Definition: BiCGSTAB_step_by_step.cpp:9
void KnotAveraging(const KnotVectorType &parameters, DenseIndex degree, KnotVectorType &knots)
Computes knot averages.
Definition: SplineFitting.h:47
char char char int int * k
Definition: level2_impl.h:374

References constants::degree, i, j, k, and Eigen::KnotAveraging().

Referenced by Eigen::SplineFitting< SplineType >::InterpolateWithDerivatives().