Условный мутат на основе результатов слияния в dplyr

Я учил себя R с нуля, в основном предпринимая что-то, затем читая подобные посты и методом проб и ошибок, основанных на этом. Иногда я ударяюсь о стену и протягиваю руку.

Я врезался в стену. У меня установлен dplyr 0.7. У меня есть столбец со столбцом - назовите его contract_key - я добавил, применив mutate (coalesce ()) к трем другим столбцам в таблице. Вот пример данных:

product <- c("655393265191","655393265191","168145850127","168145850127","350468621217","350468621217","977939797847","NA","928893912852")
supplier <- c("person5","person3","person10","person5","person11","person5","person11","person14","person5")
vendor <- c("org2","org3","org3","org2","org1","org2","org1","org5","org2")
quantity <- c(7,5,6,1,2,1,18,2,2)
gross <- c(0.0419,0.0193,0.0439,0.0069,0.0027,0.0055,0.0233,NA,0.0004)

df <- data_frame(product,supplier,vendor,quantity,gross)

Вот как я создал contract_key:

df <- df %>% 
  mutate(contract_key = coalesce(product,supplier,vendor))

Теперь я хочу добавить еще один столбец, который классифицирует содержимое contract_key в зависимости от того, какой из трех столбцов предоставил содержимое (через coalesce ()). Так, например, если contract_key = "person5", новый столбец, contract_level, будет "поставщиком". И contract_key = "org2" будет отображаться на contract_level = "vendor" и т. Д.

По сути, я буду использовать contract_level как переменную соединения с другим тибблом.

Я в тупике. Я пробовал if_else и вижу, что не стоит пытаться case_when (потому что он внутри mutate ()). Я также безуспешно пытался вложить if_else.

Вероятно, это базовый синтаксис R, которого я просто не знаю. Что-то связанное с точечной нотацией и грамматикой. Если кто-то предоставит ответ, я буду прослеживать, пока не выясню, что вы сделали. (И я выучу новый урок в R!)

Спасибо!


person Steve    schedule 12.09.2017    source источник
comment
В образце данных для product измените "NA" на NA, чтобы оно было правильно закодировано как отсутствующее значение, а не как строка "NA".   -  person eipi10    schedule 12.09.2017
comment
Отвечает ли это на ваш вопрос? Можно ли использовать пакет dplyr для условного изменения?   -  person divibisan    schedule 16.06.2020


Ответы (1)


Как насчет этого:

df %>% mutate(contract_key = coalesce(product,supplier,vendor),
              contract_level = case_when(contract_key %in% product ~ "product",
                                         contract_key %in% supplier ~ "supplier",
                                         contract_key %in% vendor ~ "vendor",
                                         TRUE ~ "none"))
       product supplier vendor quantity  gross contract_key contract_level
1 655393265191  person5   org2        7 0.0419 655393265191        product
2 655393265191  person3   org3        5 0.0193 655393265191        product
3 168145850127 person10   org3        6 0.0439 168145850127        product
4 168145850127  person5   org2        1 0.0069 168145850127        product
5 350468621217 person11   org1        2 0.0027 350468621217        product
6 350468621217  person5   org2        1 0.0055 350468621217        product
7 977939797847 person11   org1       18 0.0233 977939797847        product
8         <NA> person14   org5        2     NA     person14       supplier
9 928893912852  person5   org2        2 0.0004 928893912852        product

Другие варианты, требующие меньше кода:

df %>% mutate(contract_key = coalesce(product,supplier,vendor),
              contract_level = if_else(!is.na(product), 'product', 
                                       if_else(!is.na(supplier), 'supplier', 'vendor')))

df %>% mutate(contract_key = coalesce(product,supplier,vendor),
              contract_level = apply(., 1, function(x) names(.)[min(which(!is.na(x)))]))
person eipi10    schedule 12.09.2017
comment
Спасибо! Думаю, действительно так просто. Для будущих читателей: я даже не пробовал case_when, потому что в документации dplyr прямо сказано, что case_when не работает внутри mutate (). Но так оно и было, по крайней мере, в этом случае! Спасибо @ eipi10 - person Steve; 12.09.2017
comment
Просто любопытно, где в документации говорится, что case_when не работает внутри mutate. В справке для case_when есть пример, который начинается с case_when is particularly useful inside mutate.... - person eipi10; 12.09.2017
comment
Ах, я думаю, что это было проблемой в более ранних версиях dplyr, но не больше. - person eipi10; 12.09.2017
comment
blog.rstudio.com/2016/06/27/dplyr -0-5-0, примерно на полпути вниз по странице в разделе case_when (): case_when () все еще является своего рода экспериментом и в настоящее время не работает внутри mutate (). Это будет исправлено в будущей версии. Это документ для 0.7, который, я думаю, является текущим основным выпуском? - person Steve; 12.09.2017
comment
в любом случае, теперь мне нужно выяснить, как выполнить условное соединение на основе contract_level. обратно в соляные шахты !! - person Steve; 12.09.2017