代码之家  ›  专栏  ›  技术社区  ›  stschn

并非for循环中的所有R对象类型更新都保留

  •  0
  • stschn  · 技术社区  · 1 年前

    我遇到了以下问题,目前我还没有解释。

    a <- array(seq(24), dim = c(4, 3, 2))
    
    # The axis to be fixed and read completely
    axis = c(3)
    
    d <- dim(a)
    ds <- lapply(d, seq)
    
    # initialize the list for later slicing
    ds[-axis] <- 1
    
    # The axis to be iterated along
    axis_iter <- seq_along(d)[-axis]
    
    # Number of iterations
    n_iter <- prod(d[-axis])
    order <- rev(seq_along(d[-axis]))
    
    # Only for demonstration purposes
    tmp <- rep(NA, n_iter)
    
    for (iter in seq(n_iter)) {
      tmp[iter] <- iter
      # This shows that the values within ds are updated
      print(unlist(ds))
      # slice array and calculate the minimum value
      # Note: That's also only for demonstration purposes
      print(min(do.call(`[`, c(list(a), ds, list(drop = TRUE)))))
      for (i in order) {
        ds[axis_iter][[i]] <- ds[axis_iter][[i]] + 1
        if (ds[axis_iter][[i]] <= d[i])
          break
        else
          ds[axis_iter][[i]] <- 1
      }
    }
    

    代码本身工作得很好。但我不知道为什么向量tmp的更新会在for循环之后保留,而对于列表ds则不会。运行代码后,列表对象的值与之前相同:

    > ds
    [[1]]
    [1] 1
    
    [[2]]
    [1] 1
    
    [[3]]
    [1] 1 2
    

    提前感谢您的帮助!

    1 回复  |  直到 1 年前
        1
  •  1
  •   kernelize    1 年前

    for 正在应用循环。列表 ds 结果和循环逻辑的初始after相同。

    [ 1 ] Before nested for-loop:    1 1 1 2 
    [ 1 ] After nested for-loop:     1 2 1 2 
    [ 2 ] Before nested for-loop:    1 2 1 2 
    [ 2 ] After nested for-loop:     1 3 1 2 
    [ 3 ] Before nested for-loop:    1 3 1 2 
    [ 3 ] After nested for-loop:     2 1 1 2 
    [ 4 ] Before nested for-loop:    2 1 1 2 
    [ 4 ] After nested for-loop:     2 2 1 2 
    [ 5 ] Before nested for-loop:    2 2 1 2 
    [ 5 ] After nested for-loop:     2 3 1 2 
    [ 6 ] Before nested for-loop:    2 3 1 2 
    [ 6 ] After nested for-loop:     3 1 1 2 
    [ 7 ] Before nested for-loop:    3 1 1 2 
    [ 7 ] After nested for-loop:     3 2 1 2 
    [ 8 ] Before nested for-loop:    3 2 1 2 
    [ 8 ] After nested for-loop:     3 3 1 2 
    [ 9 ] Before nested for-loop:    3 3 1 2 
    [ 9 ] After nested for-loop:     4 1 1 2 
    [ 10 ] Before nested for-loop:   4 1 1 2 
    [ 10 ] After nested for-loop:    4 2 1 2 
    [ 11 ] Before nested for-loop:   4 2 1 2 
    [ 11 ] After nested for-loop:    4 3 1 2 
    [ 12 ] Before nested for-loop:   4 3 1 2 
    [ 12 ] After nested for-loop:    1 1 1 2 
    

    根据逻辑,上一次迭代中嵌套的for循环将把[[1]]和[[2]]更新为1。

    cat("[",iter,"]","Before nested for-loop:\t", unlist(ds),"\n")
    # ds: 4 3 1 2
    for (i in order) {
        ds[axis_iter][[i]] <- ds[axis_iter][[i]] + 1 # at i=2 => ds: 4 4 1 2, at i=1 => ds: 5 1 1 2
        if (ds[axis_iter][[i]] <= d[i]) # condition not satisfied
          break
        else
          ds[axis_iter][[i]] <- 1  # at i=2 => ds: 4 1 1 2, at i=1 => ds: 1 1 1 2
    }
    cat("[",iter,"]","After nested for-loop:\t", unlist(ds),"\n")
    # ds: 1 1 1 2