The_Anomaly
The_Anomaly

Reputation: 2505

Convert row values into columns in R

I have a data table that looks like this, resulting from a questionnaire about what drugs (encoded as a Drug ID) people are taking:

ID  Drug1 Drug2 Drug3 Drug4
1   45    NA    NA    NA
2   NA    NA    NA    NA
3   23    45    NA    NA
4   23    NA    NA    NA
5   57    45    23    NA

In other words, the 1st person is taking a drug with ID "45" The second person is not taking any drugs. The third person is taking drug 23 and 45.

I would like to convert this into the following matrix:

ID  23     45      57
1   FALSE  TRUE    FALSE
2   FALSE  FALSE    FALSE
3   TRUE   TRUE    FALSE
4   TRUE   FALSE    FALSE
5   TRUE   TRUE    TRUE

How can I do this in R? I could not find a solution online that works for multiple columns like this.

Upvotes: 2

Views: 2250

Answers (3)

akrun
akrun

Reputation: 887118

We could use mtabulate

library(qdapTools)
res <- cbind(df1[1],!!mtabulate(as.data.frame(t(df1[-1]))))
row.names(res) <- NULL
res
#  ID    23    45    57
#1  1 FALSE  TRUE FALSE
#2  2 FALSE FALSE FALSE
#3  3  TRUE  TRUE FALSE
#4  4  TRUE FALSE FALSE
#5  5  TRUE  TRUE  TRUE

Upvotes: 1

thelatemail
thelatemail

Reputation: 93813

No packages needed:

with( cbind(dat[1], stack(dat[-1]) ), table(ID, values) > 0 )

#   values
#ID     23    45    57
#  1 FALSE  TRUE FALSE
#  2 FALSE FALSE FALSE
#  3  TRUE  TRUE FALSE
#  4  TRUE FALSE FALSE
#  5  TRUE  TRUE  TRUE

Upvotes: 2

Pierre L
Pierre L

Reputation: 28441

We can use recast from reshape2 to melt then cast the data frame. The exclamation points !! are short for as.logical:

library(reshape2)
r <- recast(df, id.var="ID", ID~value)
cbind(r[1], !!r[,-c(1,ncol(r))])
#   ID    23    45    57
# 1  1 FALSE  TRUE FALSE
# 2  2 FALSE FALSE FALSE
# 3  3  TRUE  TRUE FALSE
# 4  4  TRUE FALSE FALSE
# 5  5  TRUE  TRUE  TRUE

Upvotes: 2

Related Questions