Условно создать новый столбец на основе значений строк - PullRequest
1 голос
/ 23 марта 2020

заранее спасибо за любую помощь.

У меня есть фрейм данных:

df <- structure(list(ID = c("0001", "0002", "0003", "0004"), May_1 = c(1, 
2, 1, 3), May_5 = c(NA, 1, 2, 1), May_10 = c(NA, 3, 3, NA), May_16 = c(2, 
NA, NA, NA), May_20 = c(3, NA, NA, 2)), row.names = c(NA, -4L
), class = c("tbl_df", "tbl", "data.frame"))

Я хотел бы создать новые столбцы с именами «Первое предпочтение», «Второе предпочтение» и «Третье предпочтение» на основе значений строк для каждого ответа ,

Если значение строки == 1, я хотел бы добавить столбец с именем «First Preference», содержащий имя столбца, где значение строки == 1.

Мои фактические данные содержат около 40 дат, которые будут меняться неделя за неделей, поэтому обобщаемое решение наиболее ценно.

Вот идеальный вариант:

df_ideal <- structure(list(ID = c("0001", "0002", "0003", "0004"), May_1 = c(1, 
2, 1, 3), May_5 = c(NA, 1, 2, 1), May_10 = c(NA, 3, 3, NA), May_16 = c(2, 
NA, NA, NA), May_20 = c(3, NA, NA, 2), First_Preference = c("May_1", 
"May_5", "May_1", "May_5"), Second_Preference = c("May_16", "May_1", 
"May_5", "May_20"), Third_Preference = c("May_20", "May_10", 
"May_10", "May_1")), row.names = c(NA, -4L), class = c("tbl_df", 
"tbl", "data.frame"))

A tidyverse было бы предпочтительным решением, но я, безусловно, открыт для всего.

Спасибо!

Ответы [ 2 ]

1 голос
/ 23 марта 2020

В базе R мы можем использовать apply по строкам order значения, удаляющие значения NA и получать соответствующие имена столбцов.

cols <- paste(c('First', 'Second', 'Third'), "Preference", sep = "_")
df[cols] <- t(apply(df[-1], 1, function(x) names(df)[-1][order(x, na.last=  NA)]))
df

# A tibble: 4 x 9
#  ID    May_1 May_5 May_10 May_16 May_20 First_Preference Second_Preference Third_Preference
#  <chr> <dbl> <dbl>  <dbl>  <dbl>  <dbl> <chr>            <chr>             <chr>           
#1 0001      1    NA     NA      2      3 May_1            May_16            May_20          
#2 0002      2     1      3     NA     NA May_5            May_1             May_10          
#3 0003      1     2      3     NA     NA May_1            May_5             May_10          
#4 0004      3     1     NA     NA      2 May_5            May_20            May_1          
1 голос
/ 23 марта 2020

Мы можем изменить его в «длинный» формат, удалив элементы NA с values_drop_na, затем использовать столбец «значение» в качестве индекса для изменения меток и затем преобразовать обратно в «широкий» формат с * 1003. *

library(dplyr)
library(tidyr)
df %>%
  pivot_longer(cols = -ID, values_drop_na = TRUE) %>%
  group_by(ID) %>% 
  mutate(value = c("First_Preference", "Second_Preference", 
        "Third_Preference")[value]) %>%
  ungroup %>%
  pivot_wider(names_from = value, values_from = name) %>%     
  left_join(df, .)
# A tibble: 4 x 9
#  ID    May_1 May_5 May_10 May_16 May_20 First_Preference Second_Preference Third_Preference
#* <chr> <dbl> <dbl>  <dbl>  <dbl>  <dbl> <chr>            <chr>             <chr>           
#1 0001      1    NA     NA      2      3 May_1            May_16            May_20          
#2 0002      2     1      3     NA     NA May_5            May_1             May_10          
#3 0003      1     2      3     NA     NA May_1            May_5             May_10          
#4 0004      3     1     NA     NA      2 May_5            May_20            May_1   

Чтобы получить имена столбцов автоматически, мы можем использовать ordinal из english

library(english)
library(stringr)
df %>%
  pivot_longer(cols = -ID, values_drop_na = TRUE) %>%
  group_by(ID) %>% 
  mutate(value = str_c(ordinal(value), "_preference")) %>%
  ungroup %>%
  pivot_wider(names_from = value, values_from = name) %>%     
  left_join(df, .)

Или используя data.table

library(data.table)
setDT(df)[dcast(melt(df, id.var = 'ID', na.rm = TRUE), 
    ID ~ paste0(ordinal(value), "_preference"), value.var = 'variable'), on = .(ID)]
#     ID May_1 May_5 May_10 May_16 May_20 first_preference second_preference third_preference
#1: 0001     1    NA     NA      2      3            May_1            May_16           May_20
#2: 0002     2     1      3     NA     NA            May_5             May_1           May_10
#3: 0003     1     2      3     NA     NA            May_1             May_5           May_10
#4: 0004     3     1     NA     NA      2            May_5            May_20            May_1
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...