Skip to content

算法

算法层是白皮书进入“可操作精度”的地方。它不引入新的产品面,而是把今天维护中的 stat / filter 能力解释清楚,让评审者在不立刻跳进源码的前提下,也能对正确性、吞吐和资源边界形成稳定判断。

过滤流水线

过滤路径被刻意设计成“聚焦且可组合”的执行链。当前 baseline 支持:

  • predicate:最小平均质量、最小长度、最大长度、最大 N 比例;
  • mutator:质量修剪、adapter trimming、polyG trimming、受控的 polyX trimming;
  • 单次遍历执行:让过滤与修剪在同一条处理链内完成,而不是为每一步反复重建输入流。

因此,过滤层的重点不是“罗列所有可能的预处理变换”,而是在保持记录合法性、序列/质量长度一致,以及吞吐可控的前提下,完成一条窄而清晰的 QC 处理路径。命令参数层面的细节请继续看 CLI 参考,阶段边界为什么这样划分则回到 架构

统计路径

统计路径的存在,是为了让 QC 决策保持可解释。stat 命令负责输出 summary metrics 与逐位点测量结果,而不只是一个“成功/失败”的终端状态。按照当前维护中的范围,这包括读段数量、长度分布、碱基组成、GC 含量,以及类似 Q20/Q30 的质量指标。

产品 baseline 还允许在默认文本报告之外输出轻量级 signature sidecar。需要强调的是:sidecar 只能作为附加材料,不能替代主报告契约。这一点也正是研究附录在比较报告型工具时会反复提到的边界。

执行模型

FastQTools 沿用架构层描述的同一套阶段模型:source → processing → sink。这背后的执行承诺可以概括为:

  1. reader 负责读取与批次形成;
  2. processing 阶段负责适合并发的过滤、修剪与统计工作;
  3. sink 负责有序输出、汇总写回与最终错误边界。

当前维护中的并发实现基于 oneTBB parallel_pipeline,但对读者来说,更关键的并不是“用了哪个库”,而是执行路径始终保持分阶段、可审查、且资源有界。于是,性能证据与实现行为可以沿着同一套模型被解释,而不会出现“快的时候一套说法、正确的时候另一套说法”。

内存约束

内存策略之所以属于算法层,是因为吞吐故事本身就依赖它。FastqBatch 为记录数据提供连续存储,记录字段则在批次生命周期内以 std::string_view 视图暴露出来。这样可以减少无谓复制,但也带来一条硬约束:视图绝不能逃逸出所属批次的生命周期。

RFC-0004 描述的对象池策略,正是为了控制分配抖动并保持 in-flight 内存有界。因此,内存不是性能页最后顺手提一下的话题,而是维护中的执行约束之一。

正确性不变量

算法层应该用不变量来评审,而不能只看吞吐:

不变量为什么重要
FASTQ 记录保持四行逻辑单元。如果记录结构变得含混,解析再快也没有意义。
mutation 后 sequence 与 quality 长度仍然一致。过滤与修剪不能产出无效 FASTQ。
同一输入与配置下 predicate 决策保持确定性。可复现 QC 比机会性的并行顺序更重要。
批次视图不能逃逸出所属存储。零拷贝只有在生命周期纪律明确时才安全。
signature sidecar 只能作为附加输出。可选 QC 摘要不能替代默认 stat 报告契约。

接下来去哪里验证

MIT License © LessUp