Reputation: 4346
I have the following data.frame
qs <- structure(list(Question = c("This is a question", "This is a question"),
Correct_Answer = c("D", "B"),
Answer.A = c("This is an answer", "This is an answer"),
Answer.B = c("This is an answer", "This is an answer"),
Answer.C = c("This is an answer", "This is an answer"),
Answer.D = c("This is an answer", "This is an answer"),
Explanation = c("Just because!", "Just because!"),
Response_A = c("", ""),
Response_B = c("", ""),
Response_C = c("", ""),
Response_D = c("", "")),
.Names = c("Question", "Correct_Answer", "Answer.A", "Answer.B",
"Answer.C", "Answer.D", "Explanation", "Response_A",
"Response_B", "Response_C", "Response_D"),
row.names = 1:2, class = "data.frame")
I want to set the Response_X
value to match the Explanation
for each question. For example in the first row, the Correct_Answer
is D, so the Response_D
should equal to the explanation, the other Responses_
should remain blank.
I've tried the following:
library(dplyr)
qs %>% rowwise() %>% mutate_(.dots=setNames(paste(Explanation),
paste0("Response_",Correct_Answer)))
It gives:
Error in paste0("Response_", Correct_Answer) :
object 'Correct_Answer' not found
I feel I should be using apply here, but not sure how.
Upvotes: 2
Views: 611
Reputation: 8601
A tidyverse
solution. You gather the data to a "tidy" form, mutate conditionally on Correct_Answer
, and spread it back.
library(tidyr)
library(dplyr)
qs %>%
gather(Resp, val, Response_A:Response_D, -Correct_Answer, -Explanation) %>% select(-val) %>%
mutate(Expl = if_else(paste("Response", Correct_Answer, sep="_") == Resp, Explanation, "")) %>%
spread(Resp, Expl)
Hope that does the trick!
Upvotes: 2
Reputation: 2076
Using regular for loop you could do this:
for(i in 1:nrow(qs)){
qs[i,paste('Response_',qs[i,'Correct_Answer'], sep = '')]=qs[i,'Explanation']
}
Im still trying to figure out how to update the col values using sapply.
sapply(1:nrow(qs), function(i) qs[paste('Response_',qs[i,'Correct_Answer'], sep = '')]=qs[i,'Explanation'])
Upvotes: 1
Reputation: 388817
One way is using a custom function which assigns the correct value in the correct column for that row
assignValue <- function(x) {
qs[x, paste0("Response_", qs$Correct_Answer[x])] <<- qs$Explanation[x]
}
and then call the function for every row using sapply
sapply(1:nrow(qs), function(x) assignValue(x))
Note, the use of <<-
operator in the function. From the help page (?"<<-"
)
The operators <<- and ->> are normally only used in functions, and cause a search to made through parent environments for an existing definition of the variable being assigned. If such a variable is found (and its binding is not locked) then its value is redefined, otherwise assignment takes place in the global environment
Upvotes: 2