Search and replace: Are you tired of nested `ifelse`?
Want to share your content on R-bloggers? click here if you have a blog, or here if you don't.
It happens all the time: you have a vector of fruits and you want to replace all bananas with apples, all oranges with pineapples, and leave all the other fruits as-is, or maybe change them all to figs. The usual solution? A big old nested `ifelse`:
basket <- c("apple", "banana", "lemon", "orange", | |
"orange", "pear", "cherry") | |
ifelse(basket == "banana", "apple", | |
ifelse(basket == "orange", "pineapple", | |
basket)) # or "fig")) | |
# [1] "apple" "apple" "lemon" "pineapple" | |
# [4] "pineapple" "pear" "cherry" |
Ok, that didn’t look too bad, especially with the code and fruits nicely aligned. But what if I had a lot of fruits to change and little patience? Wouldn’t it be nice if R had a built-in function for doing multiple search and replace? Someone please tell me if there is already such a function. If not, here is one I wrote that builds a nested `ifelse` function by recursion:
decode <- function(x, search, replace, default = NULL) { | |
# build a nested ifelse function by recursion | |
decode.fun <- function(search, replace, default = NULL) | |
if (length(search) == 0L) { | |
function(x) if (is.null(default)) x else rep(default, length(x)) | |
} else { | |
function(x) ifelse(x == search[1L], replace[1L], | |
decode.fun(tail(search, -1L), | |
tail(replace, -1L), | |
default)(x)) | |
} | |
return(decode.fun(search, replace, default)(x)) | |
} |
Note that I named the function after the `decode` SQL function. Here are a couple examples:
decode(basket, search = c("banana", "orange"), | |
replace = c("apple", "pineapple")) | |
# [1] "apple" "apple" "lemon" "pineapple" "pineapple" "pear" "cherry" | |
decode(basket, search = c("banana", "orange"), | |
replace = c("apple", "pineapple"), | |
default = "fig") | |
# [1] "fig" "apple" "fig" "pineapple" "pineapple" "fig" "fig" |
Feel free to use it with your favorite fruits or vegetables! Cheers!
P.S.: I wrote this function as an answer to this S.O. question. Thank you to Matthew Lundberg for sharing ideas.
R-bloggers.com offers daily e-mail updates about R news and tutorials about learning R and many other topics. Click here if you're looking to post or find an R/data-science job.
Want to share your content on R-bloggers? click here if you have a blog, or here if you don't.