10语音与语言处理(第3版)

机器翻译

自动翻译

机器翻译Seq2SeqBLEU

🎯 AI 时代的学习建议:不要只读理论。理解这一章的设计动机(为什么需要这个概念?)和边界条件(什么情况下会失效?)。当 AI 生成的代码涉及这些概念时,你能判断它是否用对了场景。AI 能帮你总结内容,但无法替代你亲手阅读、思考、建立直觉的过程。

第10章:机器翻译(Machine Translation)

一、导读

1.1 本章学习目标

机器翻译(MT)是 NLP 最具标志性的任务之一,目标是将一种自然语言的文本自动翻译为另一种自然语言。从统计机器翻译到神经机器翻译,再到基于大语言模型的翻译,这一领域经历了深刻的技术变革。

本章的核心学习目标包括:

  • 理解机器翻译的发展历程:从规则方法到统计方法再到神经网络方法
  • 掌握 Seq2Seq 架构:编码器-解码器框架的工作原理
  • 深入理解注意力机制:注意力如何改善 Seq2Seq 的性能
  • 掌握 Transformer 在 MT 中的应用:为什么 Transformer 成为 MT 的标准架构
  • 理解 MT 的评估方法:BLEU 分数的计算和局限性
  • 了解现代 MT 系统:多语言翻译、低资源翻译、大模型翻译

1.2 为什么本章如此重要

机器翻译是 NLP 的"试金石"任务。它综合了语言理解(源语言)和语言生成(目标语言)的能力,是对 NLP 技术最全面的考验。

MT 的技术进步直接推动了 NLP 的核心方法发展:

  • Seq2Seq 架构:成为处理序列到序列任务的标准框架
  • 注意力机制:最初在 MT 中提出,后来成为 Transformer 的核心
  • Transformer:最初为 MT 设计,后来成为 NLP 的通用架构
  • 预训练-微调:在 MT 中验证了迁移学习的有效性

理解机器翻译,就是理解现代 NLP 的核心技术脉络。

1.3 核心问题引导

机器翻译的核心难点是什么?为什么它比其他 NLP 任务更具挑战性?

Seq2Seq 架构如何工作?编码器-解码器框架的优势是什么?

注意力机制解决了 Seq2Seq 的什么问题?它如何工作?

为什么 Transformer 取代了 RNN 成为 MT 的标准架构?

BLEU 分数如何计算?它有什么局限性?

低资源语言翻译面临什么挑战?有哪些解决方案?


二、核心概念详解

10.1 机器翻译的发展历程

10.1.1 规则机器翻译(RBMT)

基于语言学家编写的规则进行翻译。需要为每对语言编写大量的语法规则和词典。

优点:可解释性强,翻译质量可控

缺点:规则编写成本极高,覆盖面窄,难以处理歧义

10.1.2 统计机器翻译(SMT)

基于统计模型从平行语料中学习翻译概率。代表性模型包括 IBM 模型系列和短语翻译模型。

核心思想:找到使 $P(\text{target} | \text{source})$ 最大的翻译:

$$\hat{e} = \arg\max_e P(e|f) = \arg\max_e P(f|e) \cdot P(e)$$

其中 $P(f|e)$ 是翻译模型,$P(e)$ 是目标语言的语言模型。

10.1.3 神经机器翻译(NMT)

使用神经网络端到端地学习翻译。Seq2Seq + Attention 是 NMT 的经典架构。

10.2 Seq2Seq 架构

10.2.1 编码器-解码器框架

编码器:将源语言序列编码为固定长度的上下文向量。

$$\mathbf{h}_t = \text{Encoder}(\mathbf{x}_t, \mathbf{h}_{t-1})$$

$$\mathbf{c} = \mathbf{h}_T$$

解码器:根据上下文向量逐步生成目标语言序列。

$$\mathbf{s}_t = \text{Decoder}(\mathbf{y}_{t-1}, \mathbf{s}_{t-1}, \mathbf{c})$$

$$P(y_t | y_{<t}, \mathbf{x}) = \text{softmax}(\mathbf{W} \mathbf{s}_t)$$

python
import torch
import torch.nn as nn

class Encoder(nn.Module):
    def __init__(self, vocab_size, embed_dim, hidden_dim):
        super().__init__()
        self.embedding = nn.Embedding(vocab_size, embed_dim)
        self.lstm = nn.LSTM(embed_dim, hidden_dim, batch_first=True)

    def forward(self, x):
        embedded = self.embedding(x)
        outputs, (hidden, cell) = self.lstm(embedded)
        return hidden, cell

class Decoder(nn.Module):
    def __init__(self, vocab_size, embed_dim, hidden_dim):
        super().__init__()
        self.embedding = nn.Embedding(vocab_size, embed_dim)
        self.lstm = nn.LSTM(embed_dim, hidden_dim, batch_first=True)
        self.fc = nn.Linear(hidden_dim, vocab_size)

    def forward(self, input, hidden, cell):
        embedded = self.embedding(input).unsqueeze(1)
        output, (hidden, cell) = self.lstm(embedded, (hidden, cell))
        prediction = self.fc(output.squeeze(1))
        return prediction, hidden, cell

class Seq2Seq(nn.Module):
    def __init__(self, encoder, decoder):
        super().__init__()
        self.encoder = encoder
        self.decoder = decoder

    def forward(self, src, trg, teacher_forcing_ratio=0.5):
        batch_size = src.shape[0]
        trg_len = trg.shape[1]
        trg_vocab_size = self.decoder.fc.out_features

        outputs = torch.zeros(batch_size, trg_len, trg_vocab_size)
        hidden, cell = self.encoder(src)

        input = trg[:, 0]  # <sos> token

        for t in range(1, trg_len):
            output, hidden, cell = self.decoder(input, hidden, cell)
            outputs[:, t] = output

            teacher_force = torch.rand(1).item() < teacher_forcing_ratio
            top1 = output.argmax(1)
            input = trg[:, t] if teacher_force else top1

        return outputs

10.3 注意力机制

10.3.1 动机

经典 Seq2Seq 将整个源序列压缩为一个固定长度的向量,这导致信息瓶颈——长序列的信息难以完整传递。

注意力机制允许解码器在每一步直接访问编码器的所有隐藏状态,动态地"关注"源序列的不同部分。

10.3.2 Bahdanau 注意力(加性注意力)

$$e_{ti} = \mathbf{v}^T \tanh(\mathbf{W}_a [\mathbf{s}_{t-1}; \mathbf{h}_i])$$

$$\alpha_{ti} = \frac{\exp(e_{ti})}{\sum_{j=1}^{T_x} \exp(e_{tj})}$$

$$\mathbf{c}_t = \sum_{i=1}^{T_x} \alpha_{ti} \mathbf{h}_i$$

python
class Attention(nn.Module):
    def __init__(self, hidden_dim):
        super().__init__()
        self.attn = nn.Linear(hidden_dim * 2, hidden_dim)
        self.v = nn.Linear(hidden_dim, 1, bias=False)

    def forward(self, hidden, encoder_outputs):
        # hidden: (batch, hidden_dim)
        # encoder_outputs: (batch, src_len, hidden_dim)
        src_len = encoder_outputs.shape[1]
        hidden = hidden.unsqueeze(1).repeat(1, src_len, 1)
        energy = torch.tanh(self.attn(torch.cat((hidden, encoder_outputs), dim=2)))
        attention = self.v(energy).squeeze(2)
        return torch.softmax(attention, dim=1)

10.3.3 Luong 注意力(乘性注意力)

$$e_{ti} = \mathbf{s}_t^T \mathbf{W}_a \mathbf{h}_i$$

乘性注意力计算更高效,是 Transformer 注意力的前身。

10.4 Transformer 用于机器翻译

10.4.1 架构

"Attention Is All You Need" (Vaswani et al., 2017) 提出了完全基于注意力的 Transformer 架构:

  • 编码器:6 层,每层包含多头自注意力 + 前馈网络
  • 解码器:6 层,每层包含掩码自注意力 + 交叉注意力 + 前馈网络

10.4.2 为什么 Transformer 优于 RNN

  • 并行计算:不需要逐步处理序列
  • 长距离依赖:自注意力直接连接任意两个位置
  • 训练效率:训练速度比 RNN 快数倍

10.5 评估方法

10.5.1 BLEU 分数

BLEU (Bilingual Evaluation Understudy) 是最常用的 MT 评估指标:

$$\text{BLEU} = BP \cdot \exp\left(\sum_{n=1}^{N} w_n \log p_n\right)$$

其中 $p_n$ 是 n-gram 精确率,$BP$ 是简短惩罚。

python
from nltk.translate.bleu_score import corpus_bleu, sentence_bleu

# 句子级 BLEU
reference = [["the", "cat", "is", "on", "the", "mat"]]
hypothesis = ["the", "cat", "sat", "on", "the", "mat"]
score = sentence_bleu(reference, hypothesis, weights=(0.25, 0.25, 0.25, 0.25))
print(f"BLEU: {score:.4f}")

# 语料级 BLEU
references = [
    [["the", "cat", "is", "on", "the", "mat"], ["there", "is", "a", "cat", "on", "the", "mat"]],
    [["the", "dog", "is", "in", "the", "garden"]],
]
hypotheses = [
    ["the", "cat", "sat", "on", "the", "mat"],
    ["the", "dog", "is", "in", "the", "garden"],
]
score = corpus_bleu(references, hypotheses)
print(f"Corpus BLEU: {score:.4f}")

10.5.2 其他评估指标

  • METEOR:考虑同义词和词形变化
  • TER:基于编辑距离
  • BERTScore:基于 BERT 嵌入的语义相似度
  • COMET:基于神经网络的评估

10.6 现代 MT 的挑战

10.6.1 低资源翻译

当平行语料很少时,翻译质量急剧下降。解决方案:

  • 迁移学习:从高资源语言对迁移知识
  • 多语言翻译:使用单一模型处理多种语言对
  • 回译(Back-Translation):用目标→源方向的模型生成伪平行数据
  • 零样本翻译:利用语言间的共享表示

10.6.2 大语言模型翻译

GPT-4 等大语言模型展示了强大的翻译能力,通过提示即可进行高质量翻译:

python
# 使用 GPT 进行翻译
prompt = """Translate the following English text to Chinese:

English: Natural language processing is a fascinating field.
Chinese:"""

# GPT-4 会生成:"自然语言处理是一个引人入胜的领域。"

三、实战案例

3.1 使用 Hugging Face 进行翻译

python
from transformers import MarianMTModel, MarianTokenizer

# 加载英中翻译模型
model_name = "Helsinki-NLP/opus-mt-en-zh"
tokenizer = MarianTokenizer.from_pretrained(model_name)
model = MarianMTModel.from_pretrained(model_name)

def translate(text, source_lang="en", target_lang="zh"):
    inputs = tokenizer(text, return_tensors="pt", padding=True)
    outputs = model.generate(**inputs, max_length=128)
    return tokenizer.decode(outputs[0], skip_special_tokens=True)

# 测试
text = "Natural language processing is a fascinating field of computer science."
translation = translate(text)
print(f"English: {text}")
print(f"Chinese: {translation}")

3.2 训练简单的 Seq2Seq 翻译模型

python
import torch
import torch.nn as nn
import torch.optim as optim

# 超参数
SRC_VOCAB_SIZE = 5000
TRG_VOCAB_SIZE = 5000
EMBED_DIM = 256
HIDDEN_DIM = 512
N_LAYERS = 2

# 创建模型
encoder = Encoder(SRC_VOCAB_SIZE, EMBED_DIM, HIDDEN_DIM)
decoder = Decoder(TRG_VOCAB_SIZE, EMBED_DIM, HIDDEN_DIM)
model = Seq2Seq(encoder, decoder).to(device)

optimizer = optim.Adam(model.parameters(), lr=1e-3)
criterion = nn.CrossEntropyLoss(ignore_index=PAD_IDX)

# 训练循环
for epoch in range(N_EPOCHS):
    model.train()
    total_loss = 0

    for batch in train_loader:
        src = batch.src.to(device)
        trg = batch.trg.to(device)

        optimizer.zero_grad()
        output = model(src, trg)
        output = output[:, 1:].reshape(-1, TRG_VOCAB_SIZE)
        trg = trg[:, 1:].reshape(-1)

        loss = criterion(output, trg)
        loss.backward()
        optimizer.step()
        total_loss += loss.item()

    print(f"Epoch {epoch}, Loss: {total_loss / len(train_loader):.4f}")

3.3 使用 Transformer 进行翻译

python
from transformers import AutoModelForSeq2SeqLM, AutoTokenizer

# 使用预训练 Transformer 翻译模型
model_name = "t5-small"
tokenizer = AutoTokenizer.from_pretrained(model_name)
model = AutoModelForSeq2SeqLM.from_pretrained(model_name)

def translate_with_t5(text, target_lang="Chinese"):
    input_text = f"translate English to {target_lang}: {text}"
    inputs = tokenizer(input_text, return_tensors="pt")
    outputs = model.generate(**inputs, max_length=128)
    return tokenizer.decode(outputs[0], skip_special_tokens=True)

text = "The weather is beautiful today."
print(translate_with_t5(text))

四、本章小结

本章系统讲解了机器翻译:

发展历程:从规则方法到统计方法再到神经网络方法。NMT 取得了突破性进展。

Seq2Seq 架构:编码器将源序列编码为向量,解码器逐步生成目标序列。信息瓶颈是主要问题。

注意力机制:允许解码器动态关注源序列的不同部分,解决了信息瓶颈。

Transformer:完全基于注意力,支持并行计算,成为 MT 的标准架构。

评估方法:BLEU 是最常用的指标,但有局限性。BERTScore 等基于语义的指标正在兴起。

现代挑战:低资源翻译、大模型翻译、多语言翻译是当前的研究热点。

机器翻译是 NLP 最综合的任务之一,它推动了 Seq2Seq、注意力、Transformer 等核心技术的发展。下一章我们将学习问答系统。


五、思考与练习

思考题

比较统计机器翻译和神经机器翻译的优缺点。

注意力机制的可视化能揭示什么信息?翻译过程中模型是如何"对齐"源语言和目标语言的?

BLEU 分数有什么局限性?为什么高 BLEU 分数的翻译不一定好?

大语言模型(如 GPT-4)的翻译能力与专门的翻译模型(如 MarianMT)相比如何?

编程练习

实现一个带注意力机制的 Seq2Seq 翻译模型。可视化注意力权重。

使用 MarianMT 模型进行英中翻译。计算 BLEU 分数并与人工评估比较。

使用 GPT-4 进行零样本翻译。设计提示模板,比较不同提示对翻译质量的影响。


10/12机器翻译
0%