I\'m sorry for the confusion but eventually, the first example I posted (at the bottom of the page), did not help me to figure out how tidyeval works with mutate, so I\'m ad
@MrFlick's solution works for the one column case, but since OP used ... as an argument, I assume OP would also want the function to be able to take in multiple columns. For example, the following would not work:
colTo1 <- function(dt, ...) {
col <- quo_name(quo(...))
mutate(dt, !!col := 1)
}
colTo1(mtcars, mpg, cyl)
Error in inherits(x, "quosure") : object 'cyl' not found
What we can do is to use quos instead of quo and mutate_at instead of mutate:
colTo1 <- function(dt, ...) {
cols <- quos(...)
mutate_at(dt, vars(!!!cols), function(x) x=1)
}
quos converts each argument from ... into vector of quosures. Using mutate_at's vars syntax and explicit splicing with !!! from rlang, we can unquote each quosure in cols, and mutate on those specified columns.
Now this works as intended:
colTo1(mtcars, mpg, cyl)
Result:
mpg cyl disp hp drat wt qsec vs am gear carb
1 1 1 160.0 110 3.90 2.620 16.46 0 1 4 4
2 1 1 160.0 110 3.90 2.875 17.02 0 1 4 4
3 1 1 108.0 93 3.85 2.320 18.61 1 1 4 1
4 1 1 258.0 110 3.08 3.215 19.44 1 0 3 1
5 1 1 360.0 175 3.15 3.440 17.02 0 0 3 2
6 1 1 225.0 105 2.76 3.460 20.22 1 0 3 1
7 1 1 360.0 245 3.21 3.570 15.84 0 0 3 4
8 1 1 146.7 62 3.69 3.190 20.00 1 0 4 2
9 1 1 140.8 95 3.92 3.150 22.90 1 0 4 2
10 1 1 167.6 123 3.92 3.440 18.30 1 0 4 4
...
It's also easy enough to let "1" be another argument to be passed into the function:
colToX <- function(dt, ..., X) {
cols <- quos(...)
mutate_at(dt, vars(!!!cols), function(x) x=X)
}
colToX(mtcars, mpg, cyl, X = 2)
Edit: OP changed the question to require that X should be another column in the same dataframe. Below is my new solution:
colToX <- function(dt, ..., X) {
cols <- quos(...)
X_quo <- enquo(X)
mutate_at(dt, vars(!!!cols), funs(.data$`!!`(X_quo)))
}
colToX(mtcars, mpg, cyl, X = hp)
Here, I am using the funs function to create a list of function calls to each column referenced from vars. .data refers to the input dataframe into mutate_at (in this case dt). I used enquo to convert what's called from X into a quosure and unquote it using !!.
Result:
mpg cyl disp hp drat wt qsec vs am gear carb
1 110 110 160.0 110 3.90 2.620 16.46 0 1 4 4
2 110 110 160.0 110 3.90 2.875 17.02 0 1 4 4
3 93 93 108.0 93 3.85 2.320 18.61 1 1 4 1
4 110 110 258.0 110 3.08 3.215 19.44 1 0 3 1
5 175 175 360.0 175 3.15 3.440 17.02 0 0 3 2
6 105 105 225.0 105 2.76 3.460 20.22 1 0 3 1
7 245 245 360.0 245 3.21 3.570 15.84 0 0 3 4
8 62 62 146.7 62 3.69 3.190 20.00 1 0 4 2
9 95 95 140.8 95 3.92 3.150 22.90 1 0 4 2
10 123 123 167.6 123 3.92 3.440 18.30 1 0 4 4
...