Reference

This package's workhorse function is sinfit(p::Problem, a::Algorithm). It takes a problem p and calculates a fit using algorithm a.

SinusoidalRegressions.sinfitFunction
sinfit(problem::Problem, algorithm::Algorithm)

Calculate a sinosoidal regression on problem using algorithm.

Currently supported problem types are:

  • Sin3Problem – three-parameter sinusoidal regression
  • Sin4Problem – four-parameter sinusoidal regression
  • MixedLinSin4Problem – four-parameter mixed linear and sinusoidal regression
  • MixedLinSin5Problem – five-parameter mixed linear and sinusoidal regression

Currently supported algorithms are:

  • IEEE1057
  • IntegralEquations
  • LevMar
  • Liang

Example

julia> using SinusoidalRegressions
julia> t = range(0, 1, length = 100)                  # time instants
julia> s = sin.(2*pi*15*t .+ pi/4) .+ 0.1*randn(100)  # noisy samples
julia> p = Sin3Problem(t, s, 15)                      # define regression problem
julia> sinfit(p, IEEE1057())                          # calculate fit with IEEE 1057
Sinusoidal parameters SinusoidP{Float64}:
  Frequency (Hz)      : 15.0
  DC                  : -0.01067218324878172
  Sine amplitude (Q)  : 0.7299806464221965
  Cosine amplitude (I): 0.6822068658523716

See the documentation for more details.

source

Algorithms

IEEE 1057

Sinusoidal regressions specified by 1057-2017, IEEE Standard for Digitizing Waveform Recorders. These are the same algorithms specified in 1241-2010, IEEE Standard for Terminology and Test Methods for Analog-to-Digital Converters.

SinusoidalRegressions.IEEE1057Type
IEEE1057([iterations = 6]) <: Algorithm

Define an instance of the IEEE 1057 sinusoidal fitting algorithm.

Optional argument iterations specifies how many iterations to run before the algorithm stops. The default value is 6, which is the value recommended by the standard. This value is only used when calculating a 4-parameter fit.

source

Method of integral equations

Four types of sinusoidal regressions using the algorithms proposed by J. Jacquelin in "Régressions et Equations Intégrales". These algorithms are not iterative, and they do not require an initial estimate of the frequency or any other parameter. They may be used by themselves, or to calculate initial estimates for more-precise least-squares methods based on non-linear optimization (described below).

SinusoidalRegressions.IntegralEquationsType
IntegralEquations() <: Algorithm

Define an instance of the integral-equations sinusoidal fitting algorithm described by J. Jacquelin in "Régressions et équations intégrales", 2014 (available at https://fr.scribd.com/doc/14674814/Regressions-et-equations-integrales).

This algorithm does not accept any configuration parameters.

source

Non-linear optimization

Wrapper for LsqFit.curve_fit(), which defines the appropriate model, calculates initial parameter estimates if not provided by the user, and wraps the returned fit in the appropriate parameter container.

SinusoidalRegressions.LevMarType
LevMar([use_ga = false]) <: Algorithm

Define an instance of the Levenberg-Marquardt sinusoidal fitting algorithm.

If the optional argument use_ga is set to true, the algorithm will use geodesic acceleration to potentially improve its performance and accuracy. See curve_fit for more details.

source

Liang

Algorithm designed for fitting when only a fraction of a period is sampled.

SinusoidalRegressions.LiangType
Liang([threshold = 0.15, iterations = 100, q = 1e-5]) <: Algorithm

Define an instance of the sinusoidal fitting algorithm described in Liang et al, "Fitting Algorithm of Sine Wave with Partial Period Waveforms and Non-Uniform Sampling Based on Least-Square Method." Journal of Physics: Conference Series 1149.1 (2018)ProQuest. Web. 17 Apr. 2023.

This algorithm is designed for scenarios where only a fraction of a period of the sinusoid has been sampled. Its optional parameters threshold and q are described in the paper. Additionally, a maximum number of iterations may be specified in iterations.

source

Problems

A Problem encapsulates what is known: at a minimum, the sampling times and the samples, and possibly also estimates or bounds on some or all parameters. The problem type specifies the number of unknown parameters, and the model (sinusoidal or mixed linear-sinusoidal).

SinusoidalRegressions.Sin3ProblemType
Sin3Problem(X, Y, f , [DC, Q, I, lb, ub]) <: Problem

Define a three-parameter sinusoidal regression problem.

The data is fit to the model $f(x; DC, Q, I) = DC + Q\sin(2πfx) + I\cos(2πfx)$. The sampling instants are given by X, and the samples by Y. The frequency f (in Hz) is assumed to be known exactly.

When using a fitting algorithm that accepts initial parameter estimates, these may be given by the optional keyword arguments DC, Q and I (default missing). Lower and upper bounds may be specified in lb and ub, which must be vectors of length 3.

See also: Sin4Problem

source
SinusoidalRegressions.Sin4ProblemType
Sin4Problem(X, Y ; [f, DC, Q, I, lb, ub]) <: Problem

Define a four-parameter sinusoidal regression problem.

The data is fit to the model $f(x; f, DC, Q, I) = DC + Q\sin(2πfx) + I\cos(2πfx)$. The sampling instants are given by X, and the samples by Y.

When using a fitting algorithm that accepts initial parameter estimates, these may be given by the optional keyword arguments f, DC, Q and I (default missing). Lower and upper bounds may be specified in lb and ub, which must be vectors of length 4.

See also: Sin3Problem

source
SinusoidalRegressions.MixedLinSin4ProblemType
MixedLinSin4Problem(X, Y, f ; [DC, Q, I, m, lb, ub])

Define a four-parameter mixed linear-sinusoidal regression problem.

The data is fit to the model $f(x; DC, Q, I, m) = DC + Q\sin(2πfx) + I\cos(2πfx) + mx$. The sampling instants are given by X, and the samples by Y. The frequency f (in Hz) is assumed to be known exactly.

When using a fitting algorithm that accepts initial parameter estimates, these may be given by the optional keyword arguments DC, Q I and m (default missing). Lower and upper bounds may be specified in lb and ub, which must be vectors of length 4.

See also: MixedLinSin5Problem

source
SinusoidalRegressions.MixedLinSin5ProblemType
MixedLinSin5Problem(X, Y ; [f, DC, Q, I, m, lb, ub])

Define a five-parameter mixed linear-sinusoidal regression problem.

The data is fit to the model $f(x ; f, DC, Q, I, m) = DC + Q\sin(2πfx) + I\cos(2πfx) + mx$. The sampling instants are given by X, and the samples by Y.

When using a fitting algorithm that accepts initial parameter estimates, these may be given by the optional keyword arguments f, DC, Q I and m (default missing). Lower and upper bounds may be specified in lb and ub, which must be vectors of length 5.

See also: MixedLinSin4Problem

source

Problem-Algorithm matrix

The following table shows which algorithms can solve which sinusoidal regression problems:

IEEE1057IntegralEquationsLevMarLiang
Sin3Problem
Sin4Problem
MixedLinearSin4Problem
MixedLinearSin5Problem

Sinusoidal parameters

SinusoidalRegressions.SinusoidPMethod
SinusoidP{T}(f, DC, Q, I)

Construct a SinusoidP{T} with the given parameters, promoting to a common type T if necessary.

To express the model as $s(x) = M\cos(2πfx + θ)$, use the torect function.

Examples

julia> SinusoidP(10, 1, -0.5, 1.2)
Sinusoidal parameters SinusoidP{Float64}:
  Frequency (Hz)      : 10.0
  DC                  : 1.0
  Sine amplitude (Q)  : -0.5
  Cosine amplitude (I): 1.2

julia> SinusoidP(1, 0, torect(1, -π/2)...)  # A pure sine
Sinusoidal parameters SinusoidP{Float64}:
  Frequency (Hz)      : 1.0
  DC                  : 0.0
  Sine amplitude (Q)  : 1.0
  Cosine amplitude (I): 0.0
source
SinusoidalRegressions.SinusoidPMethod
SinusoidP{T}(; f, DC, Q, I)

Construct a SinusoidP{T} specifying each parameter by name, promoting to a common type T if necessary.

Example

julia> SinusoidP(DC = 1, Q = -0.5, I = 1.2, f = 10)
Sinusoidal parameters SinusoidP{Float64}:
  Frequency (Hz)      : 10.0
  DC                  : 1.0
  Sine amplitude (Q)  : -0.5
  Cosine amplitude (I): 1.2
source
SinusoidalRegressions.SinusoidPMethod
(P::SinusoidP)(t)

Evaluate the sinusoidal function specified by the parameters P at the values given by t, which may be a scalar or a collection.

Example

julia> P = SinusoidP(DC = 1, Q = -0.5, I = 1.2, f = 10)
julia> t = range(0, 0.7, length = 5)
julia> P(t)
5-element Vector{Float64}:
  2.2
  1.4999999999999996
 -0.2000000000000004
  0.49999999999999944
  2.200000000000001
source
SinusoidalRegressions.MixedLinearSinusoidPMethod
MixedLinearSinusoidP{T}(f, DC, Q, I, m)

Construct a MixedLinearSinusoidP{T} with the given parameters, promoting to a common type T if necessary.

Example

julia> MixedLinearSinusoidP(10, 0, -1.2, 0.4, 2.1)
Mixed Linear-Sinusoidal parameters MixedLinearSinusoidP{Float64}:
  Frequency (Hz)       : 10.0
  DC                   : 0.0
  Sine amplitude (Q)   : -1.2
  Cosine amplitude (I) : 0.4
  Linear term (m)      : 2.1
source
SinusoidalRegressions.MixedLinearSinusoidPMethod
MixedLinearSinusoidP(; f, DC, Q, I, m)

Construct a MixedLinearSinusoidP{T} specifying each parameter by name.

Example

julia> MixedLinearSinusoidP(f = 10, DC = 0, m = 2.1, Q= -1.2, I = 0.4)
Mixed Linear-Sinusoidal parameters MixedLinearSinusoidP{Float64}:
  Frequency (Hz)       : 10.0
  DC                   : 0.0
  Sine amplitude (Q)   : -1.2
  Cosine amplitude (I) : 0.4
  Linear term (m)      : 2.1
source
SinusoidalRegressions.MixedLinearSinusoidPMethod
(P::MixedLinearSinusoidP)(t)

Evaluate the mixed linear-sinusoidal function specified by the parameters P at the values given by t, which may be a scalar or a collection.

Example

julia> P = MixedLinearSinusoidP(f = 10, DC = 0, m = 2.1, Q= -1.2, I = 0.4)
julia> t = range(0, 0.7, length = 5)
julia> P(t)
5-element Vector{Float64}:
  0.4
  1.5674999999999997
  0.3349999999999989
 -0.09750000000000014
  1.870000000000002
source

Error measurement

Functions to easily compare a calculated fit to actual data, using root mean-square errors, or mean absolute errors.

SinusoidalRegressions.rmseFunction
rmse(fit::T, exact::T, x) where {T <: SinusoidalFunctionParameters}

Calculate the root mean-square error between fit and exact sampled at collection x.

See also: mae

source
rmse(fit::T, samples, x) where {T <: SinusoidalFunctionParameters}

Calculate the root mean-square error between fit and the samples taken at x.

See also: mae

source
SinusoidalRegressions.maeFunction
mae(fit::T, exact::T, x) where {T <: SinusoidalFunctionParameters}

Calculate the mean absolute error between fit and exact sampled at collection x.

See also: rmse

source

Plotting

This package provides recipes for Plots.jl. This makes it very easy to plot data and the calculated fit.

There are two recipes included: plotting one fit, and plotting data and up to two fits.

Plotting a fit

plot(X, fit::T, ; fitlabel = "") where {T <: SinusoidalFunctionParameters}

Plot the model with parameters given by fit at the points specified in collection X. The optional keyword argument fitlabel controls the label (legend) of the plot.

Example
using SinusoidalRegressions
X = range(0, 1, length = 100)
Y = 2 .+ 3cos.(2*pi*5*X) .- 0.2sin.(2*pi*5*X) .+ 0.1*randn(100)
fit = sinfit(Sin3Problem(X, Y, 5), IEEE1057())
plot(X, fit, fitlabel = "example")

Plotting data and one or two different fits

plot(X, Y, fit::T ; exact :: Union{T, Nothing} = nothing,
                    samples    = 100,
                    fitlabel   = "fit",
                    datalabel  = "data",
                    exactlabel = "exact") where {T <: SinusoidalFunctionParameters}

Plot the data Y and the model with parameters given by fit evaluated at the points specified in the collection X. The following keyword arguments are supported (with default values in parenthesis):

  • exact::T = nothing: add one more model to the plot. This allows plotting the exact function, the data and the fit in a single plot.
  • samples::Int = 100: fit and exact are evaluated for range(first(X), last(X), length = samples).
  • fitlabel::String = "fit": the label (legend) for the fit plot.
  • datalabel::String = "data": the label for the data plot.
  • exactlabel::String = "exact": the label for the exact plot.
Example
X = range(0, 1, length = 20)
exact = SinusoidP(5, 2, -0.2, 3)
Y = exact.(X) .+ 0.3*randn(20)
fit = sinfit(Sin4Problem(X, Y), IntegralEquations())
plot(X, Y, fit, exact = exact,
     datalabel = "measurements",
     fitlabel = "NLS",
     exactlabel = "true")

Abstract types