parsnip extract_parameter_dials() in R: Get Tuning Ranges

The parsnip extract_parameter_dials() function in R returns a single dials parameter object, such as trees() or mtry(), pulled from one tunable argument of a model specification, recipe, or workflow.

⚡ Quick Answer
extract_parameter_dials(spec, "trees")        # one param from a model spec
extract_parameter_dials(rec, "num_comp")      # one param from a recipe
extract_parameter_dials(wf, "penalty")        # one param from a workflow
extract_parameter_dials(pset, "min_n")        # one param from a parameter set
finalize(extract_parameter_dials(spec, "mtry"), df)  # resolve a [1, ?] range
extract_parameter_set_dials(spec)             # every tunable param at once

Need explanation? Read on for examples and pitfalls.

📊 Is extract_parameter_dials() the right tool?
STARTinspect one tuning parameter's rangeextract_parameter_dials(spec, "trees")get every tunable parameter at onceextract_parameter_set_dials(spec)mark a model argument for tuningboost_tree(trees = tune())resolve a data-dependent rangefinalize(param, train_data)build the tuning grid from paramsgrid_regular(param_set, levels = 5)pull the fitted engine model objectextract_fit_engine(model_fit)

What extract_parameter_dials() does

extract_parameter_dials() returns the dials object that controls one tunable argument. When you tag a model argument with tune(), parsnip records that the argument is unknown and must be searched. extract_parameter_dials() looks up which dials parameter governs that argument and hands it back, ready to inspect or modify.

A dials parameter object carries the search space for tuning: a numeric range, a scale (linear or log), and a human-readable label. For trees that is the integer range [1, 2000]. For penalty it is a log-scaled range. You reach for this object whenever you want to see, or change, the values a tuning grid will draw from.

The function is an S3 generic from the hardhat package. The tune package supplies the methods for model_spec, recipe, workflow, and parameters objects, so the same call works at every layer of a tidymodels pipeline. Because this page is parsnip-focused, the examples below pass a parsnip model_spec.

Key Insight
A model spec only knows an argument is tunable; the dials object knows what to tune it over. extract_parameter_dials() is the bridge between the two: it turns a bare tune() tag into a concrete, editable search range.

extract_parameter_dials() syntax and arguments

The signature has two arguments because the function locates one parameter and returns it unchanged. It is an S3 generic, so the method that runs depends on the class of x.

Run live
Run live, no install needed. Every R block on this page runs in your browser. Click Run, edit the code, re-run instantly. No setup.
Rextract_parameter_dials generic signature
extract_parameter_dials(x, parameter)

  
Argument Description
x A tunable object: a parsnip model_spec, a recipe, a workflow, a parameters set, or tune_results.
parameter A single string: the id of the parameter to extract. This is the argument name, or the custom id you passed to tune().

The return value is one dials parameter object whose class is quant_param (numeric) or qual_param (categorical). If x has no tunable parameter with that id, the function returns a logical NA rather than raising an error.

The argument must already be tagged with tune(). A fully specified spec has nothing to extract, because extract_parameter_dials() reads the tuning tags, not the engine defaults. See the official hardhat extract reference for the full method list.

Extract tuning parameters: four examples

Each example below uses a built-in dataset and a different kind of parameter. Start by tagging two arguments of a boosted tree for tuning, then pull one of them out.

RExtract one parameter from a model spec
library(parsnip) library(tune) library(dials) bt_spec <- boost_tree(trees = tune(), tree_depth = tune()) |> set_engine("xgboost") |> set_mode("regression") extract_parameter_dials(bt_spec, "trees") #> Trees (quantitative) #> Range: [1, 2000]

  

Some parameters have a range that depends on the data. mtry cannot exceed the number of predictors, so its upper bound prints as ? until you resolve it with finalize().

RResolve a data-dependent range
rf_spec <- rand_forest(mtry = tune(), min_n = tune()) |> set_engine("ranger") |> set_mode("regression") mtry_param <- extract_parameter_dials(rf_spec, "mtry") mtry_param #> Randomly Selected Predictors (quantitative) #> Range: [1, ?] finalize(mtry_param, mtcars[, -1]) #> Randomly Selected Predictors (quantitative) #> Range: [1, 10]

  

Parameters can also live on a transformed scale. A regularization penalty is searched on a log-10 scale, which the returned object reports directly.

RExtract a log-scaled parameter
lasso_spec <- linear_reg(penalty = tune()) |> set_engine("glmnet") extract_parameter_dials(lasso_spec, "penalty") #> Amount of Regularization (quantitative) #> Transformer: log-10 [1e-100, Inf] #> Range (transformed scale): [-10, 0]

  

Because the result is a real dials object, you can edit its range and feed it straight into a grid builder.

RModify a range and build a grid
trees_param <- extract_parameter_dials(bt_spec, "trees") trees_param <- range_set(trees_param, c(100, 500)) grid_regular(trees_param, levels = 3) #> # A tibble: 3 x 1 #> trees #> <int> #> 1 100 #> 2 300 #> 3 500

  
Tip
Extract once, then reuse the object. Assign the result to a variable so you can inspect it, narrow its range with range_set(), and pass the same object into grid_regular() or grid_latin_hypercube() without re-extracting.

extract_parameter_dials() vs extract_parameter_set_dials()

Use extract_parameter_dials() for one parameter and extract_parameter_set_dials() for all of them. The plural function returns the whole tuning blueprint; the singular function drills into one row of it.

RCompare with extract_parameter_set_dials
extract_parameter_set_dials(bt_spec) #> Collection of 2 parameters for tuning #> #> identifier type object #> trees trees nparam[+] #> tree_depth tree_depth nparam[+]

  

The set is what you finalize and pass to tune_grid(). The single object is what you inspect or hand-tune when one parameter needs a custom range.

Aspect extract_parameter_dials() extract_parameter_set_dials()
Returns One dials parameter object A parameters set (all tunable params)
Needs a parameter id Yes No
Use it to Inspect or edit one range Build or finalize the full grid
Result class quant_param or qual_param parameters
Note
The methods ship with the tune package, not parsnip. extract_parameter_dials() is a hardhat generic, and tune registers the model_spec method. Load library(tune) (or library(tidymodels)) so the parsnip method is available.

Common pitfalls

Most failures trace back to a parameter that was never tagged for tuning. These three mistakes account for nearly every confusing result.

Extracting an argument that holds a fixed value returns NA, because there is no tuning tag to read.

RPitfall: argument is not tunable
fixed_spec <- boost_tree(trees = 500) |> set_engine("xgboost") |> set_mode("regression") extract_parameter_dials(fixed_spec, "trees") #> [1] NA

  

When you give tune() a custom id, you must extract by that id, not the argument name.

RPitfall: wrong parameter id
bt2 <- boost_tree(trees = tune("n_trees")) |> set_engine("xgboost") |> set_mode("regression") extract_parameter_dials(bt2, "trees") # argument name: returns NA #> [1] NA extract_parameter_dials(bt2, "n_trees") # the tune() id: works #> Trees (quantitative) #> Range: [1, 2000]

  

Building a grid from a parameter with an unresolved range fails. Call finalize() first.

RPitfall: grid built before finalize
grid_regular(extract_parameter_dials(rf_spec, "mtry"), levels = 3) #> Error: These arguments contain unknowns: `mtry`. See the dials::finalize() function.

  

Try it yourself

Try it: Build a rand_forest() spec with min_n = tune(), then extract the min_n dials parameter and save it to ex_param.

RYour turn: extract min_n
# Try it: extract the min_n parameter ex_spec <- rand_forest(min_n = tune()) |> set_engine("ranger") |> set_mode("regression") ex_param <- # your code here ex_param #> Expected: a "Minimal Node Size" dials parameter

  
Click to reveal solution
RSolution
ex_param <- extract_parameter_dials(ex_spec, "min_n") ex_param #> Minimal Node Size (quantitative) #> Range: [2, 40]

  

Explanation: extract_parameter_dials() reads the tune() tag on min_n and returns the matching dials object, min_n(), with its default search range of 2 to 40.

These functions sit next to extract_parameter_dials() in a tidymodels tuning workflow. Reach for them when you need a whole set, a finalized range, or the fitted model.

  • extract_parameter_set_dials(): returns every tunable parameter as one parameters set.
  • finalize(): resolves data-dependent ranges such as mtry to concrete bounds.
  • grid_regular(): turns parameter objects into a tuning grid.
  • extract_fit_engine(): pulls the raw engine model from a fitted object, not a tuning range.
  • set_engine() and boost_tree(): build the spec you extract parameters from.

FAQ

What does extract_parameter_dials() return?

It returns one dials parameter object describing the search space for a single tunable argument. The object holds a range, a label, and a scale, and prints as something like Trees (quantitative) Range: [1, 2000]. The class is quant_param for numeric parameters and qual_param for categorical ones. You can inspect it, edit its range with range_set(), or pass it to a grid function.

Why does extract_parameter_dials() return NA?

A logical NA means the object has no tunable parameter with the id you asked for. The usual cause is an argument that holds a fixed value instead of a tune() tag, so there is nothing to extract. The second cause is an id mismatch: if you wrote tune("my_id"), you must extract by "my_id", not the argument name. Check the spec with extract_parameter_set_dials() to see the valid ids.

What is the difference between extract_parameter_dials() and extract_parameter_set_dials()?

extract_parameter_dials() returns one parameter object and needs a parameter id. extract_parameter_set_dials() returns the whole parameters set and takes no id. Use the set to build or finalize a complete tuning grid, and use the single object when one parameter needs a hand-tuned range before it joins the grid.

Do I need the tune package to use extract_parameter_dials()?

Yes, for parsnip objects. The generic is defined in hardhat, but the method for a model_spec is registered by tune. Load library(tune) or library(tidymodels) before calling it on a parsnip spec, otherwise R cannot find the method and falls back to a default that returns NA.