# 章末小测验 [[章末小测验]]

让我们测试一下你在这章学到了什么！

### 1．以下哪些任务可以看作为 token 分类问题？

<Question
	choices={[
		{
			text: "找出句子中的不同词的词性。",
			explain: "正确！我们可以为每个词打上名词、动词等标签。",
			correct: true
		},
		{
			text: "判断一个句子的语法是否正确。",
			explain: "不，这是一个序列分类问题。"
		},
		{
			text: "找出句子中提到的人或物。",
			explain: "正确！我们可以将每个词标注为人名或非人名。",
            correct: true
		},
        {
			text: "找出句子中回答问题的段落。",
			explain: "不对，那应该是一个问答（QA）的问题。"
		}
	]}
/>

### 2． token 分类的预处理部分与其他预处理流程有什么不同？

<Question
	choices={[
		{
			text: "不需要进行预处理；文本已经被分词了。",
			explain: "虽然文本确实已经被分词，但我们仍然需要进行子词分词。"
		},
		{
			text: "输入的文本就是单词序列，所以我们只需要进行子词分词。",
			explain: "正确！这与通常需要完整的分词流程预处理不同。你能想到另一个差异吗？",
			correct: true
		},
		{
			text: "我们使用 <code>-100</code> 来标记特殊 token 。",
			explain: "这不是 token 分类特有的 —— 我们总是用 <code>-100</code> 作为我们想在损失中忽略的 token 的标签。"
		},
		{
			text: "在进行截断/填充时，我们需要确保将待预测的标签截断或填充到与输入相同的大小",
			explain: "的确如此！但这并不是唯一的区别。",
			correct: true
		}
	]}
/>

### 3．在 token 分类问题中，当我们分词并想要子词分词时，会出现什么问题？

<Question
	choices={[
		{
			text: "Tokenizer 添加了特殊的 token ，我们没有这些 token 的标签。",
			explain: "我们把这些 token ID设置为 <code>-100</code>，所以在计算损失时它们会被忽略。"
		},
		{
			text: "每个词可能产生多个 token ，因此我们最终会得到比我们拥有的标签更多的 token 。",
			explain: "这是主要的问题，我们需要将原始的标签与 token 对齐。",
			correct: true
		},
		{
			text: "添加的 token 没有标签，所以没有问题。",
			explain: "这是不正确的；我们需要和 token 相同数量的标签，否则我们的模型会报错。"
		}
	]}
/>

### 4.“领域适应”是什么意思？
<Question
	choices={[
		{
			text: "我们在一个数据集上运行模型，并获取该数据集中每个样本的预测结果。",
			explain: "不，这只是模型推理的过程。"
		},
		{
			text: "当我们在数据集上训练模型时。",
			explain: "不对，这只是训练模型的过程；这里没有适应。"
		},
		{
			text: "我们在一个新的数据集上微调一个预训练的模型，并在测试集上有一定的适应性。",
			explain: "正确！模型将其知识适应到了新的数据集上。",
            correct: true
		},
        {
			text: "我们将被模型分类错误的样本添加到数据集中，使得我们的模型更加健壮。",
			explain: "如果你定期重新训练模型，的确应该这样做，但这不是领域适应。"
		}
	]}
/>

### 5．掩码语言建模问题中的标签是什么？
<Question
	choices={[
		{
			text: "输入句子中的一些标记是随机屏蔽的，标签就是原始输入 token 。",
			explain: "就是这样！",
            correct: true
		},
		{
			text: "输入句子中的一些 token 是随机屏蔽的，标签是原始的输入 token 向左移动形成的。",
			explain: "不，将待预测的标签向左移动相当于预测下一个单词，这就是因果语言模型。"
		},
		{
			text: "输入句子中的一些 token 是随机屏蔽的，标签是这个句子是积极的还是消极的。",
			explain: "这是一个数据增强的序列分类问题，而不是掩码语言建模。"
		},
        {
			text: "两个句子中的一些 token 是随机屏蔽的，标签是两个句子是否相似。",
			explain: "这是一个数据增强的序列分类问题，而不是掩码语言建模。"
		}
	]}
/>

### 6．哪些任务可以被看作是序列到序列的问题？
<Question
	choices={[
		{
			text: "撰写长文档的简短评论",
			explain: "是的，这是一个文档摘要任务。试试另一个答案！",
            correct: true
		},
		{
			text: "回答关于一个文档的问题。",
			explain: "这可以被构建为一个序列到序列的问题。这不是唯一的正确答案。",
            correct: true
		},
		{
			text: "将一段中文文本翻译成英文。",
			explain: "这绝对是一个从序列到序列的问题。你能发现另一个吗？",
            correct: true
		},
        {
			text: "修正我侄子/朋友发来的信息，纠正他们的语法错误",
			explain: "这是一种翻译问题，所以绝对是一个序列到序列的任务。这不是唯一的正确答案。",
			correct: true
		}
	]}
/>

### 7．对于序列到序列的问题，预处理数据的正确方法是什么？
<Question
	choices={[
		{
			text: "输入和目标必须一起发送到 tokenizer ，使用 `input = ...` 和 `target = ...` 。",
			explain: "这可能是我们未来要添加的一个 API，但现在还不行。"
		},
		{
			text: "输入和目标都必须在 tokenizer 的两次独立调用中进行预处理。",
			explain: "这是正确的，但是不完整。你还需要做一些事情来确保 tokenizer 正确处理两者。"
		},
		{
			text: "像往常一样，我们只需要对输入进行 tokenize",
			explain: "在一个序列到序列问题中，并不仅仅是输入文本需要进行 tokenize，目标文本也需要进行同样的转换！"
		},
        {
			text: "输入序列和目标序列都需要通过特殊的上下文管理器分别发送给 tokenizer 进行预处理。",
			explain: "这是正确的， tokenizer 需要通过该上下文管理器找到目标序列的范围并进行处理。",
			correct: true
		}
	]}
/>

{#if fw === 'pt'}

### 8．为什么需要有一个特定的 `Trainer `子类来解决序列到序列问题？

<Question
	choices={[
		{
			text: "因为序列到序列问题使用自定义的损失计算方法，忽略 <code>-100</code> 的标签",
			explain: "这根本不是自定义的损失计算方法，而是自然语言处理中一种常规的忽略特定 token 计算方式。"
		},
		{
			text: "因为序列到序列问题需要特殊的评估循环",
			explain: "没错。序列到序列模型的预测通常需要使用 <code>generate()</code> 方法",
			correct: true
		},
		{
			text: "因为该问题中的预测目标是序列到序列中问题部分的文本",
			explain: "这不是<code>Trainer</code>需要考虑的部分，因为这些文本在进入`Tranier`之前已经被预处理过。"
		},
        {
			text: "因为我们在序列到序列问题中使用了两个模型",
			explain: "我们确实以某种方式使用两种模型，编码器和解码器，但它们被组合在一个模型中"
		}
	]}
/>

{:else}

### 9．为什么在 Transformer 模型上调用 `compile()` 时通常不需要指定损失的计算方法？

<Question
	choices={[
		{
			text: "因为 Transformer 模型是以非监督式学习进行训练",
			explain: "并非如此——即使是无监督学习也需要损失函数！"
		},
		{
			text: "因为默认使用模型的内部损失计算方法",
			explain: "没错！",
			correct: true
		},
		{
			text: "因为我们在训练后计算评估指标",
			explain: "我们确实经常这样做，但这并不能解释我们在训练中优化的损失值是从哪里得到的。"
		},
        {
			text: "因为损失是在`model.fit()`中指定的",
			explain: "不，一旦运行`model.compile()`，损失函数就总是固定的，并且不能在`model.fit()`中更改。"
		}
	]}
/>

{/if}

### 10．你应该在什么时候预先训练一个新的模型？
<Question
	choices={[
		{
			text: "当你的特定语言没有预训练模型可用时",
			explain: "没错。",
			correct: true
		},
		{
			text: "当你有大量可用的数据时，即使有一个经过训练的模型可以处理这些数据",
			explain: "在这种情况下，你可能应该使用预训练的模型并对数据进行微调，以避免巨大的计算成本。"
		},
		{
			text: "当你担心你所使用的预先训练过的模型有较大偏差时",
			explain: "这是正确的，但是你需要确保你用于训练的数据真的更好。",
			correct: true
		},
        {
			text: "当可用的预先训练好的模型还不够好的时候",
			explain: "那么，你确定你已经正确地调试了你的训练吗？"
		}
	]}
/>

### 11．为什么在大量的文本上预先训练一个语言模型是很容易的呢？

<Question
	choices={[
		{
			text: "当你担心你所使用的预先训练的模型的偏差时",
			explain: "虽然这是真的，和这个问题没什么关系。再试一次！"
		},
		{
			text: "因为预训练不需要人工标记数据",
			explain: "没错，语言建模是一个自监督的问题。",
			correct: true
		},
		{
			text: "因为🤗 Transformers 库只需要几行代码就可以开始训练",
			explain: "虽然这是真的，但是并足以回答这个问题。再试一次！"
		}
	]}
/>

### 12．问答任务预处理数据时，主要的挑战是什么？

<Question
	choices={[
		{
			text: "你需要对输入进行 tokenize。",
			explain: "的确是需要的，但这真的是一个专属于问答任务的主要的挑战吗？"
		},
		{
			text: "你需要处理非常长的上下文，这些非常长的上下文提供了一些训练特性，这些特性可能有也可能没有答案。",
			explain: "这绝对是挑战之一。",
			correct: true
		},
		{
			text: "你需要将问题的答案以及输入进行 tokenize。",
			explain: "虽然的确需要这样做，但这并不能构成主要的挑战，试试另一个答案吧！"
		},
       {
			text: "你需要从文本中找到答案部分在 tokenize 后的输入中对应的起始和结束位置。。",
			explain: "这是最难的部分之一，是的！",
			correct: true
		}
	]}
/>

### 13．问答任务中的后处理通常是怎样进行的？
<Question
	choices={[
		{
			text: "模型给出了答案的开始位置和结束位置，你只需要根据这些位置解码对应的 tokens。",
			explain: "这可能是一种方法，但是有点太粗略了，还有些细节没考虑到。"
		},
		{
			text: "该模型为每个示例创建的每个特征提供了答案的起始和结束位置，你只需在得分最高的那个特征中解码相应的 tokens。",
			explain: "这与我们研究的后处理过程很接近，但并不完全正确。"
		},
		{
			text: "模型会为每个样本创建的每个特征给出了答案的起始和结束位置，你只需要将它们与上下文中的片段匹配，找到得分最高的那个。",
			explain: "简而言之就是这样！",
			correct: true
		},
        {
			text: "模型生成一个答案，你只需要解码它。",
			explain: "虽然的确需要这个过程，但是有点太简略了。试试另一个答案吧！"
		}
	]}
/>


<EditOnGithub source="https://github.com/huggingface/course/blob/main/chapters/zh-CN/chapter7/9.mdx" />