【问题标题】:Tokenizing & encoding dataset uses too much RAM标记和编码数据集使用太多 RAM
【发布时间】:2021-06-19 05:02:53
【问题描述】:

尝试对数据进行标记和编码以提供给神经网络。

我只有 25GB 的 RAM,每次我尝试运行以下代码时,我的 google colab 都会崩溃。知道如何防止他的发生吗? “您的会话在使用所有可用 RAM 后崩溃”

我认为标记/编码 50000 个句子的块会起作用,但不幸的是没有。 该代码适用于长度为 130 万的数据集。当前数据集长度为 500 万。

max_q_len = 128
max_a_len = 64    
trainq_list = train_q.tolist()    
batch_size = 50000
    
def batch_encode(text, max_seq_len):
      for i in range(0, len(trainq_list), batch_size):
        encoded_sent = tokenizer.batch_encode_plus(
            text,
            max_length = max_seq_len,
            pad_to_max_length=True,
            truncation=True,
            return_token_type_ids=False
        )
      return encoded_sent

    # tokenize and encode sequences in the training set
    tokensq_train = batch_encode(trainq_list, max_q_len)

tokenizer 来自 HuggingFace:

tokenizer = BertTokenizerFast.from_pretrained('bert-base-multilingual-uncased')

【问题讨论】:

    标签: python nlp pytorch huggingface-transformers huggingface-tokenizers


    【解决方案1】:

    无论大小,您都应该使用生成器并将数据传递给tokenizer.batch_encode_plus

    从概念上讲,是这样的:

    培训清单

    这可能包含从某些文件中读取的句子列表。如果这是一个大文件,您可以按照this answer 懒惰地读取输入的部分内容(最好一次读取batch_size 行):

    def read_in_chunks(file_object, chunk_size=1024):
        """Lazy function (generator) to read a file piece by piece.
        Default chunk size: 1k."""
        while True:
            data = file_object.read(chunk_size)
            if not data:
                break
            yield data
    

    否则打开单个文件(比内存小很多,因为使用 BERT 编码后会变大),如下所示:

    import pathlib
    
    
    def read_in_chunks(directory: pathlib.Path):
        # Use "*.txt" or any other extension your file might have
        for file in directory.glob("*"):
            with open(file, "r") as f:
                yield f.readlines()
    

    编码

    编码器应该使用这个生成器和yield 回编码部分,如下所示:

    # Generator should create lists useful for encoding
    def batch_encode(generator, max_seq_len):
        tokenizer = BertTokenizerFast.from_pretrained("bert-base-multilingual-uncased")
        for text in generator:
            yield tokenizer.batch_encode_plus(
                text,
                max_length=max_seq_len,
                pad_to_max_length=True,
                truncation=True,
                return_token_type_ids=False,
            )
    

    保存编码文件

    由于文件太大而无法放入 RAM 内存,您应该将它们保存到磁盘(或在生成时以某种方式使用)。

    类似的东西:

    import numpy as np
    
    
    # I assume np.arrays are created, adjust to PyTorch Tensors or anything if needed
    def save(encoding_generator):
        for i, encoded in enumerate(encoding_generator):
            np.save(str(i), encoded)
    

    【讨论】:

    • 太好了,谢谢!就我而言,file_object 已经是加载到笔记本中的 pandas df,这似乎使用的 RAM 不超过 1gb。所以,我需要编写一个生成器来使用这个 df 而不是 file_object?
    • @Exa 是的,接受这个df 并生成它的切片(比如64 示例,越多越好,但请记住RAM 限制),可能作为一个列表。
    • 好的,谢谢!您认为将标记化和编码移至训练循环是否有意义?因此,它不会像上面那样有一个单独的函数,而是包含在 run_training() 之类的东西中。
    • 一般使用很多小函数,更容易上手,所以我会拒绝。
    猜你喜欢
    • 2021-10-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2021-03-17
    • 2020-11-25
    • 2018-01-13
    • 2017-01-01
    相关资源
    最近更新 更多