Добавление набора данных и аргументов столбца в функцию из именованного вопроса вектора -rlang - PullRequest
0 голосов
/ 19 февраля 2020

У меня есть ряд функций, которые составляют несколько диаграмм ggplot2.

У меня есть новый набор данных, на котором я хочу использовать эти функции для создания диаграмм.

Этот новый набор данных имеет свои уникальные имена для столбцов, которые нужны функциям.

Вполне вероятно, что в будущем я получу дополнительные новые наборы данных (с собственными именами столбцов).

Я думал о создании именованного вектора, в котором я указывал имена столбцов нового набора данных для использовать (а также имя самого нового объекта набора данных), и я мог бы дать значения этого именованного вектора каждой из функций.

Вот минимально воспроизводимый пример того, о чем я говорю.

Я знаю, что это будет связано с некоторой комбинацией !!, enquo, sym ... но я пробовал кучу, и похоже, что это меня побило.

Кроме того, я хотел бы сделать это без изменения функций (т. е. я все еще хотел бы использовать функции, также напрямую вводя имена объектов набора данных / столбца).

library(tidyverse)
library(rlang)

# make a dataset
dif_data_name <- tibble(dif_col_name = 1:50)


# a function that only utilises a dataset
test_function_only_data <- function(dataset) {

  dataset %>% 
    pull() %>% 
    sum()
}

# a function that utilises the dataset and a specific column

test_function_with_col <- function(dataset, only_column) {

  only_column <- enquo(only_column)

  dataset %>% 
    pull(!! only_column) %>%
    sum()
}



# If I specify the datset object, this works
test_function_only_data(dif_data_name)

# so does this (with the column name as well)
test_function_with_col(dif_data_name, dif_col_name)


# But I was hoping to use a named vector for the dataset and column arguments

function_arguments <- c("dataset" = "dif_data_name",
                         "only_column" = "dif_col_name")


# These (below) do not work. But I would like to figure out how to make them work.


# first function test

test_function_only_data(
  function_arguments[["dataset"]]
                        )


# second function test

test_function_with_col(function_arguments[["dataset"]],  
                       function_arguments[["only_column"]])



1 Ответ

1 голос
/ 19 февраля 2020

Обновление (за комментарии OP)
Вот полный пример использования данных, размещенных в гистограмме в этой цепочке комментариев.

set.seed(123)

new_table <- tibble(
  Date = seq.Date(as.Date("2016-01-01"), as.Date("2019-12-31"), 1)
  ) %>% 
  mutate(total_sales = rnorm(n()))

new_yearly_lines_fn <- function(sales_table, date_col, money_col) {
  date_col <- sym(date_col)
  money_col <- sym(money_col)
  sales_table <- eval(sym(sales_table))

  sales_table %>%
    group_by(year_month = floor_date({{date_col}}, "months"),
             year = year({{date_col}})) %>%
    summarise(total_sales = sum({{money_col}})) %>%
    ungroup() %>%
    ggplot() +
    aes(year_month, total_sales, col = factor(year)) +
    geom_line(stat = "identity", size = 2) +
    geom_point(stat = "identity", size = 2, col = "black")

}

function_arguments <- c("the_dataset" = "new_table",
                        "the_date_col" = "Date",
                        "the_money_col" = "total_sales")

new_yearly_lines_fn(function_arguments[["the_dataset"]], 
                    function_arguments[["the_date_col"]], 
                    function_arguments[["the_money_col"]])

enter image description here

FWIW, есть более простые способы передать нужную информацию в функцию с помощью аккуратной оценки. Но вот как вы это сделаете с вашим именованным вектором:

f <- function(named) {
  df_str <- named[["dataset"]]
  col_str <- named[["only_column"]]

  dataset <- eval(sym(df_str))

  dataset %>% 
    pull({{col_str}}) %>%
    sum()
}

f(function_arguments)
# 1275

Варианты, которые передаются в отдельные компоненты function_arguments, также будут работать:

f2 <- function(df_str, col_str) {
  col <- sym(col_str)
  dataset <- eval(sym(df_str))

  dataset %>% 
    pull({{col_str}}) %>%
    sum()
}

f2(function_arguments[["dataset"]], function_arguments[["only_column"]])
# 1275 

Обратите внимание, что !! нотация теперь заменяется нотацией {{ }}, начиная с rlang. 0.4.0 .

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...