Динамически определить, существует ли столбец данных, и изменить его, если он есть - PullRequest
0 голосов
/ 26 октября 2018

У меня есть код, который извлекает и обрабатывает данные из базы данных на основе имени клиента.Некоторые клиенты могут иметь данные, которые не содержат определенного имени столбца, например, last_name или first_name.Для клиентов, которые не используют last_name или first_name, мне все равно.Для клиентов, которые действительно используют любое из этих полей, мне нужно mutate() эти столбцы с toupper(), чтобы я мог присоединиться к этим стандартизированным полям позже в процессе ETL.

Rightтеперь я использую серию операторов if() и некоторые вспомогательные функции, чтобы посмотреть имена фреймов данных, а затем изменить их, если они существуют. Я использую if() операторы, потому что ifelse() в основном векторизован и плохо обрабатывает кадры данных.

library(dplyr)
set.seed(256)

b <- data.frame(id = sample(1:100, 5, FALSE), 
                col_name = sample(1000:9999, 5, FALSE), 
                another_col = sample(1000:9999, 5, FALSE))

d <- data.frame(id = sample(1:100, 5, FALSE), 
                col_name = sample(1000:9999, 5, FALSE), 
                last_name = sample(letters, 5, FALSE))

mutate_first_last <- function(df){

  mutate_first_name <- function(df){
    df %>%
      mutate(first_name = first_name %>% toupper())
  }

  mutate_last_name <- function(df){
    df %>%
      mutate(last_name = last_name %>% toupper())
  }


  n <- c("first_name", "last_name") %in% names(df)

  if (n[1] & n[2]) return(df %>% mutate_first_name() %>% mutate_last_name())
  if (n[1] & !n[2]) return(df %>% mutate_first_name())
  if (!n[1] & n[2]) return(df %>% mutate_last_name())
  if (!n[1] & !n[2]) return(df)

}

Я получаю то, что ожидаю получить таким образом

> b %>% mutate_first_last()
  id col_name another_col
1 48     8318        6207
2 39     7155        7170
3 16     4486        4321
4 55     2521        8024
5 15     1412        4875
> d %>% mutate_first_last()
  id col_name last_name
1 64     7438         A
2 43     4551         Q
3 48     7401         K
4 78     3682         Z
5 87     2554         J

но разве это лучший способ справиться с такой задачей?Чтобы динамически проверить, существует ли имя столбца в кадре данных, измените его, если оно есть?Кажется странным иметь в этой функции несколько операторов if(). Есть ли более удобный способ обработки этих данных?

1 Ответ

0 голосов
/ 26 октября 2018

Вы можете использовать mutate_at с one_of, оба с dplyr.Это приведет к изменению столбца, только если он совпадает с одним из c("first_name", "last_name").Если совпадения нет, оно выдаст простое предупреждение, но вы можете проигнорировать или подавить его.

library(dplyr)

d %>%
  mutate_at(vars(one_of(c("first_name", "last_name")), toupper)

  id col_name last_name
1 19     7461         V
2 52     9651         H
3 56     1901         P
4 13     7866         Z
5 25     9527         U

# example with no match
b %>%
  mutate_at(vars(one_of(c("first_name", "last_name"))), toupper)

  id col_name another_col
1 34     9315        8686
2 26     5598        4124
3 17     3318        2182
4 32     1418        4369
5 49     4759        6680
Warning message:
Unknown variables: `first_name`, `last_name`

Вот несколько других ?select_helpers в dplyr -

Эти функции позволяют вам выбирать переменные на основе их имен.

start_with (): начинается с префикса

заканчивается_with (): заканчивается префиксом

Содержит ():содержит буквенную строку

match (): соответствует регулярному выражению

num_range (): числовой диапазон, например x01, x02, x03.

one_of (): переменные всимвольный вектор.

everything (): все переменные.

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