Skip to content

Commit 16f2960

Browse files
committed
Add example on periodic interpolations / fitting
1 parent 0e34685 commit 16f2960

File tree

3 files changed

+53
-1
lines changed

3 files changed

+53
-1
lines changed

README.md

+2
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,8 @@ This package provides:
1919

2020
- spline interpolations, smoothing splines and function approximation;
2121

22+
- periodic splines;
23+
2224
- basis recombination, for generating bases satisfying homogeneous boundary
2325
conditions using linear combinations of B-splines.
2426
Supported boundary conditions include Dirichlet, Neumann, Robin, and

docs/src/index.md

+2
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ This package provides:
1515
- [spline interpolations](@ref interpolation-example), [smoothing splines](@ref smoothing-example) and
1616
[function approximation](@ref function-approximation-example);
1717

18+
- [periodic splines](@ref interpolation-periodic-example);
19+
1820
- [basis recombination](@ref basis-recombination-api), for generating bases
1921
satisfying homogeneous boundary conditions using linear combinations of
2022
B-splines.

examples/interpolation.jl

+49-1
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@ current_figure() # hide
3737
# We can also choose other interpolation orders for comparison:
3838

3939
for k (5, 6, 8)
40-
S = interpolate(xs, ys, BSplineOrder(k))
40+
local S = interpolate(xs, ys, BSplineOrder(k))
4141
lines!(0..1, S; label = "k = $k", color = Cycled(k - 3))
4242
end
4343
axislegend()
@@ -177,3 +177,51 @@ lines!(ax, -0.5..1.5, E_flat; label = "Flat", linestyle = :dot, linewidth = 2)
177177
axislegend(ax)
178178
fig
179179

180+
# ## [Periodic data](@id interpolation-periodic-example)
181+
#
182+
# It is also possible to interpolate or fit data which is expected to result from a periodic
183+
# function, such that ``f(x + L) = f(x)`` for some period ``L``.
184+
# For this, one can pass [`Periodic(L)`](@ref Periodic) as a boundary condition to
185+
# [`interpolate`](@ref) or [`fit`](@ref).
186+
#
187+
# The following example starts from data at points ``x_j`` within the ``[-1, 1]`` interval,
188+
# and assumes the resulting spline can be extended periodically outside of this interval.
189+
190+
# We start by generating some data:
191+
192+
N = 40
193+
f_slow(x) = cospi(x)
194+
f_fast(x) = 0.2 * sinpi(40x)
195+
xs = [-cospi(n / N) for n = 0:(N - 1)] # in [-1, 1) // NOTE: the endpoint (x = 1) must be excluded!!
196+
ys = @. f_slow(xs) + f_fast(xs);
197+
198+
# Interpolate the data:
199+
200+
L = 2
201+
S_interp = interpolate(xs, copy(ys), BSplineOrder(4), Periodic(L))
202+
203+
# Create a periodic cubic smoothing spline. Note that `BSplineOrder(4)` is assumed (it's
204+
# currently the only supported choice). We also compare with a smoothing spline which
205+
# doesn't assume periodic boundary conditions.
206+
207+
λ = 0.001 # smoothing parameter
208+
S_fit_natural = fit([xs; xs[begin] + L], [ys; ys[begin]], λ) # for comparison, compute a natural spline (no implied periodicity)
209+
S_fit_periodic = fit(xs, ys, λ, Periodic(L))
210+
211+
# Plot the results:
212+
213+
fig = Figure()
214+
ax = Axis(fig[1, 1])
215+
scatter!(ax, xs, ys; label = "Data")
216+
lines!(ax, -1..1, S_interp; label = "Interpolation", color = (:grey, 0.5))
217+
lines!(ax, -1..1, S_fit_periodic; linewidth = 3, label = "Smoothing (periodic)")
218+
lines!(ax, -1..1, S_fit_natural; linewidth = 3, linestyle = :dash, label = "Smoothing (natural)")
219+
axislegend(ax)
220+
fig
221+
222+
# As can be expected, the smoothing spline with periodic boundary conditions mostly differs
223+
# from the "natural" smoothing spline near the boundaries.
224+
# In particular, the natural smoothing spline simply does not satisfy periodic boundary
225+
# conditions (even at the level of the zero-th derivative!), so it's not very adapted for
226+
# constructing periodic functions.
227+

0 commit comments

Comments
 (0)