问题描述
样本数据集
ab <- matrix(1:100,ncol = 5)
dat
是矩阵/数据框(例如 ab
)
con
是我想在函数内部使用的条件(例如 > 50
、=< 80
等)
fil_dat <- function (dat,con ) {
fildat <- data[which(rowMeans(dat)"the condition *con* should go here"),]
return(fildat)
}
如何在此处插入条件?此外,必须有其他方法来子集和派生 fildat
。我认为 dplyr::filter
会更容易。但我想不出正确的方法来做到这一点。请问有人可以帮忙吗?而且,更进一步,我可以同时使用多个条件,例如 > 50 & <= 80
吗?
编辑:抱歉,我之前忘记提到这一点。如果该函数还可以处理 NULL 条件语句(即无条件),那就太好了。我知道这对于这个玩具示例没有意义,但对于我的实际功能来说,它确实如此。我也知道我可以在函数中编写一个 if-loop
来克服这个问题。但是子集函数本身可以处理这个会很棒。
解决方法
也许你可以试试eval
fil_dat <- function (dat,con = NULL ) {
if (is.null(con)) return(dat)
return(eval(str2expression(sprintf("dat[which(rowMeans(dat)%s),]",con))))
}
给出
> fil_dat(ab,"<=50")
[,1] [,2] [,3] [,4] [,5]
[1,] 1 21 41 61 81
[2,] 2 22 42 62 82
[3,] 3 23 43 63 83
[4,] 4 24 44 64 84
[5,] 5 25 45 65 85
[6,] 6 26 46 66 86
[7,] 7 27 47 67 87
[8,] 8 28 48 68 88
[9,] 9 29 49 69 89
[10,] 10 30 50 70 90
> fil_dat(ab)
[,] 10 30 50 70 90
[11,] 11 31 51 71 91
[12,] 12 32 52 72 92
[13,] 13 33 53 73 93
[14,] 14 34 54 74 94
[15,] 15 35 55 75 95
[16,] 16 36 56 76 96
[17,] 17 37 57 77 97
[18,] 18 38 58 78 98
[19,] 19 39 59 79 99
[20,] 20 40 60 80 100
,
这是一个解决方案,同样使用 eval
但在 parse
之后。
fil_dat <- function (data,con,drop = FALSE) {
con <- paste("rowMeans(data)",con)
i <- eval(parse(text = con))
data[which(i),drop = drop]
}
ab <- matrix(1:100,ncol = 5)
fil_dat(ab,">= 50")
# [,5]
# [1,] 10 30 50 70 90
# [2,] 11 31 51 71 91
# [3,] 12 32 52 72 92
# [4,] 13 33 53 73 93
# [5,] 14 34 54 74 94
# [6,] 15 35 55 75 95
# [7,] 16 36 56 76 96
# [8,] 17 37 57 77 97
# [9,] 18 38 58 78 98
#[10,] 19 39 59 79 99
#[11,] 20 40 60 80 100
fil_dat(ab,"== 50")
# [,5]
#[1,] 10 30 50 70 90
fil_dat(ab,"== 50",TRUE)
#[1] 10 30 50 70 90