haven icon indicating copy to clipboard operation
haven copied to clipboard

Allow `labels` to be passed through to `labelled()` as unnamed vector of same length as `x`

Open kinto-b opened this issue 2 years ago • 0 comments

Hi,

Thanks for your excellent package. One thing I find myself needing to do often enough is to create a single labeled vector out of a vector of codes and a vector of labels. It's easy enough to do this, but it'd be nice if labelled() took care of it for me.

lang <- data.frame(
  id = 1:5,
  ascl = c(1201, 1201, 1301, 1201, 2101),
  ascl_txt = c("English", "English", "German", "English", "French") 
)

# Currently
lang$ascl <- haven::labelled(
    lang$ascl,
    tibble::deframe(unique(lang[ , c("ascl_txt", "ascl")]))
)

# Desired
lang$ascl <- haven::labelled(lang$ascl, labels=lang$ascl_txt)

I think it would just be a matter of adding something like this:

labelled <- function(x = double(), labels = NULL, label = NULL) {
  x <- vec_data(x)
  
  if (!is.null(labels) && is.null(names(labels)) && length(labels) == length(x)) {
     labels <- unique(data.frame(x=x, labels=labels))
     labels <- stats::setNames(labels$x, labels$labels)
   } else {
     labels <- vec_cast_named(labels, x, x_arg = "labels", to_arg = "x")
   }
  
  validate_labelled(new_labelled(x, labels = labels, label = label))
}

kinto-b avatar Dec 13 '23 05:12 kinto-b