在R中将228×228数据框按6×6块分割为列表的问题
解决DataFrame分割为6×6子集列表的问题
你的需求很清晰:把228×228的DataFrame按6行6列的规则分割成所有不重叠的子块,最终得到长度为38×38=1444的列表。先拆解下你原代码里的几个核心问题:
- 索引语法错误:
i:i+5会被R解析为(i:i) + 5,这不是你想要的连续6行区间,正确的写法应该是i:(i+5),列索引同理需要写成j:(j+5)。 - 循环赋值逻辑错误:内层循环每次迭代都会覆盖变量
a的值,最后外层循环只把内层循环最后一次生成的a赋值给mylist[[i]],导致最终列表只有38个元素(对应行块数量),远达不到1444个的要求。 - 列表索引错误:用
i作为列表的索引时,i是1,7,13,...223这类间隔值,会导致列表出现大量空缺,同时元素数量完全不符合预期。
修正后的嵌套循环解法
我们可以用一个计数器来追踪列表的当前位置,在嵌套循环里逐个添加每个6×6的子块:
# 生成测试数据 df <- data.frame(replicate(228, sample(0:234, 228, rep=TRUE))) # 生成行/列的起始索引(每6个一组) block_starts <- seq(1, nrow(df), 6) mylist <- list() counter <- 1 # 用来记录列表的当前插入位置 for(i in block_starts) { for(j in block_starts) { # 提取6×6的子块,注意索引的正确写法 sub_df <- df[i:(i+5), j:(j+5)] mylist[[counter]] <- sub_df counter <- counter + 1 } } # 验证列表长度 length(mylist) # 应该返回1444,符合要求
更简洁的向量化解法(用purrr包)
如果你熟悉purrr包,可以用expand.grid生成所有行块和列块的起始位置组合,再用map2批量提取子块,代码更简洁直观:
library(purrr) df <- data.frame(replicate(228, sample(0:234, 228, rep=TRUE))) block_starts <- seq(1, nrow(df), 6) # 生成所有行起始和列起始的组合(共38×38=1444组) block_combinations <- expand.grid(row_start = block_starts, col_start = block_starts) # 批量提取每个组合对应的6×6子块 mylist <- map2(block_combinations$row_start, block_combinations$col_start, function(r, c) df[r:(r+5), c:(c+5)]) length(mylist) # 返回1444,符合需求
子块正确性验证
你可以检查列表的关键元素确认结果:
mylist[[1]]对应df[1:6,1:6]mylist[[2]]对应df[1:6,7:12]- 最后一个元素
mylist[[1444]]对应df[223:228,223:228],完全匹配你的预期。
内容的提问来源于stack exchange,提问作者Milaa
相关产品推荐
相关产品推荐

