【问题标题】:Pass/loop over column names to data.table and ggplot as variables将列名作为变量传递/循环到 data.table 和 ggplot
【发布时间】:2021-10-14 01:57:32
【问题描述】:

data.tableggplot 经常遇到的一个问题是它们在 for 循环中的使用,我在其中迭代一组列名。

以这张数据表为例:

dt <- data.table(values1=rep(c(1,2),each=2),
                 values2=rep(c(10,20),each=2),
                 notthis=0,
                 category=rep(c('a','b'),each=2))
##
##    values1 values2 notthis category
## 1:       1      10       0        a
## 2:       1      10       0        a
## 3:       2      20       0        b
## 4:       2      20       0        b

假设我想遍历dt 的所有列,除了notthiscategory。对于每一列,我想根据category绘制其值的两个直方图,并添加一条表示它们的平均值的垂直线(可能使用pdfprintdev.off将这些图传递到pdf设备) .

代码思路可以如下:

loopnames <- setdiff(colnames(dt), c('notthis', 'category'))
## [1] "values1" "values2"

for(ZZZ in loopnames){
    dtmeans <- dt[, .(means=mean(ZZZ)), by=category]

    ggplot(dt) + geom_histogram(aes(x=ZZZ, fill=category)) +
                 geom_vline(data=dtmeans, aes(xintercept=means, color=category))
}

但显然它不起作用。使用ZZZ 变量会在data.tableggplot 中产生错误。

注意某些代码行背后的原因:

  • 我想构建一个列列表进行迭代,由差异定义:dt 可能有数百列,我只想排除其中两个列。
  • 我需要构建一个数据表,其中包含传递给geom_vline 的方法(在我看来,这个数据表是多余的,但这是ggplot 想要的)。
  • 我想使用data.table的特殊语法来构造这样的数据表。

参考this postthis postthis post 的有用答案,我尝试了各种组合以使上述代码理念发挥作用:使用with=FALSE 作为数据表,quote()/ eval() 对,“取消引用”!! 字符,以及 as.names()sym()。但没有任何组合奏效。最接近解决问题的是 quote()/eval() 对,它似乎对 data.tableggplot 都有效,但我没有设法在 for 循环中使用此解决方法。

您能否建议一种通用方法不使用 tidyverse 命令来处理包中的变量/循环列名,例如 data.tableggplot

【问题讨论】:

    标签: r for-loop ggplot2 data.table


    【解决方案1】:

    尝试在循环体中使用get(ZZZ),而不是ZZZ

    【讨论】:

    • aes_string(x=ZZZ, fill="category")
    • 太棒了,get 在这两个包中都能胜任!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-07-05
    • 2014-08-13
    • 2017-03-16
    • 2017-02-13
    • 2015-11-21
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多