It is straightforward to turn existing functions into functions that can deal with any ts-boxable object.
The ts_
function is a constructor function for tsbox time series functions. It
can be used to wrap any function that works with time series. The default is set
to R base "ts"
class, so wrapping functions for "ts"
time series (or vectors
or matrices) is as simple as:
ts_rowsums <- ts_(rowSums)
ts_rowsums(ts_c(mdeaths, fdeaths))
Note that ts_
returns a function, which can be with or without a name. Let' have a closer look at how ts_rowsums
looks like:
ts_rowsums
#> function (x, ...)
#> {
#> stopifnot(ts_boxable(x))
#> z <- rowSums(ts_ts(x), ...)
#> copy_class(z, x)
#> }
This is how most ts-functions work. They use a specific converter function
(here: ts_ts
) to convert a ts-boxable object to the desired class. They then
perform the main operation on the object (here: rowSums
). Finally they convert
the result back to the original class, using copy_class
.
Here is a slightly more complex example, which uses a post processing function:
ts_prcomp <- ts_(function(x) predict(prcomp(x, scale = TRUE)))
ts_prcomp(ts_c(mdeaths, fdeaths))
It is easy to make functions from external packages ts-boxable, by wrapping them
into ts_
.
ts_dygraphs <- ts_(dygraphs::dygraph, class = "xts")
ts_forecast <- ts_(function(x) forecast::forecast(x)$mean, vectorize = TRUE)
ts_seas <- ts_(function(x) seasonal::final(seasonal::seas(x)), vectorize = TRUE)
ts_dygraphs(ts_c(mdeaths, EuStockMarkets))
ts_forecast(ts_c(mdeaths, fdeaths))
ts_seas(ts_c(mdeaths, fdeaths))
If you are explicit about the namespace (e.g., dygraphs::dygraph
),
ts_
recognized the package in use and delivers a meaningful message if the
package is not installed.
Note that the ts_
function deals with the conversion stuff, 'vectorizes' the
function so that it can be used with multiple time series.
Let' have another look at ts_forecast
:
ts_forecast
#> function (x, ...)
#> {
#> load_suggested("forecast")
#> ff <- function(x, ...) {
#> stopifnot(ts_boxable(x))
#> z <- (function(x) forecast::forecast(x)$mean)(ts_ts(x),
#> ...)
#> copy_class(z, x)
#> }
#> ts_apply(x, ff, ...)
#> }
There three main differences here: First, the function requires the forecast
package. If it is not installed, load_suggested
will ask the user to do so.
Second, the function in use is an anonymous function, function(x)
forecast::forecast(x)$mean
, that also extracts the mean
from the result.
Third, the function is 'vectorized', using ts_apply
. This causes the process
to be repeated for each time series in the object.