You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何从mutate_()迁移至tidy evaluation?是否需通过函数实现?

Migrating from mutate_() to Tidy Evaluation: A Practical Guide

Great question! Making the switch from old underscore-style functions like mutate_() to tidy evaluation is a smart move—once you get familiar with the syntax, it’s far more intuitive and flexible for dynamic data manipulation. Let’s walk through how to make this transition, and address whether functions are the right approach here.

Basic Replacement: Simple Mutations

First, let’s cover the most common case: replacing a straightforward mutate_() call with modern tidy evaluation.

Old mutate_() Syntax

If you were writing something like this (using formulas or strings to define columns):

# Using formulas
mutate_(my_data, new_col = ~old_col + 1)

# Using strings (less common but still used)
mutate_(my_data, "new_col" = "old_col + 1")

Modern Tidy Evaluation Syntax

You can now write this directly with mutate()—no underscore needed, and you can use plain R expressions:

mutate(my_data, new_col = old_col + 1)

This works because dplyr now uses tidy evaluation to automatically capture and evaluate the expressions you pass.

Dynamic Column Names & Batch Mutations

Your question mentions passing a list of new variables and their creation logic—this is where tidy evaluation really shines. Let’s break down how to replicate that workflow.

Old .dots Approach

Previously, you might have used the .dots parameter to pass a list of formulas/strings:

var_specs <- list(
  sum_ab = ~a + b,
  prod_ab = ~a * b,
  diff_ab = ~a - b
)

mutate_(my_data, .dots = var_specs)

Modern Unquoting with !!!

With tidy evaluation, you can use the unquote-splice operator (!!!) to pass your list of expressions directly to mutate():

library(dplyr)
library(rlang) # For quosure helpers, though dplyr loads most of these now

var_specs <- list(
  sum_ab = ~a + b,
  prod_ab = ~a * b,
  diff_ab = ~a - b
)

mutate(my_data, !!!var_specs)

The !!! tells dplyr to "unpack" the list and treat each element as a separate argument to mutate().

Dynamic Column Names (Strings)

If your new variable names are stored as strings (instead of being named in the list), use sym() to convert them to symbols, and := (the "named unquote" operator) to assign them:

var_names <- c("sum_ab", "prod_ab")
var_exprs <- list(~a + b, ~a * b)

# Combine names and expressions into a named list
named_specs <- set_names(var_exprs, var_names)

mutate(my_data, !!!named_specs)

# Or do it inline
mutate(my_data, !!sym(var_names[1]) := a + b, !!sym(var_names[2]) := a * b)

You can also use the curly-curly operator ({{ }}) as a simpler shorthand if you’re working with function arguments (more on that below).

Should You Use Functions for This?

Absolutely—this is exactly the kind of scenario where wrapping your logic in a custom function makes sense. Tidy evaluation was designed to make it easy to write reusable, dynamic functions that work seamlessly with dplyr.

Example Custom Function

Let’s build a function that takes a dataset and a list of variable specifications, then returns the dataset with the new columns added:

add_custom_columns <- function(data, specs) {
  # specs is a named list where names = new column names, values = expressions
  mutate(data, !!!specs)
}

# Usage
my_data <- tibble(a = 1:5, b = 6:10)
my_specs <- list(
  sum_ab = a + b, # You can even skip the ~ now!
  prod_ab = a * b,
  avg_ab = (a + b)/2
)

add_custom_columns(my_data, my_specs)

Even More Flexible: Accepting Direct Expressions

If you want users to pass the column definitions directly as arguments (like they would with mutate()), use enquos() to capture the expressions:

add_custom_columns <- function(data, ...) {
  # Capture all the expressions passed via ...
  new_vars <- enquos(...)
  mutate(data, !!!new_vars)
}

# Usage (just like regular mutate!)
add_custom_columns(my_data,
  sum_ab = a + b,
  prod_ab = a * b,
  avg_ab = (a + b)/2
)

This makes your function feel just like a native dplyr function, which is super intuitive for other tidyverse users.

Key Takeaways

  • Replace mutate_() with plain mutate() for static mutations—no extra syntax needed.
  • Use !!! to splice lists of expressions into mutate() for batch operations.
  • Use sym() + := or {{ }} for dynamic column names.
  • Wrapping this logic in a function is highly recommended—it makes your code reusable, testable, and easier to maintain.

内容的提问来源于stack exchange,提问作者kputschko

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.19 06:42:52