Skip to content

neuralnet.cpp v1.13.0 — 多仓拆分

Choose a tag to compare

@EthanPeng-2048 EthanPeng-2048 released this 25 Oct 22:19
· 82 commits to main since this release

neuralnet.cpp v1.13.0 Release Notes

发布范围:v1.12.0(tag v1.12.0)→ v1.13.0(tag v1.13.0)。
主题:多仓拆分——把 core / threadpool / kvrecord / dataset / tokenizer 拆为
5 个独立子仓(neuralnet-cpp-dev org 下 *.neuralnet.cpp),门面仓 neuralnet.cpp
经 submodule 引用;各子仓可被独立复用。
兼容性:下游 #include <neuralnet.cpp/xxx.hpp> 路径零变化(子仓头统一在
<repo>/include/neuralnet.cpp/ 下,文件名不冲突,经 include path 透明解析)。
唯一操作性变更:克隆/嵌入本库时必须递归初始化 submodule(见 §3 迁移指南)。


1. 主题与定位

v1.13.0 是一次结构性重构,不改 API 语义、不改模型/数据文件格式、不改 CLI。目标:

  • 独立复用:线程池、分词器、KV 容器等通用组件各自成仓,下游可单独引入,不必拉整个引擎;
  • 编译边界:纯常量消费方(如只用 Scalar/BLOCK_SIZE)不再传递拉入线程池;
  • 门面保留:neuralnet.cpp 仍是唯一聚合入口(nn.hpp),编排层(algebra / compute /
    engine / model / train / rl / dataset_samples)留在门面。

依赖 DAG(箭头 = 依赖方向):

base.neuralnet.cpp            (无依赖;Result/断言/精度/常量/文件 I/O/sha256)
   ├─ threadpool.neuralnet.cpp (线程池 + 并行算法)
   ├─ kvrecord.neuralnet.cpp   (自描述二进制 KV 容器)
   │      └─ dataset.neuralnet.cpp   (.nndataset/.nnvocab 格式 I/O)
   └─ tokenizer.neuralnet.cpp  (BPE / CharBPE;依赖上述全部)
neuralnet.cpp                 (门面;依赖全部子仓)

2. 新增能力

2.1 五个可独立复用的子仓

仓名 内容 依赖
base.neuralnet.cpp Result<T>/NN_FAIL/NN_TRY、断言、精度类型、编译期常量、文件 I/O、SHA-256 无
threadpool.neuralnet.cpp ThreadPool/global_thread_pool() + nn::for_each/transform/transform_reduce/parallel_for_* base
kvrecord.neuralnet.cpp KeyValueRecord(v1 内联 + v2 地址布局,版本自举,前向兼容) base
dataset.neuralnet.cpp .nndataset/.nnvocab 格式常量 + Dataset/TextCorpus base + kvrecord
tokenizer.neuralnet.cpp BPETokenizer/CharBPETokenizer + make_tokenizer base + threadpool + kvrecord + dataset

各仓均为 header-only,提供 CMake INTERFACE 目标(neuralnet::base / ::threadpool /
::kvrecord / ::dataset / ::tokenizer),独立编译与端到端消费均已验证。

2.2 编译边界收敛

  • core_config.hpp 瘦身为纯常量叶子头(202 → 78 行),不再依赖 core_threadpool.hpp;
    5 个并行包装函数移入新头 core_parallel.hpp。
  • 效果:core_config/lr_scheduler/train_state/text_train_config/expr_spec/core_env
    等纯常量消费方不再传递拉入线程池。
  • nn.hpp 单 TU 编译实测 14.4s → 11.5s。

3. 迁移指南(唯一操作性变更)

子仓以嵌套 submodule 位于门面仓 extern/。无论克隆还是嵌入,都必须把子仓一并取到,
否则 extern/*/include 为空、编译时报 neuralnet.cpp/core_errors.hpp 等头找不到。

# 克隆
git clone --recurse-submodules git@github.com:neuralnet-cpp-dev/neuralnet.cpp.git
# 已 clone 但漏了子仓
git submodule update --init --recursive
  • add_subdirectory 嵌入:同上,保证 3rd_party/neuralnet.cpp/extern/ 下子仓已初始化。
  • FetchContent 嵌入:CMake ≥ 3.17 默认递归拉取嵌套 submodule;更旧或被关闭时需在
    FetchContent_MakeAvailable 后手动 git submodule update --init --recursive。

源码侧 include 写法不变:#include <neuralnet.cpp/nn.hpp> 及单头引用均照旧。

4. 破坏性变更

  • 无 API / CLI / 文件格式变更。
  • 构建侧:如 §3,需递归初始化 submodule。这是本次唯一的破坏性操作点。
  • 本地 include/neuralnet.cpp/ 删除了已搬走的 15 个头(core×10、kvrec、dataset×2、
    tokenizer×4,详见 git 历史),但这些头经子仓 include path 仍以相同路径可用。

5. 验收基线

  • 门面 nn.hpp 全量编译通过;核心 app(mnist/text/tokenizer/dataset)编译通过。
  • kvrec/tokenizer/train_state/dataset 测试全绿。
  • 下游 go.neuralnet.cpp(submodule 引用本库)在拆分后递归初始化下端到端编译通过。
  • 已知与拆分无关的既有失败:t1_58_test / write_epoch_test(引用尚未实现的
    nn::PrecisionSet/nn::Linear,拆分前 commit 5c03956 上同样失败)。

6. 子仓版本策略

门面 v1.13.0 tag 钉住 5 个子仓的确切 commit(经 submodule gitlink)。子仓独立演进时,
门面通过更新 submodule 指针引入;各子仓的 include/neuralnet.cpp/ 前缀在生态内统一,
#include <neuralnet.cpp/xxx.hpp> 跨仓透明。