# Parametric differentiable interpolation of a 2D data set

I have a set of data

table = Reverse[{
{0, -947}, {-212, -947}, {-424, -950}, {-635, -963}, {-845, -995}, {-1051, -1044},
{-1248, -1119}, {-1432, -1224}, {-1591,-1365}, {-1715, -1537}, {-1796, -1732},
{-1828, -1942}, {-1810,-2153}, {-1755, -2357}, {-1668, -2551}, {-1556, -2730},
{-1423,-2895}, {-1278, -3050}, {-1126, -3197}, {-973, -3343}, {-803,-3506}
}];


which I need to interpolate with a parametric curve. Endpoints and tangent vectors at them are critical. Trying independent polynomial fits for X and Y leads to a wavy curve which is unacceptable. BSplineFunction of degree around 3 leads to a very good-looking curve:

interp = BSplineFunction[table, SplineDegree -> 3];
Show[ListPlot[table], ParametricPlot[interp[t], {t, 0, 1}], AspectRatio -> 1]


but has a discontinuous derivative (btw: why? help promises that it should be a BSplineFunction of one lesser degree but it's a scary jump-step function if you plot it):

x1[t_?NumericQ] := Module[{val}, val = interp[t]; First@val]
y1[t_?NumericQ] := Module[{val}, val = interp[t]; Last@val]
Plot[Norm[{x1'[t], y1'[t]}], {t, 0, 1}, PlotRange -> All]


I then intend to use these functions in NDSolve, NIntegrate etc., therefore behaviour like above is too bad. What parametric interpolation is better in this case?

-
 What are x1 and y1? – VLC Feb 7 at 15:21 @VLC check the x and y in mathematica.stackexchange.com/questions/19229/… – PlatoManiac Feb 7 at 15:41 @PlatoManiac Ah, ok. – VLC Feb 7 at 15:55 By extracting the values from the BSplineFunction and then differentiating, you are taking a finite difference derivative sampled at whatever points Plot feels like using. Try e.g. Plot[Norm[interp'[t]], {t, 0, 1}], which I think you will find much better. – Oleksandr R. Feb 8 at 1:41

Borrowing the parametrizeCurve[] routine from this answer (it's amazing what searching can do...), you can do this:

tvals = parametrizeCurve[table];
{ft, gt} = Interpolation[Transpose[{tvals, #}], Method -> "Spline"] & /@ Transpose[table];

ParametricPlot[{ft[u], gt[u]}, {u, 0, 1}, Axes -> None, Frame -> True,
Epilog -> {AbsolutePointSize[4], Magenta, Point /@ table}]


Verify the $C^2$ continuity:

{Plot[{ft'[u], gt'[u]}, {u, 0, 1}], Plot[{ft''[u], gt''[u]}, {u, 0, 1}]} // GraphicsRow


-
 There turns out to be some substantial wavering at the lower end, so I had to come up with some crazy Fit with basis {1,t,t^2,...,t^6,Exp[0.05 t],Cos[t]} which magically led to incredibly smooth curve with constant-signed curvature. – level1807 Feb 20 at 14:14 All this is so important because of its architectural nature. – level1807 Feb 20 at 14:15

(1) I get a reasonable result interpolating separately.

(2) I don't think your derivatives are doing what you expect.

x1 = Interpolation[table[[All, 1]]];
y1 = Interpolation[table[[All, 2]]];

Show[ListPlot[table], ParametricPlot[{x1[t], y1[t]}, {t, 1, 21}],
AspectRatio -> 1]


Here are those derivatives.

Plot[{x1'[t], y1'[t]}, {t, 0, 21}, PlotRange -> All]


If you raise the InterpolationOrder then those derivative curves get smoother.

-
 Problem with Interpolation is that as soon as no points are close to each other, everything seems fine. But if data is not equidistant like this, the curve breaks between close points - something that doesn't happen with BezierFunction for example (though it's not an interpolation at all). – level1807 Feb 8 at 6:30

Check!

target = Interpolation[{#, Norm[{x1'[#], y1'[#]}]} & /@
Range[0, 1, .01], InterpolationOrder -> 3];
Plot[target[t], {t, 0, 1}, PlotStyle -> Thick,PlotRange -> {0, 60000}, Frame -> True]


It will be better if you try first to learn from the answers of your previous questions! InterpolationOrder is the trick in this case.

BR

-
 I did learn from your previous answer. It's just that I already have a big chunck of code written and now I try to find a good parametrization of a curve for those calculations. But what's the sense in interpolating derivatives? I need a smooth curve which has smooth derivative out of the box. – level1807 Feb 7 at 15:31 @level1807 do not be offended! The above interpolating function target is a smooth function. – PlatoManiac Feb 7 at 15:42 I see that it's smooth, but derivative is not what I need to interpolate. target is not a derivative of x1[t] ot y1[t], while I need to construct an interpolation curve {x1[t], y1[t]} which has smooth x1'[t] and y1'[t]. Smooth graphs is not what I chase here. Does it make any sense? – level1807 Feb 7 at 16:10