2014-12-29 4 views
2

У меня data.frame L1States_df, который выглядит следующим образом:Для каждой строки data.frame, получить имя столбца, где значение ИСТИНА

BoltOn CutOn IdleOn PumpOn 
1 FALSE FALSE FALSE FALSE 
2 FALSE FALSE TRUE FALSE 
3 FALSE FALSE TRUE FALSE 
4 FALSE FALSE TRUE FALSE 
5 FALSE FALSE TRUE FALSE 
6 FALSE FALSE FALSE TRUE 

Для каждой линии L1States_df, может либо один, либо нет (ноль) ИСТИНА, остальное будет FALSE. Я хотел бы создать новый вектор, который содержит, для каждой строки:

  • имя столбца, связанного с TRUE (если есть ИСТИНА на этой линии)
  • NA, если нет каких-либо ИСТИНА на этой линии

Sample желаемый результат:

State 
1 NA 
2 "IdleOn" 
3 "IdleOn" 
4 "IdleOn" 
5 "IdleOn" 
6 "PumpOn" 

Я пробовал:

apply(L1States_df,1,function(x) names(which(x==TRUE))) 

но это не создает NA, когда нет никакого TRUE на линии, поэтому я ставлю IFELSE:

apply(L1States_df,1,function(x) ifelse(is.null(names(which(x==TRUE))),NA,names(which(x==TRUE)))) 

Есть ли лучший/быстрый способ, или есть предопределенная функция, которая делает такого рода вещи (возможно, data.table)?

Дополнительные пункты:, хотя это никогда не должно происходить, просто для спокойствия: как я могу получить генерируемое NA, если на определенной строке имеется более одного ИСТИНА?

ответ

0

Другой возможность

m <- as.matrix(mydf) 
replace(NA, row(m)[m], colnames(m)[col(m)[m]]) 
# [1] NA  "IdleOn" "IdleOn" "IdleOn" "IdleOn" "PumpOn" 

А для бонусных очков, вы можете использовать match для создания NA по строкам с более одного ИСТИНА

match(rowSums(mydf) > 1, TRUE) 
# [1] NA NA NA NA NA NA 
1

Вот Векторизованное возможное решение (без необходимости в apply)

indx <- which(L1States_df == TRUE, arr.ind = TRUE) 
names(L1States_df)[indx[match(seq_len(nrow(L1States_df)), indx[, 1]), 2]] 
## [1] NA  "IdleOn" "IdleOn" "IdleOn" "IdleOn" "PumpOn" 
Смежные вопросы