G+Smo  25.01.0
Geometry + Simulation Modules
 
Loading...
Searching...
No Matches
knotVector_example.cpp

In this example, we show how to create a knot vector, and how to perform some basic operations on it.

First we include the library and use the gismo namespace.

#include <iostream>
#include <string>
#include <algorithm>
#include <gismo.h>
using namespace gismo;
Main header to be included by clients using the G+Smo library.
The G+Smo namespace, containing all definitions for the library.

Then we consider different knot vector initializations. Empty knot vector initialization:

  • empty constructor: sets the degree to -1 and leaves the knots empty.
  • only with degree: set the degree and leaves the knots uninitialized.
    // --- empty constructor
    // --- only with degree
    Class for representing a knot vector.
    Definition gsKnotVector.h:80

To construct a uniform knot vector, we need to specify in the following order:

  • the first knot value;
  • the last knot value;
  • the number of interior knots;
  • the multiplicity at the two end knots;
  • the multiplicity of the interior knots (default = 1);
  • the degree of the spline space (default = -1). If the degree is -1, than the degree is inferred from the multiplicities of the ending knots, assuming clamped knots.

Uniform knot vector initialization:

// --- uniform initialization
real_t a = 1; // starting knot
real_t b = 3; // ending knot
index_t interior = 4; // number of interior knots
index_t multEnd = 3; // multiplicity at the two end knots
gsKnotVector<> kv2(a, b, interior, multEnd);
index_t multInt = 2; // multiplicity of the interior knots (default = 1)
gsKnotVector<> kv3(a, b, interior, multEnd, multInt);
index_t degree = 5; // degree of the spline space (default = -1);
gsKnotVector<> kv4(a, b, interior, multEnd, multInt, degree);
#define index_t
Definition gsConfig.h:32

A knot vector can be defined also by specifying the knot values directly via, passed to the constructor via a container. Knot vector container initialization:

// --- construction from knot container
std::vector<real_t> knotContainer;
knotContainer.push_back(0);
knotContainer.push_back(0.1);
knotContainer.push_back(0.5);
knotContainer.push_back(0.6);
knotContainer.push_back(0.9);
knotContainer.push_back(1);
gsKnotVector<> kv5(knotContainer, 2); // knots, degree

To define uniform knot vector on \([0,1]\), we can use the following constructors:

  • initUniform: sets the knot vector so that it has prescribed number of interior knots and the multiplicities of the ending knots (0, 1) are also set.
  • initClamped: defines the knot vector so that it is uniform and has clamped ending knots.

For a gsKnotVector, we can query its properties, such as

  • size(): returns the total number of knots;
  • iFind(u): returns an iterator to the last occurrence of the knot at the beginning of the knot interval containing the value u;
  • has(u): returns true iff the knot exists in the vector;
  • isUniform(): checks whether the knot vector is uniform;
  • isOpen(): returns true iff the knot is open (i.e., both endpoints have multiplicities equal to degree+1);
  • multiplicity(u): returns the multiplicity of the knot at the value u;
  • etc.
    gsInfo << "kv7.size(): " << kv7.size() << "\n"
    << "kv7.findspan(1.5): " << kv7.iFind(1.5) - kv7.begin() << "\n"
    << "kv7.findspan(2): " << kv7.iFind(2) - kv7.begin() << "\n"
    << "kv7.has(2): " << kv7.has(2) << "\n"
    << "kv7.has(2.1): " << kv7.has(2.1) << "\n"
    << "kv7.isUniform(): " << kv7.isUniform() << "\n"
    << "kv7.isOpen(): " << kv7.isOpen() << "\n"
    << "kv7.multiplicity(4/3): " << kv7.multiplicity(4./3) << "\n"
    << "kv7.numKnotSpans(): " << kv7.uSize() - 1 << "\n\n";
    #define gsInfo
    Definition gsDebug.h:43

Morevoer, we can perform operations, such as

  • unique(): returns unique knot values, without repetitions;
  • greville(): returns the greville points of the B-splines defined on this knot vector;
  • multiplicities(): returns vector of multiplicities of the knots;
  • uniformRefine(numKnots, mult): inserts numKnots (default = 1), each of them mult - times (default = 1), between each pair of knots;
  • degreeElevate(): elevates the degree, i.e., increase the multiplicity of all the knots by one and increment the degree;
  • etc.
    std::vector<real_t> unique = kv6.unique();
    gsInfo << "\nUnique knots: \n";
    std::for_each(unique.begin(), unique.end(), print);
    gsMatrix<> greville = kv6.greville();
    gsInfo << "\n\nGreville points: \n" << greville << "\n\n";
    std::vector<index_t> mult = kv6.multiplicities();
    gsInfo << "Multiplicities: ";
    std::for_each(mult.begin(), mult.end(), print);
    gsInfo << "\n\n";
    printKnotVector(kv6, "kv6");
    gsInfo << "kv6.uniformRefine()\n";
    kv6.uniformRefine();
    printKnotVector(kv6);
    gsInfo << "kv6.degreeElevate()\n";
    kv6.degreeElevate();
    printKnotVector(kv6);
    A matrix with arbitrary coefficient type and fixed or dynamic size.
    Definition gsMatrix.h:41

Finally, here we show how to loop over the knots of a knot vector.

for (gsKnotVector<>::iterator it = kv4.begin(); it != kv4.end(); it++)
{
gsInfo << *it << " ";
}
gsInfo << "\n\n";
// looping over unique knots
for (gsKnotVector<>::uiterator it = kv4.ubegin(); it != kv4.uend(); it++)
{
gsInfo << *it << " ";
}
gsInfo << "\n\n";
std::vector< T >::const_iterator iterator
Definition gsKnotVector.h:97
internal::gsUKnotIterator< T > uiterator
Definition gsKnotVector.h:102

For these and additional capabilities, see the source files of gsKnotVector.

Annotated source file

Here is the full file examples/knotVector_example.cpp. Clicking on a function or class name will lead you to its reference documentation.

#include <iostream>
#include <string>
#include <algorithm>
#include <gismo.h>
using namespace gismo;
// forward declaration of some utility functions
void printKnotVector(const gsKnotVector<>& kv, const std::string& name);
void printKnotVector(const gsKnotVector<>& kv);
void print(const real_t& el);
int main(int argc, char* argv[])
{
gsCmdLine cmd("Tutorial on gsKnotVector class.");
try { cmd.getValues(argc,argv); } catch (int rv) { return rv; }
// ======================================================================
// different construction of a knot vector
// ======================================================================
gsInfo << "------------- Constructions -------------\n";
// --- empty constructor
// --- only with degree
printKnotVector(kv0, "kv0");
printKnotVector(kv1, "kv1");
// --- uniform initialization
real_t a = 1; // starting knot
real_t b = 3; // ending knot
index_t interior = 4; // number of interior knots
index_t multEnd = 3; // multiplicity at the two end knots
gsKnotVector<> kv2(a, b, interior, multEnd);
index_t multInt = 2; // multiplicity of the interior knots (default = 1)
gsKnotVector<> kv3(a, b, interior, multEnd, multInt);
index_t degree = 5; // degree of the spline space (default = -1);
gsKnotVector<> kv4(a, b, interior, multEnd, multInt, degree);
printKnotVector(kv2, "kv2");
printKnotVector(kv3, "kv3");
printKnotVector(kv4, "kv4");
// --- construction from knot container
std::vector<real_t> knotContainer;
knotContainer.push_back(0);
knotContainer.push_back(0.1);
knotContainer.push_back(0.5);
knotContainer.push_back(0.6);
knotContainer.push_back(0.9);
knotContainer.push_back(1);
gsKnotVector<> kv5(knotContainer, 2); // knots, degree
printKnotVector(kv5, "kv5");
// --- more initializations
kv6.initUniform(5, 3); // number of knots, multiple ends
printKnotVector(kv6, "kv6");
kv7.initClamped(a, b, 3, 5); // start, end, degree, number of interior knots
printKnotVector(kv7, "kv7");
// ======================================================================
// some properties
// ======================================================================
gsInfo << "------------- Some properties -------------\n"
<< "kv7: \n\n";
printKnotVector(kv7, "kv7");
gsInfo << "kv7.size(): " << kv7.size() << "\n"
<< "kv7.findspan(1.5): " << kv7.iFind(1.5) - kv7.begin() << "\n"
<< "kv7.findspan(2): " << kv7.iFind(2) - kv7.begin() << "\n"
<< "kv7.has(2): " << kv7.has(2) << "\n"
<< "kv7.has(2.1): " << kv7.has(2.1) << "\n"
<< "kv7.isUniform(): " << kv7.isUniform() << "\n"
<< "kv7.isOpen(): " << kv7.isOpen() << "\n"
<< "kv7.multiplicity(4/3): " << kv7.multiplicity(4./3) << "\n"
<< "kv7.numKnotSpans(): " << kv7.uSize() - 1 << "\n\n";
// ======================================================================
// some operations
// ======================================================================
gsInfo << "------------- Some operations -------------\n";
printKnotVector(kv6, "kv6");
std::vector<real_t> unique = kv6.unique();
gsInfo << "\nUnique knots: \n";
std::for_each(unique.begin(), unique.end(), print);
gsMatrix<> greville = kv6.greville();
gsInfo << "\n\nGreville points: \n" << greville << "\n\n";
std::vector<index_t> mult = kv6.multiplicities();
gsInfo << "Multiplicities: ";
std::for_each(mult.begin(), mult.end(), print);
gsInfo << "\n\n";
printKnotVector(kv6, "kv6");
gsInfo << "kv6.uniformRefine()\n";
printKnotVector(kv6);
gsInfo << "kv6.degreeElevate()\n";
printKnotVector(kv6);
// ======================================================================
// looping over knots
// ======================================================================
gsInfo << "\n"
<< "------------- Looping over knots -------------\n"
<< "kv4: \n";
for (gsKnotVector<>::iterator it = kv4.begin(); it != kv4.end(); it++)
{
gsInfo << *it << " ";
}
gsInfo << "\n\n";
// looping over unique knots
for (gsKnotVector<>::uiterator it = kv4.ubegin(); it != kv4.uend(); it++)
{
gsInfo << *it << " ";
}
gsInfo << "\n\n";
gsInfo << "For other capabilites of gsKnotVector look at "
"src/gsNurbs/gsKnotVector.h\n" << "\n";
return 0;
}
void print(const real_t& el)
{
gsInfo << el << " ";
}
void printKnotVector(const gsKnotVector<>& kv,
const std::string& name)
{
gsInfo << name << ":\n" << kv << "\n";
gsInfo << "knot values:\n";
for (gsKnotVector<>::const_iterator it = kv.begin(); it != kv.end(); it++)
{
gsInfo << *it << " ";
}
gsInfo << "\n\n";
}
void printKnotVector(const gsKnotVector<>& kv)
{
for (gsKnotVector<>::const_iterator it = kv.begin(); it != kv.end(); it++)
{
gsInfo << *it << " ";
}
gsInfo << "\n\n";
}
Class for command-line argument parsing.
Definition gsCmdLine.h:57
bool isOpen() const
Definition gsKnotVector.h:882
size_t size() const
Number of knots (including repetitions).
Definition gsKnotVector.h:242
iterator begin() const
Returns iterator pointing to the beginning of the repeated knots.
Definition gsKnotVector.hpp:117
bool has(T knot) const
Definition gsKnotVector.h:819
void degreeElevate(const short_t &i=1)
Definition gsKnotVector.hpp:937
void uniformRefine(mult_t numKnots=1, mult_t mult=1)
Definition gsKnotVector.hpp:820
void initClamped(int degree, unsigned numKnots=2, unsigned mult_interior=1)
Definition gsKnotVector.hpp:693
knotContainer unique() const
Returns unique knots.
Definition gsKnotVector.h:273
multContainer multiplicities() const
Returns vector of multiplicities of the knots.
Definition gsKnotVector.hpp:714
bool isUniform(T tol=1e-9) const
Checks whether the knot vector is uniform.
Definition gsKnotVector.h:871
iterator iFind(const T u) const
Returns an iterator to the last occurrence of the knot at the beginning of the knot interval containi...
Definition gsKnotVector.hpp:779
size_t uSize() const
Number of unique knots (i.e., without repetitions).
Definition gsKnotVector.h:245
mult_t multiplicity(T u) const
Definition gsKnotVector.hpp:421
void initUniform(T first, T last, unsigned interior, unsigned mult_ends, unsigned mult_interior, short_t degree=-1)
Definition gsKnotVector.hpp:643
iterator end() const
Returns iterator pointing past the end of the repeated knots.
Definition gsKnotVector.hpp:124
gsMatrix< T > greville() const
Definition gsKnotVector.h:540