gpt4 book ai didi

r - 使用 if 条件修改 for 循环以在 R 中应用格式

转载 作者:行者123 更新时间:2023-12-02 08:03:48 25 4
gpt4 key购买 nike

我正在创建一个名为 indexPoints 的变量,其中包含通过特定条件的索引值子集 -

set.seed(1)
x = abs(rnorm(100,1))
y = abs(rnorm(100,1))
threshFC = 0.5

indexPoints=c()
seqVec = seq(1, length(x))
for (i in seq_along(seqVec)){
fract = x[i]/y[I]
fract[1] = NaN
if (!is.nan(fract)){
if(fract > (threshFC + 1) || fract < (1/(threshFC+1))){
indexPoints = c(indexPoints, i)
}
}
}

我正在尝试使用更有效的方法重新创建 indexPoints,例如应用方法(除了 sapply 之外的任何方法)。我开始了如下所示的过程 -

set.seed(1)
x = abs(rnorm(100,1))
y = abs(rnorm(100,1))
threshFC = 0.5

seqVec <- seq_along(x)
fract = x[seqVec]/y[seqVec]
fract[1] = NaN
vapply(fract, function(i){
if (!is.nan(fract)){ if(fract > (threshFC + 1) || fract < (1/(threshFC+1))){ i}}
}, character(1))

但是,这种尝试会导致错误:

Error in vapply(fract, function(i) { : values must be length 1,
but FUN(X[[1]]) result is length 0

如何继续修改代码使其成为apply格式。注意:有时,fract 变量包含 NaN 值,我在上面的最小示例中使用“fract[1] = NaN”模仿了它。

最佳答案

你的代码有几个问题:

  1. 您告诉 vapply 您希望内部代码返回一个 字符,但您唯一返回的是 i,它是 数字;
  2. 只有在所有条件都满足时才显式返回一些东西,这意味着如果条件不都好,你不会返回任何东西......这与 return(NULL) 相同,它是也不是 character(尝试 vapply(1:2, function(a) return(NULL), character(1)));
  3. 您显式设置了 fract[1] = NaN 然后测试了 !is.nan(fract),所以您永远不会得到任何东西;和
  4. (可能是打字错误)您引用了 y[I](大写的“i”),这是一个错误,除非 I 在某处定义(这不再是语法错误,但现在是逻辑错误)。

如果我在你的 for 循环中修改代码(删除 NaN 赋值),我得到

indexPoints
# [1] 3 4 5 6 10 11 12 13 14 15 16 18 20 21 25 26 28 29 30 31 32 34 35 38 39
# [26] 40 42 43 44 45 47 48 49 50 52 53 54 55 56 57 58 59 60 61 64 66 68 70 71 72
# [51] 74 75 77 78 79 80 81 82 83 86 88 89 90 91 92 93 95 96 97 98 99

如果我们真的想一次做一个(我建议不要这样做,请阅读下文),那么有几种方法:

  1. 使用Filter 只返回条件为真的索引:

    indexPoints2 <- Filter(function(i) {
    fract <- x[i] / y[i]
    !is.nan(fract) && (fract > (threshFC+1) | fract < (1/(threshFC+1)))
    }, seq_along(seqVec))
    identical(indexPoints, indexPoints2)
    # [1] TRUE
  2. 使用 vapply 正确,以任何一种方式返回一个整数:

    indexPoints3 <- vapply(seq_along(seqVec), function(i) {
    fract <- x[i] / y[i]
    if (!is.nan(fract) && (fract > (threshFC+1) | fract < (1/(threshFC+1)))) i else NA_integer_
    }, integer(1))
    str(indexPoints3)
    # int [1:100] NA NA 3 4 5 6 NA NA NA 10 ...
    indexPoints3 <- indexPoints3[!is.na(indexPoints3)]
    identical(indexPoints, indexPoints3)
    # [1] TRUE

    (注意显式返回特定类型的 NA,即 NA_integer_,这样 vapply 就会很高兴。)

  3. 如果索引符合条件,我们可以只返回逻辑:

    logicalPoints4 <- vapply(seq_along(seqVec), function(i) {
    fract <- x[i] / y[i]
    !is.nan(fract) && (fract > (threshFC+1) | fract < (1/(threshFC+1)))
    }, logical(1))
    head(logicalPoints4)
    # [1] FALSE FALSE TRUE TRUE TRUE TRUE
    identical(indexPoints, which(logicalPoints4))
    # [1] TRUE

但实际上,绝对没有必要使用 vapply 或任何 apply 函数,因为这可以很容易地(并且更有效地)作为向量进行检查:

fract <- x/y # all at once
indexPoints5 <- which(!is.nan(fract) & (fract > (threshFC+1) | fract < (1/(threshFC+1))))
identical(indexPoints, indexPoints5)
# [1] TRUE

(如果您不使用 which,您会看到它为您提供了一个 logical 向量,指示是否满足条件,类似于上面的项目符号 3 logicalPoints4.)

关于r - 使用 if 条件修改 for 循环以在 R 中应用格式,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/53934893/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com