在C#中解析含WORK NUMBER的特定日志文件的方法咨询
C#解析特定格式日志文件的可行方案
针对你提供的日志格式,可通过分块解析+强类型对象映射的方式实现高效读取,以下是具体实现方案:
1. 定义数据模型
先创建对应日志结构的实体类,将日志数据映射为可操作的强类型对象:
public class WorkEntry { public DateTime Date { get; set; } public string WorkNumber { get; set; } public List<DataPoint> DataPoints { get; set; } = new List<DataPoint>(); } public class DataPoint { public int Series { get; set; } public double ZPos { get; set; } public double Focus0 { get; set; } public double Focus1 { get; set; } public double Focus2 { get; set; } public double Focus3 { get; set; } public double Focus4 { get; set; } }
2. 核心解析逻辑
步骤1:读取并预处理日志内容
读取日志文件所有行,过滤空行和无效行:
var allLines = File.ReadAllLines("your-log-file-path.txt") .Select(line => line.Trim()) .Where(line => !string.IsNullOrEmpty(line)) .ToList();
步骤2:分割独立的工作条目
日志中用大量下划线作为分隔线,以此分割每个WORK NUMBER对应的完整数据块:
var workEntryBlocks = new List<List<string>>(); var currentBlock = new List<string>(); foreach (var line in allLines) { // 判断是否为分隔线(由下划线组成) if (line.All(c => c == '_')) { if (currentBlock.Any()) { workEntryBlocks.Add(currentBlock); currentBlock = new List<string>(); } continue; } currentBlock.Add(line); } // 添加最后一个未被分隔线收尾的数据块 if (currentBlock.Any()) { workEntryBlocks.Add(currentBlock); }
步骤3:解析每个工作条目
遍历每个数据块,提取元数据(日期、工单号)和具体数据行:
var workEntries = new List<WorkEntry>(); foreach (var block in workEntryBlocks) { var workEntry = new WorkEntry(); bool isDataSection = false; foreach (var line in block) { // 提取日期信息 if (line.StartsWith("DATE:")) { var dateStr = line.Split(new[] { ':' }, 2)[1].Trim(); workEntry.Date = DateTime.Parse(dateStr); continue; } // 提取工单号 if (line.StartsWith("WORK NUMBER:")) { var workNumber = line.Split(new[] { ':' }, 2)[1].Trim(); workEntry.WorkNumber = workNumber; continue; } // 识别数据表头,后续行均为数据内容 if (line.StartsWith("SERIES")) { isDataSection = true; continue; } // 解析数据行 if (isDataSection) { var parts = line.Split(new[] { ' ' }, StringSplitOptions.RemoveEmptyEntries); if (parts.Length == 7) // 对应SERIES到FOCUS4共7列数据 { var dataPoint = new DataPoint { Series = int.Parse(parts[0]), ZPos = double.Parse(parts[1]), Focus0 = double.Parse(parts[2]), Focus1 = double.Parse(parts[3]), Focus2 = double.Parse(parts[4]), Focus3 = double.Parse(parts[5]), Focus4 = double.Parse(parts[6]) }; workEntry.DataPoints.Add(dataPoint); } } } if (!string.IsNullOrEmpty(workEntry.WorkNumber)) { workEntries.Add(workEntry); } }
3. 扩展优化建议
- 异常处理:添加
try-catch块处理日期/数值解析失败的情况,避免程序崩溃; - 性能优化:针对超大日志文件,改用
File.ReadLines逐行读取,减少内存占用; - 格式兼容:若日志分隔线格式有变化,可调整分隔线判断逻辑(比如判断是否包含连续下划线且长度超过阈值)。
内容的提问来源于stack exchange,提问作者zdenda809
相关产品推荐
相关产品推荐

