【技术专题】AI大模型应用开发入门-拥抱Hugging Face与Transformers生态 - 使用Transformers加载预训练模型

75 阅读29分钟

大家好,我是锋哥。最近连载更新《AI大模型应用开发入门-拥抱Hugging Face与Transformers生态》技术专题。

QQ截图20260117190029.jpg 本课程主要介绍和讲解Hugging Face和Transformers,包括加载预训练模型,自定义数据集,模型推理,模型微调,模型性能评估等。是AI大模型应用开发的入门必备知识。 同时也配套视频教程《2027版 AI大模型应用开发入门-拥抱Hugging Face与Transformers生态 视频教程(无废话版) 玩命更新中~》

cuda,cudnn,Pytorch安装

我们用Pytorch运行深度学习项目,可用cpu,也可以用gpu加速。有些垂直的大模型或者是图片训练,用cpu很慢。所以我们后面学习AI大模型,都采用gpu加速训练和调用。

首先第一步,我们看下自己电脑是否有英伟达显卡,

我们可以进入任务管理器,选择性能,最底部,可以看到GPU,以及右侧可以看到显卡版本,底部可以看到显存信息。

image.png

前面我们学习过Pytorch深度学习库,这里不做多解释。

我们先来安装下cuda,

CUDA(Compute Unified Device Architecture)是由NVIDIA开发的一种并行计算架构,旨在利用NVIDIA GPU的强大计算能力来进行通用计算。它提供了一系列的开发工具、库和API,使得开发者能够在NVIDIA硬件上创建高性能的计算密集型应用程序。CUDA让开发者能够编写使用C、C++和Fortran等编程语言的代码,这些代码可以在GPU上高效运行,从而加速计算密集型任务,比如科学计算、图像处理、深度学习等。

首先,我们需要查看系统支持的最高CUDA版本。在命令行中输入nvidia-smi,查看结果中的CUDA版本信息。

image.png

我这边显示的是12.6

我们去 developer.nvidia.com/cuda-toolki… 网址 下载对应的CUDA版本

image.png

下载后,默认安装即可。

接下来我们安装下cudnn

cuDNN(CUDA Deep Neural Network library)是NVIDIA为深度学习应用提供的高性能库。它作为CUDA的一个深度学习扩展,专门针对深度神经网络的训练和推理进行了优化。cuDNN利用GPU的并行处理能力,提供了多种深度学习中常用的操作,如卷积、池化、激活函数和归一化等。

我们去 developer.nvidia.com/rdp/cudnn-a… 这里下载对应CUDA的cudnn。

image.png

CUDA默认安装路径是:C:\Program Files\NVIDIA GPU Computing Toolkit\CUDA\v12.6

image.png

我们把下载后的cudnn解压:

image.png

把bin,include,lib下的具体内容复制到CUDA目录下的bin,include,lib下即可。

最后我们安装下Pytorch,这里需要特别注意的是,我们安装的支持指定版本CUDA的PyTorch库。

打开 pytorch.org/get-started… 网址:

image.png

选择好CUDA版本,最下面自动给我们构建好安装命令:

pip install torch torchvision --index-url https://download.pytorch.org/whl/cu126

测试下是否安装成功:

import torch
print(torch.cuda.is_available())

如果返回True就表示安装成功,如果返回False,说明安装失败,建议重点检查版本匹配。

加载和使用预训练模型实例

我们第一个helloWorld示例,用下经典的Google-Bert大模型。

Google BERT(Bidirectional Encoder Representations from Transformers)是谷歌于2018年发布的开源自然语言处理(NLP)预训练模型,标志着NLP领域进入预训练模型的新时代。

BERT的核心突破在于双向上下文理解。与传统语言模型仅从左到右或从右到左进行预测不同,BERT通过Transformer编码器结构,同时利用句子前后所有词语的信息进行训练。这种双向性使其能更精准捕捉语言的复杂语义和上下文关联。

BERT采用两项关键预训练任务:掩码语言模型(MLM) 随机遮盖部分词语让模型预测,以及下一句预测(NSP) 判断两个句子是否连续。通过在海量文本上预训练后,只需针对特定任务(如文本分类、问答、情感分析)进行微调,即可获得卓越性能。

BERT开源后迅速成为NLP领域的基石模型,催生了ALBERT、RoBERTa等众多改进模型,并广泛应用于搜索引擎、智能客服、机器翻译等场景,显著提升了机器理解人类语言的能力。

下载地址:

https://huggingface.co/google-bert/bert-base-chinese

安装transformers库。

pip install transformers -i http://mirrors.aliyun.com/pypi/simple/   --trusted-host mirrors.aliyun.com

Transformers Pipeline 是 Hugging Face 提供的一个高层次的 API,旨在简化使用预训练的 Transformer 模型进行各种自然语言处理(NLP)任务。这个工具使得开发者可以方便地加载、配置和使用各种模型,以完成文本分类、文本生成、命名实体识别(NER)、翻译等任务。以下是对 Transformers Pipeline 的详细介绍:

  1. 基本概念
  • Pipeline的作用:Pipeline 提供了一种简单的接口,用于快速执行常见的 NLP 任务。用户只需调用相应的任务函数,不需要深入理解模型的底层实现细节。
  1. 支持的任务

Transformers 提供的 Pipeline 可以用于多种 NLP 任务,包括但不限于:

  • 文本分类(Text Classification) :例如情感分析,给定一段文本,判断其情感倾向(积极、消极等)。
  • 命名实体识别(Named Entity Recognition,NER) :识别文本中的特定实体,如人名、地名、组织名等。
  • 问答(Question Answering) :给定上下文和问题,模型返回问题的答案。
  • 文本生成(Text Generation) :生成连续的文本,例如基于某些输入文本生成合理的后续内容。
  • 翻译(Translation) :将文本从一种语言翻译为另一种语言。
  • 摘要(Summarization) :生成给定长文本的简短摘要。

示例代码:

from transformers import pipeline
​
# 情感分析任务
def test_classfication():
    # 1,下载模型 https://huggingface.co/google-bert/bert-base-chinese
​
    # 2,创建模型,通过 pipeline 函数
    model = pipeline(
        task='text-classification',  # 任务类型
        model='./Bert-base-chinese',  # 模型
        device=0  # GPU 设备索引
    )
​
    # 3,调用模型,返回输出结果
    result = model('今天天气不错')
    print(result)
​
​
if __name__ == '__main__':
    test_classfication()

运行输出:

image.png

在 Hugging Face 的 Transformers 库中,pipeline 方法用于简化模型的使用,使用户能够轻松地执行各种自然语言处理任务。这个方法的参数允许用户根据不同的需求配置和使用模型。以下是 pipeline 方法主要参数的简介:

  1. task
  • 类型str
  • 描述:指定要执行的任务类型,例如 "sentiment-analysis""text-classification""translation""question-answering" 等。
  • 示例pipeline("sentiment-analysis")
  1. model
  • 类型strPreTrainedModel
  • 描述:指定要加载的模型名称或路径。可以使用 Hugging Face 模型库中的模型名称,也可以指向本地保存的模型路径。
  • 示例pipeline("translation", model="Helsinki-NLP/opus-mt-en-fr")
  1. tokenizer
  • 类型strPreTrainedTokenizer
  • 描述:指定要使用的分词器名称或路径。通常,如果模型和 tokenizer 是配套的,可以省略此参数,默认会自动加载合适的 tokenizer。
  • 示例pipeline("text-classification", model="dbmdz/distilbert-base-uncased-finetuned-sst-2-english", tokenizer="dbmdz/distilbert-base-uncased-finetuned-sst-2-english")
  1. config
  • 类型strPretrainedConfig
  • 描述:指定模型配置的名称或路径。通常情况下,除非需要特别定制模型的行为,否则可以省略此参数。
  • 示例pipeline("ner", model="bert-base-uncased", config="path/to/config.json")
  1. device
  • 类型int
  • 描述:指定要使用的计算设备。可以用于选择 CPU(-1)或 GPU(一般为 0,1,2 等)。例如,如果有多个 GPU,可以指定使用哪一个。
  • 示例pipeline("text-classification", model="model-name", device=0)(使用第一个 GPU)
  1. revision
  • 类型str
  • 描述:指定模型的特定版本,例如分支或标签等。如果不特别指定,将默认加载最新版本。
  • 示例pipeline("sentiment-analysis", model="model-name", revision="specific-branch-or-tag")
  1. use_auth_tokens
  • 类型boolstr
  • 描述:在访问某些需要授权的模型时,可以通过设置这个参数来使用 Hugging Face 的认证令牌。可以设置为 True,使得会自动使用 Hugging Face 的令牌;或者提供具体的认证令牌。
  • 示例pipeline("text-classification", model="model-name", use_auth_token=True)
  1. return_all_logits
  • 类型bool
  • 描述:是否返回所有类别的 logits,通常对多分类任务很有用。默认值为 False,即只返回预测的标签。
  • 示例pipeline("text-classification", model="model-name", return_all_logits=True)
  1. kwargs
  • 类型Any
  • 描述:可以传递其他模型具体支持的参数,根据不同的任务可能会有不同的可选参数。
  • 示例:使用模型特定的参数例如 top_kmax_length 等。
task (`str`):
            The task defining which pipeline will be returned. Currently accepted tasks are:
​
            - `"audio-classification"`: will return a [`AudioClassificationPipeline`].
            - `"automatic-speech-recognition"`: will return a [`AutomaticSpeechRecognitionPipeline`].
            - `"depth-estimation"`: will return a [`DepthEstimationPipeline`].
            - `"document-question-answering"`: will return a [`DocumentQuestionAnsweringPipeline`].
            - `"feature-extraction"`: will return a [`FeatureExtractionPipeline`].
            - `"fill-mask"`: will return a [`FillMaskPipeline`]:.
            - `"image-classification"`: will return a [`ImageClassificationPipeline`].
            - `"image-feature-extraction"`: will return an [`ImageFeatureExtractionPipeline`].
            - `"image-segmentation"`: will return a [`ImageSegmentationPipeline`].
            - `"image-text-to-text"`: will return a [`ImageTextToTextPipeline`].
            - `"image-to-image"`: will return a [`ImageToImagePipeline`].
            - `"image-to-text"`: will return a [`ImageToTextPipeline`].
            - `"keypoint-matching"`: will return a [`KeypointMatchingPipeline`].
            - `"mask-generation"`: will return a [`MaskGenerationPipeline`].
            - `"object-detection"`: will return a [`ObjectDetectionPipeline`].
            - `"question-answering"`: will return a [`QuestionAnsweringPipeline`].
            - `"summarization"`: will return a [`SummarizationPipeline`].
            - `"table-question-answering"`: will return a [`TableQuestionAnsweringPipeline`].
            - `"text2text-generation"`: will return a [`Text2TextGenerationPipeline`].
            - `"text-classification"` (alias `"sentiment-analysis"` available): will return a
              [`TextClassificationPipeline`].
            - `"text-generation"`: will return a [`TextGenerationPipeline`]:.
            - `"text-to-audio"` (alias `"text-to-speech"` available): will return a [`TextToAudioPipeline`]:.
            - `"token-classification"` (alias `"ner"` available): will return a [`TokenClassificationPipeline`].
            - `"translation"`: will return a [`TranslationPipeline`].
            - `"translation_xx_to_yy"`: will return a [`TranslationPipeline`].
            - `"video-classification"`: will return a [`VideoClassificationPipeline`].
            - `"visual-question-answering"`: will return a [`VisualQuestionAnsweringPipeline`].
            - `"zero-shot-classification"`: will return a [`ZeroShotClassificationPipeline`].
            - `"zero-shot-image-classification"`: will return a [`ZeroShotImageClassificationPipeline`].
            - `"zero-shot-audio-classification"`: will return a [`ZeroShotAudioClassificationPipeline`].
            - `"zero-shot-object-detection"`: will return a [`ZeroShotObjectDetectionPipeline`].

在 Hugging Face 的 Transformers 库中,pipeline 方法支持多种自然语言处理(NLP)任务。这些任务涵盖了文本处理的多个方面,适合于不同的应用场景。以下是一些常见的任务及其简要描述:

  1. 文本分类(Text Classification)
  • 描述:将输入文本分配到一个或多个类别。
  • 示例:情感分析(判断一段文字是积极、消极或中性)。
pythonpipeline("text-classification")

2. 情感分析(Sentiment Analysis)

  • 描述:专门的文本分类,用于判断文本的情绪倾向。
  • 示例:判断一条评论是正面的、负面的还是中性的。
pythonpipeline("sentiment-analysis")

3. 命名实体识别(Named Entity Recognition, NER)

  • 描述:识别文本中具有特定意义的实体,如人名、地点、组织名等。
  • 示例:在句子 “Apple是一家科技公司” 中识别出 “Apple” 是一个组织实体。
pythonpipeline("ner")

4. 问答(Question Answering)

  • 描述:给定一个上下文和一个问题,模型返回上下文中的答案。
  • 示例:在给定文本中回答特定的问题。
pythonpipeline("question-answering")

5. 文本生成(Text Generation)

  • 描述:基于输入文本生成一个或多个后续文本段落。
  • 示例:给定一段文本生成完整的故事或段落。
pythonpipeline("text-generation")

6. 机器翻译(Translation)

  • 描述:将输入的文本从一种语言翻译成另一种语言。
  • 示例:将英语转换为法语,或将中文转换为英文。
pythonpipeline("translation-en-to-fr")  # 英语到法语

7. 摘要(Summarization)

  • 描述:为给定的长文本生成一个简短的摘要。
  • 示例:从一篇文章中提取出其关键点。
pythonpipeline("summarization")

8. 文本填空(Fill-Mask)

  • 描述:在给定的上下文中,预测被遮住的单词或短语。
  • 示例:在句子 "我喜欢吃[MASK]" 中预测被遮住的部分。
pythonpipeline("fill-mask")

9. 句子相似度(Sentence Similarity)

  • 描述:比较两个句子的相似度,通常用于语义匹配等任务。
  • 示例:判断两条句子是否表达相似的意思。
pythonpipeline("text-similarity")  # 请注意,这个任务的具体实现可能取决于模型。

10. 多模态任务(如图像标注、图像分类等)

  • 描述:处理图像与文本结合的任务(需特定模型支持)。
  • 示例:图像分类,或者图像生成描述。
pythonpipeline("image-classification")  # 图像分类,使用相关模型

11. 自定义任务

  • 描述:根据需要自定义特定的 NLP 任务,通常需要使用自定义模型。
pipeline("custom-task")

预训练模型结构文件介绍

image.png

  1. .gitattributes

这是一个 Git 配置文件,用于指定如何处理储存在 Git 仓库中的不同类型的文件。它可以定义文本文件的换行符、文件合并策略,以及某些文件在 Git 操作中的特殊处理方式(例如,指示某些文件使用特定的 diff 工具)。在机器学习项目中,使用 .gitattributes 文件可以确保项目在多平台上具有一致性。

  1. README.md

这是一个 Markdown 格式的文档,通常用于描述项目的目的、功能、安装说明和使用方法。它是开源项目的"介绍性文档",提供给用户和开发者了解项目的重要信息。良好的 README 文件可以大大增加用户的使用体验和项目的可访问性。

  1. config.json

这个文件通常包含模型的配置参数,比如模型的架构、超参数(如学习率、batch size)和训练细节。该文件为模型的加载和初始化提供了必要的信息,使得在不同平台或环境间共享模型变得更加容易。

  1. flax_model.msgpack

这个文件是使用 Flax 库(一个用于构建神经网络的库,基于 JAX)保存的模型。在机器学习中,使用特定格式(如 msgpack)保存模型可以有效地进行序列化和反序列化,以便在不同的脚本或机器之间共享和加载。

  1. model.safetensors

这是针对模型权重的保存格式,它通常用来在安全和效率之间取得良好平衡。safetensors格式避免了一些常见的安全问题,特别是在加载未验证的模型时。它旨在提升安全性,同时仍然保持高效的存储性能。

  1. pytorch_model.bin

这是 PyTorch 框架中常见的模型权重文件,采用二进制格式存储模型的权重与参数。它是通过调用 model.save_pretrained() 方法生成的,通常与 PyTorch 的 transformers 库一起使用,便于模型在不同的应用中共享和加载。

  1. tf_model.h5

这是 TensorFlow 框架中的模型保存文件,通常使用 HDF5 文件格式,对应于使用 TensorFlow/Keras 框架训练生成的模型。HDF5 是一种用于高效存储大型数据集的格式,.h5 文件可用于保存模型的权重、训练配置以及优化器状态等信息。

  1. tokenizer.json

这个文件通常存储了与特定文本处理和模型输入相关的分词器(tokenizer)配置信息。它包含了分词器如何将原始文本转换为模型可以理解的输入格式的信息,例如词汇表(vocabulary)和编码方式。该文件有助于确保输入的正确预处理。

  1. Update tokenizer.json

这个文件显然是一个临时或附加的配置文件,可能是为了更新现有的分词器或添加新的词汇。具体内容和功能依赖于项目的实际操作。

  1. tokenizer_config.json

这个文件包含有关分词器的配置信息,比如使用的分词算法类型(BPE、WordPiece等),以及特殊标记(如填充标记和开始/结束标记)。它在加载分词器时提供了必要的上下文,以确保分词器的正确运行。

  1. vocab.txt

这个文件通常存储模型使用的词汇表。分词器会使用这个文本文件中的信息来识别和映射特定的单词或标记。词汇表是训练模型时的重要部分,因为它可以直接影响模型的性能和生成的文本的质量。

总结

以上文件共同构成了一个深度学习模型和分词器的完整定义及其配置,是在机器学习和 NLP 项目中不可或缺的组成部分。在模型的开发和部署过程中,正确管理和使用这些文件,对于确保模型的复现性、可重用性以及性能至关重要。

config.json

{
  "architectures": [
    "BertForMaskedLM"
  ],
  "attention_probs_dropout_prob": 0.1,
  "directionality": "bidi",
  "hidden_act": "gelu",
  "hidden_dropout_prob": 0.1,
  "hidden_size": 768,
  "initializer_range": 0.02,
  "intermediate_size": 3072,
  "layer_norm_eps": 1e-12,
  "max_position_embeddings": 512,
  "model_type": "bert",
  "num_attention_heads": 12,
  "num_hidden_layers": 12,
  "pad_token_id": 0,
  "pooler_fc_size": 768,
  "pooler_num_attention_heads": 12,
  "pooler_num_fc_layers": 3,
  "pooler_size_per_head": 128,
  "pooler_type": "first_token_transform",
  "type_vocab_size": 2,
  "vocab_size": 21128
}

这个 JSON 配置文件看起来是针对 BERT 模型的,其中包含了模型架构及其相关超参数的定义。以下是每个字段的详细解释:

  1. architectures
  • 类型: 数组
  • 作用: 定义模型的架构类型。这里的 "BertForMaskedLM" 表示该模型是用于任务“Mask Language Modeling”(掩码语言建模)的 BERT 模型。
  1. attention_probs_dropout_prob
  • 类型: 浮点数
  • 作用: 表示在注意力机制中应用的 dropout 概率。0.1 表示有 10% 的概率将注意力概率置为零,以防止过拟合。
  1. directionality
  • 类型: 字符串
  • 作用: 指定模型的方向性。"bidi" 表示这是一个双向模型,可以从句子的两端同时接收上下文信息。
  1. hidden_act
  • 类型: 字符串
  • 作用: 定义隐藏层的激活函数。在此配置中,使用的是 "gelu"(高斯误差线性单元),被认为相较于标准的 ReLU 更能提升模型性能。
  1. hidden_dropout_prob
  • 类型: 浮点数
  • 作用: 在隐藏层中应用的 dropout 概率,0.1 表示有 10% 的概率对隐藏层输出应用 dropout,有助于防止过拟合。
  1. hidden_size
  • 类型: 整数
  • 作用: 定义每个隐藏层的大小(向量维度),在这里是 768。这意味着每个隐藏状态被表示为一个 768 维的向量。
  1. initializer_range
  • 类型: 浮点数
  • 作用: 指定模型参数初始化时的范围,通常在 [-initializer_range, initializer_range] 之间。0.02 表示参数初始化的标准差。
  1. intermediate_size
  • 类型: 整数
  • 作用: 定义中间层的大小。在 Transformer 的前馈神经网络中,通常大于隐藏层的大小。这里是 3072,意味着中间层的输出维度是 3072。
  1. layer_norm_eps
  • 类型: 浮点数
  • 作用: 指定层归一化(Layer Normalization)时使用的小正数,用于避免除以零的情况。这里是 1e-12。
  1. max_position_embeddings
  • 类型: 整数
  • 作用: 定义模型能够处理的最大序列长度(即最大位置嵌入),在这里是 512,这意味着输入序列的最大长度是 512 个标记(tokens)。
  1. model_type
  • 类型: 字符串
  • 作用: 指明模型的类型,此处为 "bert",表明该架构是 BERT。
  1. num_attention_heads
  • 类型: 整数
  • 作用: 定义注意力头的数量,这里是 12,表示在多头自注意力机制中使用了 12 个注意力头。
  1. num_hidden_layers
  • 类型: 整数
  • 作用: 指定 Transformer 模型中的隐藏层数量,这里是 12,表示该 BERT 模型有 12 层的编码器堆叠。
  1. pad_token_id
  • 类型: 整数
  • 作用: 表示填充标记的 ID,0 通常用于标记“填充”位置,以便模型在处理不同长度的输入时能够合理对齐。
  1. pooler_fc_size
  • 类型: 整数
  • 作用: 是 BERT 模型池化层中全连接层的大小,通常等于隐藏层的大小,这里是 768。
  1. pooler_num_attention_heads
  • 类型: 整数
  • 作用: 池化层中使用的注意力头的数量,通常和编码层相同,这里是 12。
  1. pooler_num_fc_layers
  • 类型: 整数
  • 作用: 池化层中的全连接层数量,这里是 3,表示在池化过程中应用了三层全连接网络。
  1. pooler_size_per_head
  • 类型: 整数
  • 作用: 指明每个注意力头输出的维度大小,这里是 128,通常计算为 hidden_size / num_attention_heads
  1. pooler_type
  • 类型: 字符串
  • 作用: 表示池化层采用的类型,此处的 "first_token_transform" 表示使用第一个 token 的表示经过线性变换作为整个序列的表示。这在分类任务中是常用的做法。
  1. type_vocab_size
  • 类型: 整数
  • 作用: 定义类型词汇的大小。在 BERT 中,通常为 2,用于区分句子 A 和句子 B。
  1. vocab_size
  • 类型: 整数
  • 作用: 表示模型使用的词汇表的大小,在这里是 21128,说明模型可以识别 21128 个不同的标记(tokens)。
  1. [UNK]
  • 全名: Unknown Token
  • 作用: 这个标记用于表示模型无法识别的输入词汇或符号。当输入文本中存在不在模型词汇表中的单词时,这些单词将被替换为 [UNK]。它的目的是确保模型可以处理未知输入,而不会导致错误或中断。
  1. [CLS]
  • 全名: Classification Token
  • 作用: [CLS] 标记通常添加到输入序列的开头,特别是在需要分类任务(如情感分析、句子分类等)时。模型在训练时会使用这个标记的最终隐藏状态作为对整个句子的表示,以便进行分类或其他任务。
  1. [SEP]
  • 全名: Separator Token
  • 作用: [SEP] 标记用于分隔不同的句子或段落。在处理句子对(例如问题-答案、句子相似性任务)时,[SEP] 可以清晰地表明两个句子之间的分界,帮助模型理解输入的结构。
  1. [MASK]
  • 全名: Mask Token
  • 作用: 在掩码语言建模(Masked Language Modeling)任务中使用。该标记表示输入文本中某些单词已经被掩盖,模型的任务是根据上下文预测这些被掩盖的单词。通过这种方式,模型能够学习上下文关系和语言结构。
  1. <S>
  • 全名: Start Token
  • 作用: 通常用于在序列生成任务(如机器翻译、文本生成等)中指示序列的开始。它可以帮助模型明确输入的起点,并相应地调整输出。
  1. <T>
  • 全名: Token (or Terminate Token)
  • 作用: 类似于 <S>,通常用于指示序列的结束,标记生成序列中最后一个 token 的位置。在一些序列生成任务中,它可以帮助模型识别何时停止生成内容。

[PAD] 是一种特殊的标记(token),通常用于自然语言处理(NLP)模型中,尤其是在处理变长序列或批量输入时。以下是 [PAD] 标记的详细解释:

  1. 全名
  • Padding Token(填充标记)
  1. 作用
  • 填充序列: 在自然语言处理任务中,模型通常需要处理固定长度的输入序列。然而,实际的文本序列往往具有不同的长度。为了使所有输入序列具有相同的长度,可以添加 [PAD] 标记,以填充较短的序列。这种填充确保模型能够在批处理过程中均匀处理输入,避免因不同长度导致的计算问题。
  1. 应用场景
  • 批量处理: 在训练和推理过程中,通常会将多个样本组合成一个批次(batch)进行并行处理。通过使用 [PAD] 标记,将所有输入序列填充到相同的长度,可以有效提高模型的计算效率。
  • 序列标记任务: 在任务如命名实体识别(NER)或文本分类中, [PAD] 标记用于保持输入序列的一致性,确保模型能够正确对齐输出和输入。
  1. 示例

假设有以下三个样本:

  • "我爱学习"(3 个字)
  • "人工智能很有趣"(6 个字)
  • "自然语言处理"(5 个字)

当将这三个样本填充到最大长度为 6 时,可以得到:

  • "我爱学习" → "我爱学习 [PAD]"
  • "人工智能很有趣" → "人工智能很有趣"
  • "自然语言处理" → "自然语言处理 [PAD]"

这样填充后的序列长度一致,便于输入模型。

tokenizer_config.json 分词器配置文件

{"do_lower_case": false, "model_max_length": 512}

0. do_lower_case

  • 类型: 布尔值(boolean)
  • 作用: 指定在文本预处理时是否将输入文本转换为小写。当设置为 false 时,文本将保持其原始大小写。当设置为 true 时,所有的字母将被转换为小写。这项配置通常影响分词器的行为,尤其是在处理大小写敏感的任务时(例如命名实体识别或某些分类任务),保留原始大小写可能是很重要的。
  1. model_max_length
  • 类型: 整数
  • 作用: 指定模型可以接受的最大输入长度(token数量)。在您的配置中,此值为 512,意味着模型可以处理最多 512 个标记(tokens)。超出此长度的文本通常需要截断或分割,以确保输入能够适应模型的要求。这项配置对于管理长文本输入特别重要,因为 Transformer 类模型的结构通常限制了最大输入长度。

vocab里面好和##好的区别

在自然语言处理(NLP)领域的词汇表(vocabulary)中,像 ##好 这样的词汇通常在使用子词(subword)分割技术的模型中出现,特别是在基于字典的分词方法(如 BERT、WordPiece 和 SentencePiece)中。以下是它们之间的主要区别:

  • 完整的单词: 这个词可以被视为一个完整的词汇单元。它通常表示“好”的意思,是一个常见的中文词汇。
  • 在词汇表中的表示: 如果使用的模型词汇表中包含 ,则模型可以直接使用这个单词进行训练和推理,而无需进一步的拆分。
  1. ##好
  • 子词表示: ## 前缀表示这是一个子词(subword)单元。具体来说,它表示这个词是由前面的部分词(prefix)构成的一部分。在 WordPiece 分词中,这种表示法通常用于处理那些不在词汇表中的较长词。
  • 用于词汇表补充: 比如,对于一个较长的词汇,如果它不能完整出现在词汇表中,模型会将这个词拆分成更小的部分,并使用 ## 前缀来指示这些部分。这样,当模型处理较复杂的词时可以更有效地捕捉语义。

示例

假设我们有一个词汇表,其中包含以下词语:

  • 电子
  • 产品

如果输入文本是“电子产品好”,然后进行分词:

  • “电子产品好” 可能被分词为 电子产品##好,其中 ##好 指的是“好”这个词的子词表示。

为什么使用子词表示

  • 处理未知词: 通过使用子词表示,模型可以处理那些它从未见过的词,即使是从已知的子词构建的词。
  • 减少词表大小: 有了子词单元,模型的词汇表可以变得小得多,因为它可以灵活构建较长的词而不需要为每个可能的组合创建一个词条。
  • 语义保持: 子词保持了对原有词的语义,同时又能支持更广泛的表达,可以帮助模型更好地理解文本的上下文。

使用AutoModel自动模型方式调用Bert预训练模型

AutoModel 是一个用来自动加载各种预训练 Transformer 模型的类。你可以使用它直接从 Hugging Face 模型库中加载模型,而无须关心具体的模型实现。主要用于构建和微调模型,以便在特定的任务上进行更深入的开发。使用 AutoModel 通常需要更细粒度的操作,比如输入数据的处理、模型的前向传播、输出的处理等。更适合需要模型架构和输入输出控制的用户,如研究人员或需要定制模型的开发者。

AutoModel 还是 pipeline 对比

特性AutoModelpipeline
使用复杂性较复杂,需要手动处理各个步骤简单,自动处理所有步骤
适用场景适合需要灵活性和微调能力的开发适合快速应用于特定任务
示例代码model = AutoModel.from_pretrained("xxx")classifier = pipeline("task")
输出处理需要手动处理模型输出自动处理输出
适用人群研究人员、开发者等快速原型或希望简化流程的用户

具体示例:

import torch
from transformers import AutoTokenizer, AutoModelForSequenceClassification
​
​
def test_classfication():
    # 加载分词器
    tokenizer = AutoTokenizer.from_pretrained('./Bert-base-chinese')
​
    # 加载模型
    model = AutoModelForSequenceClassification.from_pretrained('./Bert-base-chinese')
    print(model)
​
    # 准备输入数据
    input_ids = tokenizer.encode(
        text='今天天气不错',  # 输入文本
        return_tensors='pt',  # 返回PyTorch张量
        padding="max_length",  # 填充到最大长度
        truncation=True,  # 截断超出长度的输入
        max_length=10  # 输入最大长度
    )
    print(input_ids, input_ids.shape)
​
    # 评估模式
    model.eval()
​
    # 模型预测
    output = model(input_ids)
​
    # 5. 获取预测结果
    logits = output.logits
    prediction = torch.argmax(logits, dim=-1)
    print(logits, prediction)
    sentiment = prediction.item()  # 转换为 Python 整数
    sentiment_label = "积极" if sentiment == 1 else "消极" if sentiment == 0 else "中性"
    print(sentiment_label)
​
​
if __name__ == '__main__':
    test_classfication()

运行结果:

BertForSequenceClassification(
  (bert): BertModel(
    (embeddings): BertEmbeddings(
      (word_embeddings): Embedding(21128, 768, padding_idx=0)
      (position_embeddings): Embedding(512, 768)
      (token_type_embeddings): Embedding(2, 768)
      (LayerNorm): LayerNorm((768,), eps=1e-12, elementwise_affine=True)
      (dropout): Dropout(p=0.1, inplace=False)
    )
    (encoder): BertEncoder(
      (layer): ModuleList(
        (0-11): 12 x BertLayer(
          (attention): BertAttention(
            (self): BertSdpaSelfAttention(
              (query): Linear(in_features=768, out_features=768, bias=True)
              (key): Linear(in_features=768, out_features=768, bias=True)
              (value): Linear(in_features=768, out_features=768, bias=True)
              (dropout): Dropout(p=0.1, inplace=False)
            )
            (output): BertSelfOutput(
              (dense): Linear(in_features=768, out_features=768, bias=True)
              (LayerNorm): LayerNorm((768,), eps=1e-12, elementwise_affine=True)
              (dropout): Dropout(p=0.1, inplace=False)
            )
          )
          (intermediate): BertIntermediate(
            (dense): Linear(in_features=768, out_features=3072, bias=True)
            (intermediate_act_fn): GELUActivation()
          )
          (output): BertOutput(
            (dense): Linear(in_features=3072, out_features=768, bias=True)
            (LayerNorm): LayerNorm((768,), eps=1e-12, elementwise_affine=True)
            (dropout): Dropout(p=0.1, inplace=False)
          )
        )
      )
    )
    (pooler): BertPooler(
      (dense): Linear(in_features=768, out_features=768, bias=True)
      (activation): Tanh()
    )
  )
  (dropout): Dropout(p=0.1, inplace=False)
  (classifier): Linear(in_features=768, out_features=2, bias=True)
)
tensor([[ 101,  791, 1921, 1921, 3698,  679, 7231,  102,    0,    0]]) torch.Size([1, 10])
tensor([[-0.2556,  0.3660]], grad_fn=<AddmmBackward0>) tensor([1])
积极

AutoTokenizer 负责将生文本转换为模型可以理解的输入格式。这一过程通常涉及分词、编码等步骤。

以下介绍 AutoTokenizer.encode 方法的重要参数:

AutoTokenizer.encode 方法参数

  1. text (str or List[str])

    • 要编码的输入文本,可以是单个字符串或字符串列表。如果是列表,AutoTokenizer 将对每个字符串进行编码。
  2. text_pair (str or List[str], optional)

    • 如果您想要处理文本对(例如,问答任务),可以使用此参数。它的值也可以是单个字符串或字符串列表,表示要与 text 一同编码的第二个文本。
  3. max_length (int, optional)

    • 限制返回的序列最大长度。如果输入文本的编码长度超过此参数,将会被截断。如果没有设置,默认长度由模型的最大输入长度决定。
  4. padding (bool or str, optional)

    • 控制返回的序列是否进行填充。可以设置为 True,让所有返回的序列填充到同一最大长度,或者为 'max_length',使所有序列填充到 max_length 指定的长度。默认值通常是 False
  5. truncation (bool or str, optional)

    • 控制是否截断输入序列。通常可以设置为 True,以截断到最大长度,也可以设置为 'longest_first''do_not_truncate' 等选项。默认值通常是 False
  6. return_tensors (str, optional)

    • 如果设置,返回的张量将被转换为指定框架的张量格式,例如 'pt'(PyTorch)或者 'tf'(TensorFlow)。如果不设置,返回的是普通的 Python 列表。
  7. return_attention_mask (bool, optional)

    • 是否返回注意力掩码。注意力掩码通常用于指示模型在处理输入序列时,应该关注哪些位置。
  8. return_token_type_ids (bool, optional)

    • 是否返回 token 类型 ID 值,在一些任务(如问答)中可能会用到,它帮助模型区分不同的文本对。
  9. add_special_tokens (bool, optional)

    • 控制是否在输入文本前后添加特殊的标记(如 [CLS][SEP]),这些标记在 BERT 和其他一些模型中是必需的,帮助模型理解输入的结构。
  10. encoding (str, optional)

    • 指定字符编码类型,例如 "utf-8"。这通常在处理文本输入时很有用。

使用AutoModel自动模式方式调用gpt2预训练模型实现文本生成任务

GPT-2(Generative Pre-trained Transformer 2)是由OpenAI开发的一种语言生成模型,基于Transformer架构。它是GPT(Generative Pre-trained Transformer)系列的第二代产品,于2019年发布。GPT-2模型的核心思想是利用大规模文本数据进行无监督学习,通过自回归的方式生成自然语言文本。

GPT-2的训练数据覆盖了互联网的大量文本,包括书籍、文章、网页等,包含多种主题和风格。模型采用了1.5亿到15亿个参数的多个变体,较大的参数量使其能够捕捉丰富的语义信息和上下文依赖关系,从而生成更为连贯和上下文相关的文本。

与其前身相比,GPT-2在生成文本的质量和多样性上有了明显提升。它可以用于多种任务,如文本完成、故事生成、问答系统以及对话生成等。在实际应用中,模型可以根据给定的起始文本(prompt)生成连续的内容,展现出强大的创造力。然而,GPT-2也引发了对其潜在滥用的担忧,如生成虚假信息和垃圾邮件等。

由于其强大的能力,OpenAI起初选择分阶段发布GPT-2,以便对潜在风险进行评估。最终在2020年开源了完整模型,使得研究人员和开发者能够更广泛地使用和探索这一技术。

huggingface.co/uer/gpt2-ch…

我们用gpt2实现文本生成任务,下面是示例:

import torch
from transformers import AutoTokenizer, AutoModelForCausalLM
​
​
def test_text_generation():
    # 使用设备(GPU/CPU)
    device = torch.device("cuda" if torch.cuda.is_available() else "cpu")
    print(device)
​
    # 加载分词器
    tokenizer = AutoTokenizer.from_pretrained('./gpt2-chinese-cluecorpussmall')
​
    # 加载模型
    model = AutoModelForCausalLM.from_pretrained('./gpt2-chinese-cluecorpussmall')
    print(model)
​
    # 设置为评估模式
    model.eval()
​
    model.to(device)
​
    # 准备输入数据
    input_ids = tokenizer.encode(
        text='大语言模型技术发展',  # 输入文本
        return_tensors='pt'  # 返回PyTorch张量
    ).to(device)
​
    # 生成文本
    output_sequences = model.generate(
        input_ids=input_ids,
        max_length=100,  # 生成的文本总长度
        num_return_sequences=1,  # 返回的生成序列数量
        no_repeat_ngram_size=2,  # 避免重复的n-gram 防止相同词组重复出现,从而提高生成文本的多样性和自然性。
        temperature=0.7,  # 温度参数控制随机性
        top_k=50,  # 仅从前k个概率最高的单词中采样
        top_p=0.95,  # 只从前95%概率质量的词汇中进行随机采样 核采样策略
        do_sample=True  # 开启采样
    )
​
    print(output_sequences)
​
    # 解码并打印生成的文本
    for sequence in output_sequences:
        generated_text = tokenizer.decode(sequence, skip_special_tokens=True)
        print(generated_text)
​
​
if __name__ == '__main__':
    test_text_generation()

运行结果:

image.png