【发布时间】:2021-02-06 11:39:37
【问题描述】:
我有一个数据框,例如
df_reprex <- data.frame(id = rep(paste0("S",round(runif(100, 1000000, 9999999),0)), each=10),
date = rep(seq.Date(today(), by=-7, length.out = 10), 100),
var1 = runif(1000, 10, 20),
var2 = runif(1000, 20, 50),
var3 = runif(1000, 2, 5),
var250 = runif(1000, 100, 200),
var1_baseline = rep(runif(100, 5, 10), each=10),
var2_baseline = rep(runif(100, 50, 80), each=10),
var3_baseline = rep(runif(100, 1, 3), each=10),
var250_baseline = rep(runif(100, 20, 70), each=10))
我想编写一个包含 for 循环的函数,对于数据框中的每一行,该函数将从具有相同名称的非基线列中减去每个“_baseline”列。
我创建了一个脚本,它会自动创建一个包含我要运行的代码的字符串:
df <- df_reprex
# get only numeric columns
df_num <- df %>% dplyr::select_if(., is.numeric)
# create a version with no baselines
df_nobaselines <- df_num %>% select(-contains("baseline"))
#extract names of non-baseline columns
numeric_cols <- names(df_nobaselines)
#initialise empty string
mutatestring <- ""
#write loop to fill in string:
for (colname in numeric_cols) {
mutatestring <- paste(mutatestring, ",", paste0(colname, "_change"), "=", colname, "-", paste0(colname, "_baseline"))
# df_num <- df_num %>%
# mutate(paste0(col, "_change") = col - paste0(col, "_baseline"))
}
mutatestring <- substr(mutatestring, 4, 9999999) # remove stuff at start (I know it's inefficient)
mutatestring2 <- paste("df %>% mutate(", mutatestring, ")") # add mutate call
但是当我尝试调用“mutatestring2”时,它只会打印字符串,例如:
[1] "df %>% mutate( var1_change = var1 - var1_baseline , var2_change = var2 - var2_baseline , var3_change = var3 - var3_baseline , var250_change = var250 - var250_baseline )"
我认为这部分会相对简单,我确定我错过了一些明显的东西,但我就是无法让该字符串中的文本运行!
我尝试了各种略显荒谬的方法,但都没有返回所需的输出(即字符串作为命令输入到控制台时返回的结果):
call(mutatestring2)
eval(mutatestring2)
parse(mutatestring2)
str2lang(mutatestring2)
mget(mutatestring2)
diff_func <- function() {mutatestring2}
diff_func1 <- function() {
a <-mutatestring2
return(a)}
diff_func2 <- function() {str2lang(mutatestring2)}
diff_func3 <- function() {eval(mutatestring2)}
diff_func4 <- function() {parse(mutatestring2)}
diff_func5 <- function() {call(mutatestring2)}
diff_func()
diff_func1()
diff_func2()
diff_func3()
diff_func4()
diff_func5()
我确信一定有一种非常简单的方法可以做到这一点,但我就是想不通!
如何将字符串转换为可以运行或传递给 magrittr 管道的字符串?
【问题讨论】:
-
你需要在
parse中使用text参数,然后eval的结果。例如,您可以使用eval(parse(text = "print(5)"))。但是,重要的是要注意,这通常是一个非常糟糕的主意,并且通常有一个更明智的选择。