Как я могу объединить данные с категориальными ответами, чтобы получить процент каждого типа ответа в R?

#r #dataframe #aggregate

#r #фрейм данных #агрегировать

Вопрос:

Я хочу получить процентное соотношение типов категориальных ответов для разных типов вопросов (ТИП). У меня есть несколько ответов для каждого типа для каждого отдельного человека с несколькими категориальными ответами (разные уровни).

1) каждый человек должен находиться в другой строке, и
2) столбцы должны быть ТИПАМИ уровень ответа, при этом значение равно проценту раз, когда этот конкретный уровень ответа был задан для этого типа вопроса для этого человека.

ДАННЫЕ выглядят следующим образом:

 SUBJECT TYPE    RESPONSE  
John    a   kappa                       
John    b   gamma  
John    a   delta  
John    a   gamma  
Mary    a   kappa   
Mary    a   delta       
Mary    b   kappa  
Mary    a   gamma  
Bill    b   delta  
Bill    a   gamma  
  

Результат должен выглядеть следующим образом:

 SUBJECT a-kappa     a-gamma   a-delta   b-kappa     b-gamma b-delta
John    0.33        0.33      0.33      1.00        1.00    0.00
Mary    0.66        0.33      0.00      1.00        0.00    0.00
Bill    1.00        0.00      0.00      0.00        0.00    1.00
  

На основе ответа c1au61o_HH я смог создать что-то, что работает для моего фактического файла данных, но все равно потребуется некоторая постобработка. (Это тоже не очень элегантно, но это небольшая проблема.)

  Finaldf <- mydata %>%     
 group_by(Subject,Type) %>%     
 mutate(TOT = n()) %>%      
 group_by(Subject, Response, Type) %>%     
 mutate(RESPTOT = n())     

 Finaldf <- distinct(Finaldf)    
 Finaldf$Percentage <- Finaldf$RESPTOT/Finaldf$TOT    
  

Любая помощь очень ценится, также, пожалуйста, с некоторыми объяснениями.

Ответ №1:

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

 library(tidyverse)
df %>% 
  unite(TYPE_RESPONSE, c("TYPE", "RESPONSE"), sep = "_") %>% 
  group_by(SUBJECT) %>% 
  mutate(TOT = n()) %>% 
  group_by(SUBJECT, TYPE_RESPONSE) %>% 
  summarize(perc = n()/TOT * 100) %>% 
  spread(TYPE_RESPONSE, perc)
  

ДАННЫЕ:

 df <- tibble( SUBJECT= rep(c("John", "Mary","Bill"), each = 4), 
                 TYPE = rep(c("a","b"), 6),
                 RESPONSE = rep(c("kappa", "gamma", "delta"), 4)
)
  

РЕДАКТИРОВАТЬ в ответ на комментарий:

Я понимаю, что вы хотите рассчитать процент с помощью SUBJECT and TYPE , поэтому код будет примерно таким:

 library(tidyverse)
df %>% 
  group_by(SUBJECT, TYPE) %>% 
  mutate(TOT = n()) %>%
  unite(TYPE_RESPONSE, c("TYPE", "RESPONSE"), sep = "_") %>% 
  group_by(SUBJECT, TYPE_RESPONSE) %>% 
  summarize(perc = n()/TOT * 100)%>% 
  spread(TYPE_RESPONSE, perc)
  

Комментарии:

1. Спасибо, это дает мне несколько идей. Но мне нужен процент, например, для гаммы, только для вопросов типа A. Итак, приведенный выше код для John дает проценты 25 и 25 для a_kappa и a_delta и NA для a_gamma, но мне нужно получить, что 50% ответов «a» для John — это каппа, а 50% — дельта.

2. Итак, это процент ответа внутри типа в теме, верно?

3. Спасибо! Я смог написать что-то, что работает с моим файлом данных, но не совсем соответствует желаемому формату вывода. Я опубликовал это выше. Еще раз спасибо.

4. Вы пробовали обновленный код, который я предоставил? Разве это не то, что вы хотели?

5. Привет, это работает с сгенерированными данными, но когда я пробую это с моим фактическим фреймом данных, это дает мне, например, 200 процентов для некоторых значений. Я не уверен, почему. Но с помощью описанной выше работы я смог получить то, что мне было нужно. Большое вам спасибо за вашу помощь!