0

我在应用具有嵌套 for 循环的函数时遇到问题,因此每个人和每个月都吐出数据值。目前,我可以使用 for 循环应用该函数,以便每月获取数据。

我使用的数据集和函数非常大,但我在下面创建了一些示例数据和示例函数。

structure(list(code = c("a", "a", "a", "a", "a", "a", "b", "b", 
"b", "b", "b", "b", "c", "c", "c", "c", "c", "c"), datetime = c("16/04/2016", 
"17/04/2016", "25/05/2016", "26/05/2016", "01/06/2016", "02/06/2016", 
"16/05/2016", "17/05/2016", "25/06/2016", "26/06/2016", "01/07/2016", 
"02/07/2016", "16/06/2016", "17/06/2016", "25/07/2016", "26/07/2016", 
"01/08/2016", "02/08/2016"), score = c(17L, 16L, 12L, 16L, 14L, 
2L, 1L, 10L, 13L, 12L, 0L, 7L, 17L, 8L, 15L, 20L, 0L, 4L), monthyear = c("2016/04", 
"2016/04", "2016/05", "2016/05", "2016/06", "2016/06", "2016/05", 
"2016/05", "2016/06", "2016/06", "2016/07", "2016/07", "2016/06", 
"2016/06", "2016/07", "2016/07", "2016/08", "2016/08")), class = "data.frame", row.names = c(NA, 
-18L))

month_list <- strftime(seq(as.Date("2016/04/01"), as.Date("2016/08/31"), by = "month"),format="%Y/%m")

test_func <- function(dat) {
 metrics <- dat %>% summarize(
    mean = mean(score, na.rm = TRUE), 
    sd = sd(score, na.rm = TRUE)) 
  metrics$code <- rep(first(dat$code), nrow(metrics))
  metrics$monthyear <- rep(first(dat$monthyear), nrow(metrics))
  return(metrics)
}


my_datalist = list()

for (i in month_list) {
  # define outputs of function
  my_datalist[[i]]  <- testdat %>%
    filter(monthyear== i) %>% 
    test_func
  # add outputs to empty datalist
}

my_metric_data = do.call(rbind, my_datalist)

#turn into dataframe
my_metric_data = do.call(rbind, my_datalist)

这将返回一行数据,我的月份列表中的每个月都有一个数据。我现在需要每月将此函数(test_func)应用于数据集中的每个人。所以我想我会构建一个嵌套的 for 循环,在其中我每月过滤数据,创建该月的个人(代码)列表。然后将该函数应用于该列表。

my_datalist = list()

for (i in month_list) {
  dat <-  df %>%
    filter(monthyear== i)
  
  code_list  <- as.character(unique(dat$code))
  
  for (j in code_list){
    my_datalist[[j]] <- dat %>% 
      filter(code == j) %>% 
      test_func
  }
}

my_metric_data <- do.call(rbind, my_datalist)

但是,当我检查输出时,它看起来只是将函数应用于第一个代码,而不是按代码每月返回数据。但我不确定它为什么这样做。我认为我需要潜在地使另一个空列表来填充,然后添加到第一个列表中,但我的尝试到目前为止还没有奏效。

4

2 回答 2

0

我的一位同事帮助我解决了这个问题,所以我想我会发布答案。

修复它的最简单方法可能是在运行循环之前设置一个索引计数器变量;

idx_cnt <- 1

然后在您的内部循环( j 之一)中,使用它来索引结果列表,然后添加 1 以便下一个结果进入下一个插槽。生成的代码如下所示。

datalist = list()
idx <- 1

for (i in month_list) {
  dat <-  dat %>%
    filter(monthyear== i)
  
  code_obs <- dat %>% 
    group_by(code) %>% 
    summarise(n = n()) %>% 
    filter(n >=20) %>% 
    ungroup()
  
  code_list  <- as.character(unique(code_obs$code))
  
  for (j in code_list){
    datalist [[idx]] <- dat %>% 
      filter(code == j) %>% 
      nodeMetrics_func
    idx <- idx + 1
  }
}
于 2021-04-13T08:05:30.523 回答
0

我们没有任何数据可以运行或验证解决方案,但您可以尝试这种split+lapply方法。

result <- do.call(rbind, lapply(split(GRS_filt, 
                  list(GRS_filt$monthyear, GRS_filt$code)), net_func))
于 2021-04-06T09:56:37.790 回答