Files
WCTDataMiner/docs/architecture/parser/Qfod解析器.md
ssss 28cb2533a7 docs: 完善数据模型设计
- 重命名 log_file 为 test_scenario(测试场景)
- 拆分维度表:tx_panel、tx_hardware、tx_software、rx_type
- 采用星型模型设计,消除数据冗余
- 为所有表添加软删除字段 is_deleted
- 更新关系说明,包含全局查询过滤器配置
- 更新 ER 图和查询示例

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-07-02 15:53:30 +08:00

120 lines
3.1 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Qfod 解析器
> 所属模块:[解析器设计](./概览.md)
---
## 1. 日志格式
**格式:** `X#:Q A->B C D E`
**示例:** `0#:Q 1->25 45.5 20.5 2`
---
## 2. 字段定义
| 字段标识 | 字段名称 | 数据类型 | 取值范围 | 说明 |
|----------|----------|----------|----------|------|
| X | ChargerIndex | byte | 0, 1 | 充电器索引 |
| A | CoilIndex | byte | 0, 1, 2 | 线圈索引 |
| B | DeltaQ | int | - | Q值变化量ΔQ = CurrentQ - RawQ |
| C | CurrentQ | float | - | 当前实时Q值 |
| D | RawQ | float | - | 原始Q值 |
| E | FodType | byte | 见Table 2 | 异物类型编码 |
---
## 3. 正则表达式
```csharp
// Parsers/QfodParser.cs
private static readonly Regex QfodPattern = new(
@"^(\d)#:Q\s+(\d+)->(-?\d+)\s+([-\d.]+)\s+([-\d.]+)\s+(\d+)$",
RegexOptions.Compiled
);
```
**捕获组映射:**
| 捕获组 | 字段 | 类型转换 |
|--------|------|----------|
| Group 1 | ChargerIndex | byte.Parse() |
| Group 2 | CoilIndex | byte.Parse() |
| Group 3 | DeltaQ | int.Parse() |
| Group 4 | CurrentQ | float.Parse() |
| Group 5 | RawQ | float.Parse() |
| Group 6 | FodType | byte.Parse() |
---
## 4. 解析器实现
```csharp
// Parsers/QfodParser.cs
using System.Text.RegularExpressions;
using WCTDataMiner.Models;
namespace WCTDataMiner.Parsers;
public class QfodParser : IParser<QfodRecord>
{
private static readonly Regex QfodPattern = new(
@"^(\d)#:Q\s+(\d+)->(-?\d+)\s+([-\d.]+)\s+([-\d.]+)\s+(\d+)$",
RegexOptions.Compiled
);
public bool CanParse(string line) => QfodPattern.IsMatch(line);
public ParseResult<QfodRecord> Parse(string line, int lineNumber, Guid logFileId)
{
var match = QfodPattern.Match(line);
if (!match.Success)
{
return ParseResult<QfodRecord>.Failure(
"FORMAT_MISMATCH",
"Line does not match Qfod pattern"
);
}
try
{
var record = new QfodRecord
{
LogFileId = logFileId,
LineNumber = lineNumber,
ChargerIndex = byte.Parse(match.Groups[1].Value),
CoilIndex = byte.Parse(match.Groups[2].Value),
DeltaQ = int.Parse(match.Groups[3].Value),
CurrentQ = float.Parse(match.Groups[4].Value),
RawQ = float.Parse(match.Groups[5].Value),
FodType = byte.Parse(match.Groups[6].Value)
};
return ParseResult<QfodRecord>.Success(record);
}
catch (Exception ex)
{
return ParseResult<QfodRecord>.Failure(
"TYPE_CONVERSION",
$"Failed to convert field: {ex.Message}"
);
}
}
}
```
---
## 5. 检测通道组合
`ChargerIndex + CoilIndex` 组合唯一标识一个检测通道:
| ChargerIndex | CoilIndex | 检测通道 |
|--------------|-----------|----------|
| 0 | 0 | 充电器0 线圈0 |
| 0 | 1 | 充电器0 线圈1 |
| 0 | 2 | 充电器0 线圈2 |
| 1 | 0 | 充电器1 线圈0 |
| 1 | 1 | 充电器1 线圈1 |
| 1 | 2 | 充电器1 线圈2 |