【问题标题】:R - multiple loop counter variablesR - 多个循环计数器变量
【发布时间】:2018-02-14 13:58:22
【问题描述】:

我需要编写循环,其中每次迭代都有一组唯一的变量值。这不是一个嵌套循环“for each i do (for each j do)”类型的问题。下面只是一个示例问题,循环在做什么并不重要,它能够为循环的每次迭代使用多个变量。

简单循环:

df <- data.frame(num = 1:5)
lookup <- data.frame(colors = c("red", "green", "blue"), 
                     pets = c("cat", "dog", "rabbit"),
                     stringsAsFactors = FALSE)
for (color in lookup$colors) {
  df[, color] <- 1
}

我想做什么(伪代码):

for (color, pet in lookup$colors, lookup$pets) {
  df[, color] <- pet
}

我想出的最佳方法如下,但额外的 r[" "] 使代码更难阅读:

for (i in 1:nrow(lookup)) {
  r <- unlist(lookup[i, ])
  df[, r["colors"]] <- r["pets"]
}

df
  num red green   blue
1   1 cat   dog rabbit
2   2 cat   dog rabbit
3   3 cat   dog rabbit
4   4 cat   dog rabbit
5   5 cat   dog rabbit

我想知道解决此类问题的最佳通用方法是什么。在许多情况下,您可以将循环替换为要为每组变量调用的函数,但函数在某些情况下并不适用。

【问题讨论】:

  • 你想要df[lookup$colors] &lt;- lookup$pets[col(df[lookup$colors])]这个吗?
  • 我不确定这是如何工作的?它不适合我。但我正在寻找一种通用的方法——这似乎不是。
  • 根据您的示例,它对我有用并且也可以概括(尽管不清楚您的意思是哪种概括)您是否试图用相应的'填充'颜色'列宠物?
  • 你能显示你的预期输出吗
  • 是的,但这只是一个示例(可能具有误导性)。我正在寻找在循环中使用多个变量的最佳方法。使用您可以执行的功能:myfunc &lt;- function(color, pet) { do something with vars },然后为不同的变量集多次调用它,例如myfunc("red", "dog"); myfunc("blue", "cat") 等。我希望能够做类似的事情,但 for 循环,其中函数不能总是使用。

标签: r for-loop


【解决方案1】:

对于您的具体示例,您将以正确的心态去做。为了稍微清理一下并减少出现错误的机会,您可以将循环重写为:

for (i in seq_len(nrow(lookup))) {
  color_i <- lookup[i, "colors"]
  pet_i <- lookup[i, "pets"]
  df[[color_i]] <- pet_i
}

没有什么不同,但seq_len 避免了lookup 的行数为零的问题。在这种情况下,1:nrow(lookup) 返回c(1, 0)。而且我的循环的内容是否更容易阅读可能是主观的。

如果有帮助,针对您的具体问题的单线解决方案如下:

df[, lookup[["colors"]]] <- lapply(lookup[["pets"]], rep, nrow(df))

相切相关

我会说您的示例是 R 中的一个特殊情况,您在其中迭代地修改现有对象。大多数时候,人们只想遍历多个向量并将结果存储在一个新向量中。例如:

results <- list()

for (i in seq_len(nrow(lookup))) {
  color_i <- lookup[i, "colors"]
  pet_i <- lookup[i, "pets"]
  results[[i]] <- do_something(color_i, pet_i)
}

更好的方法是使用mapply

results <- mapply(FUN = do_something, lookup[["colors"]], lookup[["pets"]])

【讨论】:

  • 感谢您的回答 - 像您建议的那样在开头将查找值保存到一个 var 在某些情况下肯定会有所帮助,但是如果有很多 var,每个 var 在下面的代码中只使用一次,它会很乱。使用 apply 和 assign 做一些事情可能会有所帮助,但我认为这会变得太复杂了。我已经在问题中澄清了我感兴趣的不是我的示例中的特定代码 - 这是在每次循环迭代中拥有多个变量的一般想法。
  • 那么我建议将for 循环的主体更改为一个函数并使用mapply。如有必要,可以使用 &lt;&lt;- 更改函数外部的值,但这通常是不受欢迎的。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2016-01-18
  • 1970-01-01
  • 1970-01-01
  • 2022-01-22
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多