data interpolation using cubic splines and transform them to B-form

I have some data points given in space describing a closed periodic curve that i want to interpolate. I know that the curve fitting toolbox offers functions that do that.
For instance csape(x,fx,'periodic') is working perfect, but i'd like to have a B- form representation to have control over the basis. To do so i can use fn2fm(fnk,'B-') to transform the pp-form to B-form but then i gets confusing.
Usually when you read mathematical textbooks that explain how to interpolate periodc function, recommend using following b-spline basis:
In this case we look at the b-splines , , and , since they are local polynomials of degree 3. In matlab they are printed out as b-splines of order 4 since you need four coefficients to describe a polynomial of degree 3. (I have chosen order 4 to have global interpolant)
However to interpolate 8 given data points you need 7 basis functions. To get the right coefficients you have to determine the values of your choosen basis in each node and solve the linear equation. ( For closed periodic curves you have to solve the linear equations for each component)
%% generate data
n = 8;
a = 0;
b = 2*pi;
t = linspace(a,b,n);
int = linspace(a,b,300);
% data points to interpolate in one component
fx = cos(t);
%fy = sin(t);
%fz = zeros(1,length(t));
N = n-1; % # elements and of my basis functions !
x_node = linspace(0,2*pi,N+1); % nodes
element = [1:N;2:N+1]' % elements
A = my_matrix(N,x_node) % load values of all my basis functions
% solve linear equation for one component
ux = A\fx';
%uy = A\fy';
%uz = A\fz';
A =
0 0 0 0 0.1667 0.6667 0.1667
0.1667 0 0 0 0 0.1667 0.6667
0.6667 0.1667 0 0 0 0 0.1667
0.1667 0.6667 0.1667 0 0 0 0
0 0.1667 0.6667 0.1667 0 0 0
0 0 0.1667 0.6667 0.1667 0 0
0 0 0 0.1667 0.6667 0.1667 0
0 0 0 0 0.1667 0.6667 0.1667
Compering this to matlab we get the following:
% cubic spline interpolation for the first component
X = [fx]
%fy;
%fz];
F = csape(t,X,'periodic');
% transformation to B-form
B = (fn2fm(F,'B-'))
B =
struct with fields:
form: 'B-'
knots: [0 0 0 0 0.8976 1.7952 2.6928 3.5904 4.4880 5.3856 6.2832 6.2832 6.2832 6.2832]
coefs: [3×10 double]
number: 10
order: 4
dim: 3
B.knots
ans =
0 0 0 0 3.1416 3.1416 3.1416 6.2832 6.2832 6.2832 6.2832
As it can be seen matlab is using way more knots then i do.
Is it is not like that, if i choose m identical knots that the b-spline at this node / knot is ? This would mean that the b-spline is at the endpoints, since it is actually of order 4 (in matlab) (i.e ) ?
Thats the point where my confusion starts, since we have data that we want to interpolate by a function that is in each node (global ).
Looking at the B-spline basis matlab chooses for a periodic interpolation the first Basis (blue) and the last one (yellow) are those that shoud be , but matlab prits them out to have order 4, and the produced interpolant is .
basis = (spmak(B.knots(1:1+4),1))
basis =
struct with fields:
form: 'B-'
knots: [0 0 0 0 0.8976]
coefs: 1
number: 1
order: 4
dim: 1
Looking at the structure B above it can be seen that the number of basis functions is 10 (for 8 datat points). It seems that if you do interpolation for space curves with csape using periodic condition, matlab after transforming the sturcture to B-form, always takes n+2 b-spline basis functions. But if you doing the interpolation for each coordinate separatly the number of basis functions can differ from coordinate to coordinate you are interpolating.
I wanted to check if i figured out the right basis. Useing the B.coefs and multiply them with the basis lead to the right/same interpolant that i get with my chosen basis.
%plot the first component of the space curve generated by matlab
fig2 = subplot(2,1,1);
p1 = plot(B.knots,B.knots*0,'b-o','MarkerSize',10,'DisplayName','matlab knots');
hold on
p2 = plot(t,fx,'-o','DisplayName','data');
hold on
val = 0;
for i = 1:length(B.coefs)
% generate basis of order 4
B_basis = (spmak(B.knots(i:i+4),1));
fnplt(B_basis)
val = val + fnval(B_basis,int)*B.coefs(1,i);
hold on
end
hold on
p3 = plot(int,val,'-','LineWidth',2,'DisplayName','interpoland by matlab');
legend([p1,p2,p3],'Location','southeast')
title('first component fx by matlab')
% plot first component of the space curve with my basis
f2 = subplot(2,2,1);
plot(int,fval_x,'-','LineWidth',2)
hold on
plot(x_node,0*x_node,'b-o','MarkerFaceColor','r')
hold on
plot(t,fx,'-o')
hold on
plot(int,my_spline(int,element,x_node,'basis'))
legend({'interpolant','xnode','data'},'Location','southeast')
title('first component fx')
hold off
After that i tryed to calculate the coefs matlab is using for his basis. For this i looked up witch values the basis of matlab gives at each node to get a matrix that contains all information. If you use the usual approach you will end up here:
colmat = spcol(knott,4,brk2knt(tau,1))
colmat =
Columns 1 through 6
1.0000 0 0 0 0 0
0 0.2500 0.5833 0.1667 0 0
0 0 0.1667 0.6667 0.1667 0
0 0 0 0.1667 0.6667 0.1667
0 0 0 0 0.1667 0.6667
0 0 0 0 0 0.1667
0 0 0 0 0 0
0 0 0 0 0 0
Columns 7 through 10
0 0 0 0
0 0 0 0
0 0 0 0
0 0 0 0
0.1667 0 0 0
0.6667 0.1667 0 0
0.1667 0.5833 0.2500 0
0 0 0 1.0000
% solve linear equation for the first component
cofcol = (colmat\fx');
cofcol =
ans =
Columns 1 through 6
1.0000 0 1.1764 -0.3764 -1.0059 -1.0059
Columns 7 through 10
-0.3764 1.1764 0 1.0000
% matlab coefficients
B.coefs(1,:)
ans =
Columns 1 through 6
1.0000 1.0000 0.7130 -0.2545 -1.0303 -1.0303
Columns 7 through 10
-0.2545 0.7130 1.0000 1.0000
Obviously wirth wrong coefficients. This leads to the question whitch matrix is used by matlab ? and how to build it by my own?
----------------------------------------------
Questions:
1) does someone know why matlab is using that specific b-spline basis for periodic interpolation ?
2) how is it possible to get a global interpolant using this basis, since at the endpoints the basis shoud be ?
3) how to get the right matrix that contains also the periodic information to determine the coefficients
i.e how to determine the B-form structure interpolating with periodic condtion without using csape
4) is it possible to transform my interpolation to a B-structure ?
5) why do we get n+2 basis functions when we have n data points ?
Thanks in advance.
%%%%%%%%%% ---- %%%%%%%%%
look at the file jump.m, there is a example for a basis by matlab that is of order 4 but its first derivative in the choosen node has a jump. (this happens if n=3)
Derivative of the 4th basis function
The file my_spline.m gives you the basis i have chosen.
Interpolation.m contains all plots that i used above and also some more.
(i.e interpolation for curves in )

Answers (0)

Products

Release

R2018b

Asked:

on 23 Nov 2019

Edited:

on 23 Nov 2019

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!