0

我正在开发一个函数,该函数将数据框和用户指定的列作为输入,并使用glue_data() 输出一些格式良好的文本。

变量是否有效似乎是抽签的运气,但每次尝试都是一致的。例如,对于 mtcars,mpg 始终有效,而 hp 从不:

library(glue)
data <- head(mtcars)

print_messages <- function(x=NULL, att1=NULL, att2=NULL) {
  
  # This if-else seems to be the problem
  if(is.null(att1)) {
    att1_glue <- ""
  } else {
    att1_glue <- paste0("{", deparse(substitute(att1)),"}")
  }
  
  if(is.null(att2)) {
    att2_glue <- ""
  } else {
    att2_glue <- paste0("{", deparse(substitute(att2)),"}")
  }
  
  pattern <-   paste("", att1_glue,"", att2_glue)        
  
  glue_data(x, pattern)
  
}

print_messages(data, att1=mpg, att2=NULL) 

# 21  
# 21  
# 22.8  
# 21.4  
# 18.7  
# 18.1  

print_messages(data, att1=mpg, att2=hp)
#> Error in print_messages(data, att1 = mpg, att2 = hp): object 'hp' not found

这不是哪个变量进入att1vs的函数att2

我发现 if-else 是问题所在,但不知道如何解决。它被插入是因为我不能只有一个空参数——这使得glue_data()返回一个 0 字符的字符串:

print_messages <- function(x=NULL,att1=NULL, att2=NULL) {
  
  att1_glue <- paste0("{", deparse(substitute(att1)),"}")
  att2_glue <- paste0("{", deparse(substitute(att2)),"}")
  
  pattern <-   paste("",att1_glue,"", att2_glue)        
  
  glue_data(x, pattern)
  
}


print_messages(data, att1=mpg, att2=hp )
# 21  110
# 21  110
# 22.8  93
# 21.4  110
# 18.7  175
# 18.1  105

print_messages(data, att1=hp, att2=NULL )


我已经尝试过使用 in 函数中的参数的其他方法glue_data(),例如this answer。但中心问题似乎与 if-else 有关。

我想知道那里发生了什么?即使有办法解决这个问题glue,我也会对为什么解析适用于某些列而不是其他列感兴趣!

感谢您的帮助!

4

1 回答 1

1

评估不存在的对象将引发错误。

f <- function(x = NULL) if(is.null(x)) cat("hi") else cat("bye")
f(mpg) # error
f("mpg")
#> bye
f()
#> hi

第一个函数应该抛出一个错误,你的环境中是否有一个名为 mpg 的对象?在这种情况下,词法作用域会找到它,并产生is.null(mpg)as FALSE

另一种方法是使用 dots ...,并使用 的矢量化性质paste,避免使用NULL.

print_messages <- function(data, ...){
  expr = paste0("{", 
                vapply(substitute(...()), deparse, "")
                , "}", collapse = " ")
  glue_data(data, expr)
}
于 2022-02-06T04:48:37.167 回答