2
$\begingroup$

I am interested in understanding how does the splines2 library from R place the knots when computing periodic splines. I understand the logic when splines are not periodic, for example, I know that if the knots are not specified, the number of knots is equal to

$$knots = df - degree $$

where 'df' refers to the degrees of freedom of the spline basis, and 'degree' refers to the degree of the polinomial, and they are placed on the quantiles. For example:

library(splines2)
library(splines)

df = 8
degree = 3
x = seq(0, 1, length.out=15)

knots = seq(0, 1, length.out = df - degree + 2)
knots = knots[2:(length(knots)-1)]
# df - degree = length(knots)

spline_basis1 =  splines2::mSpline(x, degree=degree, df=df)
spline_basis2 =  splines2::mSpline(x, degree=degree, knots=knots)

spline_basis1 and spline_basis2 will return the same result. But if I consider periodic splines, this is no longer true:

# Periodic splines
spline_basis1 =  splines2::mSpline(x, degree=degree, df=df, periodic=T)
spline_basis2 =  splines2::mSpline(x, degree=degree, knots=knots, periodic=T) 

My guess is that when computing periodic splines, the number of parameters to be estimated (the degrees of freedom) is different, but I would like to understand how are knots placed by default when splines are periodic.

$\endgroup$
3
  • 1
    $\begingroup$ Doesn't the documentation answer that? $\endgroup$
    – whuber
    Jul 12, 2021 at 12:45
  • 1
    $\begingroup$ The documentation (cran.r-project.org/web/packages/splines2/splines2.pdf) explains the number of knots chosen but not where they are placed. I took them based on the quantiles but obtain a different solution than the default one. $\endgroup$ Jul 12, 2021 at 14:26
  • $\begingroup$ Thanks -- I see the documentation only states "... at suitable quantiles... ." The best way to obtain an answer is to inspect the source code. $\endgroup$
    – whuber
    Jul 12, 2021 at 14:30

1 Answer 1

2
$\begingroup$

Your guess is correct. The relationship between the df and knots is df = length(knots) + as.integer(intercept) for periodic splines that implemented in splines2::mSpline(). For B-splines implemented in splines::bs() or splines2::bSpline(), the relationship is df = length(knots) + degree + as.integer(intercept).

See the following code for comparison:

df <- 8
degree <- 3
x <- seq(0, 1, length.out = 15)
x2 <- x %% 1       # get x in the cyclic period [0, 1)
intercept <- FALSE # default, the first basis function excluded

## set internal knots
knots <- quantile(x2, probs = seq(0, 1, length.out = df + 1 + (! intercept)))
(knots <- knots[- c(1, length(knots))])
#>  11.11111%  22.22222%  33.33333%  44.44444%  55.55556%  66.66667%  77.77778% 
#> 0.03968254 0.15079365 0.26190476 0.37301587 0.48412698 0.59523810 0.70634921 
#>  88.88889% 
#> 0.81746032

spline_basis1 =  splines2::mSpline(x, degree = degree, df = df,
                                   periodic = TRUE, intercept = intercept)
spline_basis2 =  splines2::mSpline(x, degree = degree, knots = knots,
                                   periodic = TRUE, intercept = intercept)

knots(spline_basis1)
#> [1] 0.03968254 0.15079365 0.26190476 0.37301587 0.48412698 0.59523810 0.70634921
#> [8] 0.81746032

all.equal(spline_basis1, spline_basis2)
#> [1] TRUE
$\endgroup$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.