【transformers】基于transformers包训练新分词器,用nohup执行不记录进度条的问题

627 阅读2分钟

问题:

基于transformers教程写的分词器训练代码,直接运行在分词器训练阶段会有进度条打印 ,但是debug、或是在linux上通过nohup命令写入文件没有进度条。

解决方案

暂无

结论

transformers调用tokenizerstokenizers部分代码由rust编写,rust进度条的实现不支持nohup。所以最终rust部分的代码没有进度条显示

解决过程

Python&Rust

初步的想法是通过debug,找到训练的逻辑,然而,训练代码的位置只有.pyi文件,该文件用于应付代码静态检查,并没有实际代码,实际执行的是编译好的rust代码。

tokenizers包是一个pythonrust语言融合的包,python调用build后的rusthuggingface/tokenizers

初步的怀疑是 调用rust后,等于新启了一个进程,所以输出在另一个进程里,nohup不会记录令起的进程的结果

勘误:经过JAVA同事的教导,主线程里调用的rust,依然在主线程里(MainThread

经过测试怀疑是错的

from concurrent.futures import ThreadPoolExecutor, ProcessPoolExecutor

executor = ProcessPoolExecutor()


def submit():
    print('2')


if __name__ == '__main__':
    print('1')
    executor.submit(submit)
    print('3')

即使使用nohup执行上述代码,文件里依然会写入1\n3\n2

Rust

接下来只能从rust代码部分找问题

阅读了tokenizers包源码,其自己实现,未借助sentencepiece实现。

首先找到关于进度条的代码

以BPE训练为例,关于进度条的定义在tokenizers/src/models/bpe/trainer.rs文件的impl BpeTrainer > setup_progress()函数中,基于tokenizers/src/utils/progress.rs

根据推测,该进度条的打印仅为终端的功能,nohup不是终端,然后想去issue搜一下问题,最后在源码的readme.md找到答案。

**progressbar**: The progress bar visualization is enabled by default. It might be disabled if compilation for certain targets is not supported by the [termios](https://crates.io/crates/termios) dependency of the [indicatif](https://crates.io/crates/indicatif) progress bar.

附上进度条实现:indicatif - Rust (docs.rs)

最后再验证一下吧

以下内容针对rust小白

  1. rust官网下载安装rustup(cargo),并按照官网指引改好代码
use indicatif::ProgressBar;


fn main() {
    println!("Hello, world!");
    let bar = ProgressBar::new(1000);
    for _ in 0..1000 {
        bar.inc(1);
        // ...
    }
    bar.finish();
}
  1. 修改镜像源
  2. cargo add termios
  3. cargo run

发现进度条正常打印,接下来再使用nohup试试:

$ nohup cargo run &
[1] 29447
$ nohup: 忽略输入并把输出追加到"nohup.out"
[1]+  完成                  nohup cargo run
$ cat nohup.out
    Finished dev [unoptimized + debuginfo] target(s) in 0.01s
     Running `target/debug/hello-rust`
Hello, world!
$ cargo run
    Finished dev [unoptimized + debuginfo] target(s) in 0.01s
     Running `target/debug/hello-rust`
Hello, world!
██████████████████████████████████████████████████████████████████████████████ 1000/1000

可以发现问题确实由这里引起,但是还没有找到解决方案。

google/sentencepiece

sentencepiece包只提供了*_pb2.py文件,底层实现还是C++