Вы можете изменить несколько столбцов категории и нескольких столбцов значений с помощью pivot_wider
из пакета tidyr
(который входит в комплект tidyverse
пакетов):
library(tidyverse)
df_wide = df_long %>%
pivot_wider(names_from=c(action, ConfChall), values_from=vals)
userID SAT GRE task_conf task_chall active_conf active_chall sleep_conf sleep_chall morn_conf morn_chall
1 30798 A 1400 2 3 5 2 6 1 4 2
2 30895 A 1200 6 2 5 3 5 2 5 3
3 32678 B 1000 5 3 6 3 6 2 5 2
4 34679 A 1300 4 3 4 2 6 1 6 3
reshape2
- это старый пакет, который, насколько я знаю, больше не находится в активной разработке и был заменен tidyverse
пакетами.
Для устранения предупреждения, которое вы упомянули вкомментарии: если в широком фрейме данных есть какие-либо ячейки, имеющие более одного значения, то вы получите полученный результат. Это произойдет в вашем случае, когда существует более одной строки с одним и тем же идентификатором пользователя, SAT, GRE, action и ConfChall, или вообще, когда они представляют собой комбинации категорий строк и столбцов, которые могут появляться в более чем одной строке. Этого не происходит в вашем образце данных, но это происходит в ваших реальных данных.
Итак, давайте добавим дублированную строку к вашему образцу данных:
df_long = read.table(text="userID SAT GRE action ConfChall vals
30798 A 1400 task conf 2
30798 A 1400 task chall 3
30798 A 1400 task chall 4 # added row to create a duplicate
30798 A 1400 active conf 5
30798 A 1400 active chall 2
30798 A 1400 sleep conf 6
30798 A 1400 sleep chall 1
30798 A 1400 morn conf 4
30798 A 1400 morn chall 2
30895 A 1200 task conf 6
30895 A 1200 task chall 2
30895 A 1200 active conf 5
30895 A 1200 active chall 3
30895 A 1200 sleep conf 5
30895 A 1200 sleep chall 2
30895 A 1200 morn conf 5
30895 A 1200 morn chall 3
32678 B 1000 task conf 5
32678 B 1000 task chall 3
32678 B 1000 active conf 6
32678 B 1000 active chall 3
32678 B 1000 sleep conf 6
32678 B 1000 sleep chall 2
32678 B 1000 morn conf 5
32678 B 1000 morn chall 2
34679 A 1300 task conf 4
34679 A 1300 task chall 3
34679 A 1300 active conf 4
34679 A 1300 active chall 2
34679 A 1300 sleep conf 6
34679 A 1300 sleep chall 1
34679 A 1300 morn conf 6
34679 A 1300 morn chall 3", header=TRUE)
Теперь давайте снова изменим ширину,Обратите внимание, что мы получаем предупреждение и что одна из ячеек столбца списка имеет два значения вместо одного:
df_long %>%
pivot_wider(names_from=c(action, ConfChall), values_from=vals)
Warning message:
Values in `vals` are not uniquely identified; output will contain list-cols.
* Use `values_fn = list(vals = list)` to suppress this warning.
* Use `values_fn = list(vals = length)` to identify where the duplicates arise
* Use `values_fn = list(vals = summary_fun)` to summarise duplicates
userID SAT GRE task_conf task_chall active_conf active_chall sleep_conf sleep_chall morn_conf morn_chall
<int> <fct> <int> <list<int>> <list<int>> <list<int>> <list<int>> <list<int>> <list<int>> <list<int>> <list<int>>
1 30798 A 1400 [1] [2] [1] [1] [1] [1] [1] [1]
2 30895 A 1200 [1] [1] [1] [1] [1] [1] [1] [1]
3 32678 B 1000 [1] [1] [1] [1] [1] [1] [1] [1]
4 34679 A 1300 [1] [1] [1] [1] [1] [1] [1] [1]
Чтобы получить обычный фрейм данных, вы можете использовать unnest()
. Обратите внимание, что теперь есть пять строк, с идентификатором пользователя 30798, появляющимся дважды:
df_long %>%
pivot_wider(names_from=c(action, ConfChall), values_from=vals) %>%
unnest()
userID SAT GRE task_conf task_chall active_conf active_chall sleep_conf sleep_chall morn_conf morn_chall
<int> <fct> <int> <int> <int> <int> <int> <int> <int> <int> <int>
1 30798 A 1400 2 3 5 2 6 1 4 2
2 30798 A 1400 2 4 5 2 6 1 4 2
3 30895 A 1200 6 2 5 3 5 2 5 3
4 32678 B 1000 5 3 6 3 6 2 5 2
5 34679 A 1300 4 3 4 2 6 1 6 3
Если вы хотите, чтобы дублирующие строки каким-то образом суммировались, так что вы получите только одну строкуДля каждой комбинации переменных строки и столбца вы можете применить функцию суммирования. Ниже мы берем среднее значение для каждой ячейки, которое в данном случае влияет только на одну ячейку с двумя строками данных:
df_long %>%
pivot_wider(names_from=c(action, ConfChall), values_from=vals,
values_fn=list(vals=mean))
userID SAT GRE task_conf task_chall active_conf active_chall sleep_conf sleep_chall morn_conf morn_chall
<int> <fct> <int> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
1 30798 A 1400 2 3.5 5 2 6 1 4 2
2 30895 A 1200 6 2 5 3 5 2 5 3
3 32678 B 1000 5 3 6 3 6 2 5 2
4 34679 A 1300 4 3 4 2 6 1 6 3