@@ -107,7 +107,9 @@ extrapolate_quantiles.dist_quantiles <- function(x, p, ...) {
107
107
new_quantiles(q = c(qvals , q ), tau = c(tau , p ))
108
108
}
109
109
110
-
110
+ is_dist_quantiles <- function (x ) {
111
+ is_distribution(x ) && all(stats :: family(x ) == " quantiles" )
112
+ }
111
113
112
114
113
115
# ' Turn a a vector of quantile distributions into a list-col
@@ -124,8 +126,7 @@ extrapolate_quantiles.dist_quantiles <- function(x, p, ...) {
124
126
# ' edf_nested <- edf %>% dplyr::mutate(q = nested_quantiles(q))
125
127
# ' edf_nested %>% tidyr::unnest(q)
126
128
nested_quantiles <- function (x ) {
127
- stopifnot(is_distribution(x ),
128
- all(stats :: family(x ) == " quantiles" ))
129
+ stopifnot(is_dist_quantiles(x ))
129
130
distributional ::: dist_apply(x , .f = function (z ) {
130
131
tibble :: as_tibble(vec_data(z )) %> %
131
132
dplyr :: mutate(dplyr :: across(tidyselect :: everything(), as.double )) %> %
@@ -134,6 +135,68 @@ nested_quantiles <- function(x) {
134
135
}
135
136
136
137
138
+ # ' Pivot columns containing `dist_quantile` wider
139
+ # '
140
+ # ' Any selected columns that contain `dist_quantiles` will be "widened" with
141
+ # ' the "taus" (quantile) serving as names and the values in the data frame.
142
+ # ' When pivoting multiple columns, the original column name will be used as
143
+ # ' a prefix.
144
+ # '
145
+ # ' @param .data A data frame, or a data frame extension such as a tibble or
146
+ # ' epi_df.
147
+ # ' @param ... <[`tidy-select`][dplyr::dplyr_tidy_select]> One or more unquoted
148
+ # ' expressions separated by commas. Variable names can be used as if they
149
+ # ' were positions in the data frame, so expressions like `x:y` can
150
+ # ' be used to select a range of variables. Any selected columns should
151
+ # '
152
+ # ' @return An object of the same class as `.data`
153
+ # ' @export
154
+ # '
155
+ # ' @examples
156
+ # ' d1 <- c(dist_quantiles(1:3, 1:3 / 4), dist_quantiles(2:4, 1:3 / 4))
157
+ # ' d2 <- c(dist_quantiles(2:4, 2:4 / 5), dist_quantiles(3:5, 2:4 / 5))
158
+ # ' tib <- tibble::tibble(g = c("a", "b"), d1 = d1, d2 = d2)
159
+ # '
160
+ # ' pivot_quantiles(tib, c("d1", "d2"))
161
+ # ' pivot_quantiles(tib, tidyselect::starts_with("d"))
162
+ # ' pivot_quantiles(tib, d2)
163
+ pivot_quantiles <- function (.data , ... ) {
164
+ expr <- rlang :: expr(c(... ))
165
+ cols <- names(tidyselect :: eval_select(expr , .data ))
166
+ dqs <- map_lgl(cols , ~ is_dist_quantiles(.data [[.x ]]))
167
+ if (! all(dqs )) {
168
+ nms <- cols [! dqs ]
169
+ cli :: cli_abort(
170
+ " Variables(s) {.var {nms}} are not `dist_quantiles`. Cannot pivot them."
171
+ )
172
+ }
173
+ .data <- .data %> %
174
+ dplyr :: mutate(dplyr :: across(tidyselect :: all_of(cols ), nested_quantiles ))
175
+ checks <- map_lgl(cols , ~ diff(range(vctrs :: list_sizes(.data [[.x ]]))) == 0L )
176
+ if (! all(checks )) {
177
+ nms <- cols [! checks ]
178
+ cli :: cli_abort(
179
+ c(" Quantiles must be the same length and have the same set of taus." ,
180
+ i = " Check failed for variables(s) {.var {nms}}." ))
181
+ }
182
+ if (length(cols ) > 1L ) {
183
+ for (col in cols ) {
184
+ .data <- .data %> %
185
+ tidyr :: unnest(tidyselect :: all_of(col )) %> %
186
+ tidyr :: pivot_wider(
187
+ names_from = " tau" , values_from = " q" ,
188
+ names_prefix = paste0(col , " _" )
189
+ )
190
+ }
191
+ } else {
192
+ .data <- .data %> %
193
+ tidyr :: unnest(tidyselect :: all_of(cols )) %> %
194
+ tidyr :: pivot_wider(names_from = " tau" , values_from = " q" )
195
+ }
196
+ .data
197
+ }
198
+
199
+
137
200
138
201
139
202
# ' @export
0 commit comments