tidyverts / tidyverts/fabletools
parameterized model formulas stop working when future `plan` is declared
Open
Nobody has claimed this yet.
parellel
- Dominant language
- R
- Stars
- 98
- Forks
- 37
- PR merge metrics
- No merged PRs in 30d
Description
See reprex below. In my real codebase I'm using furrr's future_map for other purposes (reading a series of files off disk).
library(fable)
#> Loading required package: fabletools
library(tsibble)
#>
#> Attaching package: 'tsibble'
#> The following objects are masked from 'package:base':
#>
#> intersect, setdiff, union
library(feasts)
library(glue)
library(future)
# Define some random data
set.seed(7)
data <- tsibble(idx=1:1000, value=rnorm(1000), index=idx)
# Make a STL decomposition
model(data, stl = STL(value ~ trend() + season(10))) %>% components()
#> # A dable: 1,000 x 7 [1]
#> # Key: .model [1]
#> # : value = trend + season_10 + remainder
#> .model idx value trend season_10 remainder season_adjust
#> <chr> <int> <dbl> <dbl> <dbl> <dbl> <dbl>
#> 1 stl 1 2.29 -0.477 0.419 2.35 1.87
#> 2 stl 2 -1.20 -0.349 0.141 -0.988 -1.34
#> 3 stl 3 -0.694 -0.222 0.279 -0.751 -0.973
#> 4 stl 4 -0.412 -0.0899 -0.443 0.121 0.0311
#> 5 stl 5 -0.971 0.0418 0.0143 -1.03 -0.985
#> 6 stl 6 -0.947 0.170 -0.350 -0.767 -0.597
#> 7 stl 7 0.748 0.298 0.0246 0.426 0.724
#> 8 stl 8 -0.117 0.431 -0.214 -0.334 0.0972
#> 9 stl 9 0.153 0.564 -0.300 -0.112 0.453
#> 10 stl 10 2.19 0.706 0.459 1.02 1.73
#> # ℹ 990 more rows
# We can use a variable in the formula
seasonal_period <- 10
model(data, stl = STL(value ~ trend() + season(seasonal_period))) %>% components()
#> # A dable: 1,000 x 7 [1]
#> # Key: .model [1]
#> # : value = trend + season_10 + remainder
#> .model idx value trend season_10 remainder season_adjust
#> <chr> <int> <dbl> <dbl> <dbl> <dbl> <dbl>
#> 1 stl 1 2.29 -0.477 0.419 2.35 1.87
#> 2 stl 2 -1.20 -0.349 0.141 -0.988 -1.34
#> 3 stl 3 -0.694 -0.222 0.279 -0.751 -0.973
#> 4 stl 4 -0.412 -0.0899 -0.443 0.121 0.0311
#> 5 stl 5 -0.971 0.0418 0.0143 -1.03 -0.985
#> 6 stl 6 -0.947 0.170 -0.350 -0.767 -0.597
#> 7 stl 7 0.748 0.298 0.0246 0.426 0.724
#> 8 stl 8 -0.117 0.431 -0.214 -0.334 0.0972
#> 9 stl 9 0.153 0.564 -0.300 -0.112 0.453
#> 10 stl 10 2.19 0.706 0.459 1.02 1.73
#> # ℹ 990 more rows
# Or we can make a formula ourselves
stl_formula <- as.formula(glue("value ~ trend() + season({seasonal_period})"))
stl_formula
#> value ~ trend() + season(10)
# ... and hand it to STL
model(data, stl = STL(stl_formula)) %>% components()
#> # A dable: 1,000 x 7 [1]
#> # Key: .model [1]
#> # : value = trend + season_10 + remainder
#> .model idx value trend season_10 remainder season_adjust
#> <chr> <int> <dbl> <dbl> <dbl> <dbl> <dbl>
#> 1 stl 1 2.29 -0.477 0.419 2.35 1.87
#> 2 stl 2 -1.20 -0.349 0.141 -0.988 -1.34
#> 3 stl 3 -0.694 -0.222 0.279 -0.751 -0.973
#> 4 stl 4 -0.412 -0.0899 -0.443 0.121 0.0311
#> 5 stl 5 -0.971 0.0418 0.0143 -1.03 -0.985
#> 6 stl 6 -0.947 0.170 -0.350 -0.767 -0.597
#> 7 stl 7 0.748 0.298 0.0246 0.426 0.724
#> 8 stl 8 -0.117 0.431 -0.214 -0.334 0.0972
#> 9 stl 9 0.153 0.564 -0.300 -0.112 0.453
#> 10 stl 10 2.19 0.706 0.459 1.02 1.73
#> # ℹ 990 more rows
# The same thing works with ARIMA
fixed_p <- 1
model(data, arima = ARIMA(value ~ pdq(p=fixed_p))) %>% tidy()
#> # A tibble: 1 × 6
#> .model term estimate std.error statistic p.value
#> <chr> <chr> <dbl> <dbl> <dbl> <dbl>
#> 1 arima ar1 0.0194 0.0317 0.612 0.541
arima_formula <- as.formula(glue("value ~ pdq(p={fixed_p})"))
model(data, arima = ARIMA(arima_formula)) %>% tidy()
#> # A tibble: 1 × 6
#> .model term estimate std.error statistic p.value
#> <chr> <chr> <dbl> <dbl> <dbl> <dbl>
#> 1 arima ar1 0.0194 0.0317 0.612 0.541
# But the moment we declare a plan ...
plan(multisession, workers=8)
# ... "normal" formula with no parameters still works, ...
model(data, stl = STL(value ~ trend() + season(10))) %>% components()
#> # A dable: 1,000 x 7 [1]
#> # Key: .model [1]
#> # : value = trend + season_10 + remainder
#> .model idx value trend season_10 remainder season_adjust
#> <chr> <int> <dbl> <dbl> <dbl> <dbl> <dbl>
#> 1 stl 1 2.29 -0.477 0.419 2.35 1.87
#> 2 stl 2 -1.20 -0.349 0.141 -0.988 -1.34
#> 3 stl 3 -0.694 -0.222 0.279 -0.751 -0.973
#> 4 stl 4 -0.412 -0.0899 -0.443 0.121 0.0311
#> 5 stl 5 -0.971 0.0418 0.0143 -1.03 -0.985
#> 6 stl 6 -0.947 0.170 -0.350 -0.767 -0.597
#> 7 stl 7 0.748 0.298 0.0246 0.426 0.724
#> 8 stl 8 -0.117 0.431 -0.214 -0.334 0.0972
#> 9 stl 9 0.153 0.564 -0.300 -0.112 0.453
#> 10 stl 10 2.19 0.706 0.459 1.02 1.73
#> # ℹ 990 more rows
# ... but the above strategies for parameterizing the formula stop working
model(data, stl = STL(stl_formula)) %>% components()
#> Error: object 'stl_formula' not found
model(data, stl = STL(value ~ trend() + season(seasonal_period))) %>% components()
#> Warning: 1 error encountered for stl
#> [1] object 'seasonal_period' not found
#> Error in `transmute()`:
#> ℹ In argument: `cmp = map(.fit, components)`.
#> Caused by error in `UseMethod()`:
#> ! no applicable method for 'components' applied to an object of class "null_mdl"
#> Backtrace:
#> ▆
#> 1. ├─... %>% components()
#> 2. ├─generics::components(.)
#> 3. ├─fabletools:::components.mdl_df(.)
#> 4. │ ├─dplyr::transmute(...)
#> 5. │ └─dplyr:::transmute.data.frame(...)
#> 6. │ └─dplyr:::mutate_cols(.data, dots, by)
#> 7. │ ├─base::withCallingHandlers(...)
#> 8. │ └─dplyr:::mutate_col(dots[[i]], data, mask, new_columns)
#> 9. │ └─mask$eval_all_mutate(quo)
#> 10. │ └─dplyr (local) eval()
#> 11. ├─fabletools:::map(.fit, components)
#> 12. │ └─base::lapply(.x, .f, ...)
#> 13. │ ├─generics (local) FUN(X[[i]], ...)
#> 14. │ └─fabletools:::components.mdl_ts(X[[i]], ...)
#> 15. │ └─generics::components(object$fit, ...)
#> 16. └─base::.handleSimpleError(...)
#> 17. └─dplyr (local) h(simpleError(msg, call))
#> 18. └─rlang::abort(message, class = error_class, parent = parent, call = error_call)
model(data, arima = ARIMA(arima_formula)) %>% tidy()
#> Error: object 'arima_formula' not found
Contributor guide
No contributing guide indexed for this repository
First steps
- Read the whole issue, then the project's contributing guide.
- Comment on the issue to say you are picking it up — it saves two people doing the same work.
- Fork the repository and make your change on a branch.
- Open a pull request that references the issue number.
Research direction
Reproduce the failure using model() with STL() and ARIMA() after plan(multisession, workers=8), comparing literal formulas with formulas containing parameters. Trace how these model entry points capture formula environments under the future plan; done means both parameterized forms work without missing-object errors and retain their existing results.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- r
- Domain
- data
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Stale
- Clarity
- Mostly clear
- Newbie friendliness
- 38/100