Добавить имена столбцов в качестве значения строки - PullRequest
0 голосов
/ 12 декабря 2018

предположим, у меня есть следующий фрейм данных.Идея состоит в том, чтобы иметь возможность извлекать имена столбцов, которые содержат «1» в качестве значения, и добавлять их в новый фрейм данных с тем же «id».

db<-data.frame(id=c(1,2,3,4,5,6),col1=c(0,0,0,1,0,1),col2=c(0,0,1,1,0,0),col3=c(0,0,0,0,0,1),col4=c(1,0,0,0,0,0))

  id col1 col2 col3 col4
1  1    0    0    0    1
2  2    0    0    0    0
3  3    0    1    0    0
4  4    1    1    0    0
5  5    0    0    0    0
6  6    1    0    1    0

db2<-data.frame(id=c(1,2,3,4,5,6),cols=c("col4","-","col2","col1,col2","-","col1,col4"))

  id      cols
1  1      col4
2  2         -
3  3      col2
4  4 col1,col2
5  5         -
6  6 col1,col3

Ответы [ 2 ]

0 голосов
/ 12 декабря 2018

Другой вариант с использованием data.table

library(data.table)
setDT(db)

db[, .(.(names(row <- unlist(.SD))[row == 1])), by = id]

#    id        V1
# 1:  1      col4
# 2:  2          
# 3:  3      col2
# 4:  4 col1,col2
# 5:  5          
# 6:  6 col1,col3

Или, если вы хотите добавить его в качестве нового столбца

db[, cols := .(.(names(row <- unlist(.SD))[row == 1])), by = id]


#    id col1 col2 col3 col4      cols
# 1:  1    0    0    0    1      col4
# 2:  2    0    0    0    0          
# 3:  3    0    1    0    0      col2
# 4:  4    1    1    0    0 col1,col2
# 5:  5    0    0    0    0          
# 6:  6    1    0    1    0 col1,col3

, обратите внимание, что приведенный выше код создает столбец списков, а несимвольно-векторный столбец как в ответе акруна.Если вам нужен символьный векторный столбец, замените

.(.(names(row <- unlist(.SD))[row == 1]))

на

paste(names(row <- unlist(.SD))[row == 1], collapse = ',')

0 голосов
/ 12 декабря 2018

Мы можем циклически проходить по строкам с помощью apply, подставив под names значение столбца 1, paste вместе, чтобы создать столбец 'cols' в новом data.frame 'db2'.При необходимости измените пробелы ("") на -

db2 <- data.frame(db[1], cols = apply(db[-1], 1, function(x)
       paste(names(x)[x==1], collapse=",")), stringsAsFactors = FALSE)
db2$cols[db2$cols== ""] <- "-"
db2
#  id      cols
#1  1      col4
#2  2         -
#3  3      col2
#4  4 col1,col2
#5  5         -
#6  6 col1,col3

Или мы можем векторизовать его в base R

m1 <- (NA^!db[-1]) * col(db[-1])
m1[] <- colnames(m1)[m1]
v1 <- do.call(paste, c(as.data.frame(m1), sep=","))
db2 <- data.frame(db[1], cols =  gsub(",?NA,?", "", v1))
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...