You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

R语言循环处理时序文件:添加文件名列及代码问题排查

时序数据读取与处理代码排查

我有时序数据存储在月度文件夹下的日分子文件夹的txt文件中,已经通过R代码读取子文件夹下的txt文件并过滤掉无需分析的文件,但尝试循环读取文件(跳过14行)并添加文件名等列时未得到预期结果,请求排查代码缺失部分。

原代码

setwd(".../2018/Jan")
parent.folder <-".../2018/Jan"  
sub.folders <- list.dirs(parent.folder, recursive=TRUE)[-1] #To read the sub-folders under parent folder
r.scripts <- file.path(sub.folders)
A_2018 <- list()
for (j in seq_along(r.scripts)) {
  A_2018[[j]] <- dir(r.scripts[j],"\\.txt$")}
trim_to_two <- function(x) {
  runs = rle(gsub("^L1_\\d{4}_\\d{4}_","",x))
  return(cumsum(runs$lengths)[which(runs$lengths > 2)] * -1)
}

A_2018_new <- list()
for (j in seq_along(A_2018)) {
  A_2018_new[[j]] <- A_2018[[j]][trim_to_two(A_2018[[j]])]
  }
for (i in 1:length(A_2018_new)) {
  
  for (j in 1:length(A_2018_new[[i]])){
       
    filename <- paste(str_sub(A_2018_new[[i]][j], 1, 14))
        
    assign(filename, read_tsv(complete_file_name, skip = 14, col_names = FALSE), 
           )
    
    Y <- r.scripts %>% str_sub(46, 49)
    MD <- r.scripts %>% str_sub(58, 61)
    HM <- filename %>% str_sub(9, 12)
    Turn <- filename %>% str_sub(14, 14)
    time_minute <- paste(Y, MD, HM, sep="-")
    
    Map(cbind, filename, SampleID = names(filename))
    }
} 

代码问题排查与修正

  • 缺失文件完整路径变量:读取文件时使用的complete_file_name未定义,需要拼接子文件夹路径和当前文件名,否则R找不到要读取的文件。
  • assign未处理附加列:用assign创建的变量只是原始读取的数据,没有把Y、MD等附加信息合并进去,需要先读取数据到临时对象,再合并列后保存。
  • 硬编码路径索引易出错:str_sub(46,49)这类硬编码的索引是针对特定路径长度的,换个路径就会失效,应该从子文件夹名称提取日期信息,比如用basename()获取子文件夹名后再分割。
  • Map(cbind)用法错误:这里的Map没有作用到实际读取的数据上,也没有保存结果,应该直接对数据框执行cbind或mutate操作。
  • 零散变量不利于后续分析:用assign创建大量独立变量会导致环境混乱,推荐用列表统一存储所有处理后的数据,最后可合并为一个大的数据框。

修正后的代码示例

library(tidyverse)

# 设置根路径
parent.folder <- ".../2018/Jan"  
setwd(parent.folder)

# 获取所有日分子文件夹
sub.folders <- list.dirs(parent.folder, recursive = TRUE)[-1]

# 读取每个子文件夹下的txt文件列表
A_2018 <- map(sub.folders, ~ dir(.x, "\\.txt$"))

# 过滤文件的函数(调整索引逻辑,确保保留正确的文件)
trim_to_two <- function(x) {
  runs <- rle(gsub("^L1_\\d{4}_\\d{4}_","",x))
  # 标记需要剔除的索引,返回保留的索引
  exclude_indices <- cumsum(runs$lengths)[which(runs$lengths > 2)]
  keep_indices <- which(!seq_along(x) %in% exclude_indices)
  return(keep_indices)
}

# 应用过滤函数,得到待处理的文件列表
A_2018_new <- map(A_2018, ~ .x[trim_to_two(.x)])

# 初始化列表存储处理后的数据
processed_data <- list()
current_idx <- 1

# 循环处理每个子文件夹下的文件
for (i in seq_along(A_2018_new)) {
  current_subfolder <- sub.folders[i]
  # 从子文件夹名提取年月日(假设子文件夹名为"20180101"格式,可根据实际调整)
  folder_date <- basename(current_subfolder)
  year <- str_sub(folder_date, 1, 4)
  month_day <- str_sub(folder_date, 5, 8)
  
  # 处理当前子文件夹下的每个文件
  for (j in seq_along(A_2018_new[[i]])) {
    current_file <- A_2018_new[[i]][j]
    # 拼接文件完整路径
    file_full_path <- file.path(current_subfolder, current_file)
    
    # 读取文件,跳过前14行
    raw_data <- read_tsv(file_full_path, skip = 14, col_names = FALSE)
    
    # 从文件名提取信息
    filename_prefix <- str_sub(current_file, 1, 14)
    hour_minute <- str_sub(filename_prefix, 9, 12)
    turn <- str_sub(filename_prefix, 14, 14)
    time_minute <- paste(year, month_day, hour_minute, sep = "-")
    
    # 添加附加列到数据中
    processed_df <- raw_data %>%
      mutate(
        filename = current_file,
        SampleID = filename_prefix,
        year = year,
        month_day = month_day,
        hour_minute = hour_minute,
        turn = turn,
        time_minute = time_minute
      )
    
    # 将处理好的数据存入列表
    processed_data[[current_idx]] <- processed_df
    current_idx <- current_idx + 1
  }
}

# 可选:合并所有数据为一个大的数据框,方便后续分析
all_timedata <- bind_rows(processed_data)

内容的提问来源于stack exchange,提问作者Heiwa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.03 01:55:35