【问题标题】:How can I simplify five for loops into a nested for loop?如何将五个 for 循环简化为嵌套的 for 循环?
【发布时间】:2020-01-14 15:48:59
【问题描述】:

我正在尝试计算 1000 个矩阵的 L2 条件数。但是,我正在为不同维度的矩阵执行此操作。例如,我正在计算 1000 个 5x5 矩阵的 L2 条件数,然后对 10x10 矩阵再次执行相同的操作,依此类推。

我已经解决了这个问题,但这里的问题是我有 5 个 for 循环来做同样的事情。我知道我可以通过嵌套的 for 循环来简化我的代码,但我不确定如何去做。我在下面附上了我的代码。

请注意,这些数字是根据矩阵的维度随机生成的。

#Set up for loops
set.seed(2019) 
CN5 <- NULL
CN10 <- NULL

# First for loop for n = 5
## n = 5
for(i in 1:1000){
  CN5[i] <- kappa(matrix(rnorm(25), nrow = 5))
}

mean(CN5)
sd(CN5)
median(CN5)

#Second for loop with n = 10
## n = 10
for(i in 1:1000){
  CN10[i] <- kappa(matrix(rnorm(100), nrow = 10))  
}

mean(CN10)
sd(CN10)
median(CN10)

如何组合这些循环以便我只有一个?

【问题讨论】:

  • 经验法则是,如果您需要重复两次以上,请为此任务编写一个函数。

标签: r for-loop nested-loops


【解决方案1】:

如 cmets 中所建议的,一般过程是编写一个带有参数的函数,该参数考虑到不同迭代之间的变化(或可能变化)。

从您的代码来看,唯一不同的是方阵 n x n 的维度。

set.seed(2019)

cn_function <- function(n) {
    for(i in 1:1000) {
        CN_n[i] <- kappa(matrix(rnorm(n^2), nrow = n))
    }

    # Return a list with the desired results
    list(n = n, # Store n for good measure
         cn_n = CN_n,
         mean = mean(CN_n),
         median = median(CN_n),
         sd = sd(CN_n))
}

然后,如果您有 p.e. 1000 个 5x5 矩阵和 1000 个 10x10 矩阵,您可以将结果存储在另一个列表 results 中,例如。

matrices_n <- c(5, 10) # or any number of `n`

results <- list()

for(i in seq_along(matrices_n)) {
    results[[i]] <- cn_function(n = matrices_n[i])
}

或者使用很棒的 purrr 包而不是 for 循环:

cn_function <- function(n) {
    CN_n <- purrr::map_dbl(1:1000, ~kappa(matrix(rnorm(5^2), nrow = 5)))

    # Return a list with the desired results
    list(n = n, # Store n for good measure
         cn_n = CN_n,
         mean = mean(CN_n),
         median = median(CN_n),
         sd = sd(CN_n))
}

matrices_n <- c(5, 10)

results <- purrr::map(matrices_n, cn_function)

然后,您可以访问列表中的值,例如 results[[1]]$mean 或类似的东西,具体取决于您要对结果做什么。

【讨论】:

    【解决方案2】:

    看起来你可以把它们放在同一个循环中:

    for(i in 1:1000){
      CN5[i] <- kappa(matrix(rnorm(25), nrow = 5))
      CN10[i] <- kappa(matrix(rnorm(100), nrow = 10))  
    }
    

    根据评论,您可以考虑一个函数:

    get_kappa <- function(n = 25, nrow = 5) {
      return(kappa(matrix(rnorm(n), nrow = nrow)))
    }
    
    for(i in 1:1000){
      CN5[i] <- get_kappa(n = 25, nrow = 5)
      CN10[i] <- get_kappa(n = 100, nrow = 10)
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-01-26
      • 2012-06-23
      • 1970-01-01
      • 2020-07-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多