# Tradução

A tradução converte uma sequência de texto de um idioma para outro. É uma das várias tarefas que podem ser formuladas como um problema de sequência-para-sequência, um framework poderoso para retornar alguma saída a partir de uma entrada, como tradução ou sumarização. Sistemas de tradução são comumente usados para tradução entre textos de diferentes idiomas, mas também podem ser usados para fala ou alguma combinação entre eles, como texto-para-fala ou fala-para-texto.

Este guia mostrará como:

1. Ajuste fino do [T5](https://huggingface.co/google-t5/t5-small) no subconjunto inglês-francês do conjunto de dados [OPUS Books](https://huggingface.co/datasets/Helsinki-NLP/opus_books) para traduzir texto do inglês para o francês.
2. Use seu modelo ajustado para inferência.

Para ver todas as arquiteturas e checkpoints compatíveis com esta tarefa, recomendamos consultar a [página da tarefa](https://huggingface.co/tasks/translation).

Antes de começar, verifique se você tem todas as bibliotecas necessárias instaladas:

```bash
pip install transformers datasets evaluate sacrebleu
```

Recomendamos que você faça login na sua conta do Hugging Face para que possa enviar e compartilhar seu modelo com a comunidade. Quando solicitado, insira seu token para fazer login:

```py
>>> from huggingface_hub import notebook_login

>>> notebook_login()
```

## Carregar o conjunto de dados OPUS Books

Comece carregando o subconjunto inglês-francês do conjunto de dados [OPUS Books](https://huggingface.co/datasets/Helsinki-NLP/opus_books) a partir da biblioteca 🤗 Datasets:

```py
>>> from datasets import load_dataset

>>> books = load_dataset("Helsinki-NLP/opus_books", "en-fr")
```

Divida o conjunto de dados em um conjunto de treinamento e um conjunto de teste com o método [train_test_split](https://huggingface.co/docs/datasets/main/en/package_reference/main_classes#datasets.Dataset.train_test_split):

```py
>>> books = books["train"].train_test_split(test_size=0.2)
```

Em seguida, veja um exemplo:

```py
>>> books["train"][0]
{'id': '90560',
 'translation': {'en': 'But this lofty plateau measured only a few fathoms, and soon we reentered Our Element.',
  'fr': 'Mais ce plateau élevé ne mesurait que quelques toises, et bientôt nous fûmes rentrés dans notre élément.'}}
```

`translation`: uma tradução em inglês e francês do texto.

## Pré-processar

A próxima etapa é carregar um tokenizador T5 para processar os pares de idiomas inglês-francês:

```py
>>> from transformers import AutoTokenizer

>>> checkpoint = "google-t5/t5-small"
>>> tokenizer = AutoTokenizer.from_pretrained(checkpoint)
```

A função de pré-processamento que você deseja criar precisa:

1. Adicione um prompt ao início da entrada para que o T5 saiba que se trata de uma tarefa de tradução. Alguns modelos capazes de executar múltiplas tarefas de PLN exigem um prompt para tarefas específicas.
2. Defina o idioma de destino (francês) no parâmetro `text_target` para garantir que o tokenizer processe o texto de destino corretamente. Se você não definir `text_target`, o tokenizer processará o texto de destino como inglês.
3. Truncar sequências para que não excedam o comprimento máximo definido pelo parâmetro `max_length`.

```py
>>> source_lang = "en"
>>> target_lang = "fr"
>>> prefix = "translate English to French: "

>>> def preprocess_function(examples):
...     inputs = [prefix + example[source_lang] for example in examples["translation"]]
...     targets = [example[target_lang] for example in examples["translation"]]
...     model_inputs = tokenizer(inputs, text_target=targets, max_length=128, truncation=True)
...     return model_inputs
```

Para aplicar a função de pré-processamento em todo o conjunto de dados, use o método [map](https://huggingface.co/docs/datasets/main/en/package_reference/main_classes#datasets.Dataset.map) do 🤗 Datasets. Você pode acelerar a função `map` definindo `batched=True` para processar vários elementos do conjunto de dados de uma vez:

```py
>>> tokenized_books = books.map(preprocess_function, batched=True)
```

Agora crie um lote de exemplos usando [DataCollatorForSeq2Seq](/docs/transformers/main/pt/main_classes/data_collator#transformers.DataCollatorForSeq2Seq). É mais eficiente *preencher dinamicamente* as frases até o comprimento mais longo em um lote durante a colação, em vez de preencher todo o conjunto de dados até o comprimento máximo.

```py
>>> from transformers import DataCollatorForSeq2Seq

>>> data_collator = DataCollatorForSeq2Seq(tokenizer=tokenizer, model=checkpoint)
```

## Avaliar

Incluir uma métrica durante o treinamento é frequentemente útil para avaliar o desempenho do seu modelo. Você pode carregar rapidamente um método de avaliação com a biblioteca 🤗 [Evaluate](https://huggingface.co/docs/evaluate/index). Para esta tarefa, carregue a métrica [SacreBLEU](https://huggingface.co/spaces/evaluate-metric/sacrebleu) (veja o [quick tour](https://huggingface.co/docs/evaluate/a_quick_tour) do 🤗 Evaluate para saber mais sobre como carregar e calcular uma métrica):

```py
>>> import evaluate

>>> metric = evaluate.load("sacrebleu")
```

Em seguida, crie uma função que passa suas previsões e rótulos para [compute](https://huggingface.co/docs/evaluate/main/en/package_reference/main_classes#evaluate.EvaluationModule.compute) para calcular a pontuação SacreBLEU:

```py
>>> import numpy as np

>>> def postprocess_text(preds, labels):
...     preds = [pred.strip() for pred in preds]
...     labels = [[label.strip()] for label in labels]

...     return preds, labels

>>> def compute_metrics(eval_preds):
...     preds, labels = eval_preds
...     if isinstance(preds, tuple):
...         preds = preds[0]
...     decoded_preds = tokenizer.batch_decode(preds, skip_special_tokens=True)

...     labels = np.where(labels != -100, labels, tokenizer.pad_token_id)
...     decoded_labels = tokenizer.batch_decode(labels, skip_special_tokens=True)

...     decoded_preds, decoded_labels = postprocess_text(decoded_preds, decoded_labels)

...     result = metric.compute(predictions=decoded_preds, references=decoded_labels)
...     result = {"bleu": result["score"]}

...     prediction_lens = [np.count_nonzero(pred != tokenizer.pad_token_id) for pred in preds]
...     result["gen_len"] = np.mean(prediction_lens)
...     result = {k: round(v, 4) for k, v in result.items()}
...     return result
```

Sua função `compute_metrics` está pronta para uso e você voltará a ela ao configurar o treinamento.

## Treinar

Se você não está familiarizado com o ajuste fino de um modelo usando o [Trainer](/docs/transformers/main/pt/main_classes/trainer#transformers.Trainer), dê uma olhada no tutorial básico [aqui](../training)!

Agora você está pronto para começar a treinar seu modelo! Carregue o T5 com [AutoModelForSeq2SeqLM](/docs/transformers/main/pt/model_doc/auto#transformers.AutoModelForSeq2SeqLM):

```py
>>> from transformers import AutoModelForSeq2SeqLM, Seq2SeqTrainingArguments, Seq2SeqTrainer

>>> model = AutoModelForSeq2SeqLM.from_pretrained(checkpoint)
```

Neste ponto, restam apenas três etapas:

1. Defina os hiperparâmetros de treinamento em [Seq2SeqTrainingArguments](/docs/transformers/main/pt/main_classes/trainer#transformers.Seq2SeqTrainingArguments). O único parâmetro obrigatório é `output_dir`, que especifica onde salvar seu modelo. Você enviará este modelo para o Hub definindo `push_to_hub=True` (é necessário estar conectado ao Hugging Face para enviar seu modelo). No final de cada epoch, o [Trainer](/docs/transformers/main/pt/main_classes/trainer#transformers.Trainer) avaliará a métrica SacreBLEU e salvará o checkpoint de treinamento.
2. Passe os argumentos de treinamento para [Seq2SeqTrainer](/docs/transformers/main/pt/main_classes/trainer#transformers.Seq2SeqTrainer) junto com o modelo, o conjunto de dados, o tokenizer, o data collator e a função `compute_metrics`.
3. Chame [train()](/docs/transformers/main/pt/main_classes/trainer#transformers.Trainer.train) para fazer o ajuste fino do seu modelo.

```py
>>> training_args = Seq2SeqTrainingArguments(
...     output_dir="my_awesome_opus_books_model",
...     eval_strategy="epoch",
...     learning_rate=2e-5,
...     per_device_train_batch_size=16,
...     per_device_eval_batch_size=16,
...     weight_decay=0.01,
...     save_total_limit=3,
...     num_train_epochs=2,
...     predict_with_generate=True,
...     fp16=True, #change to bf16=True for XPU
...     push_to_hub=True,
... )

>>> trainer = Seq2SeqTrainer(
...     model=model,
...     args=training_args,
...     train_dataset=tokenized_books["train"],
...     eval_dataset=tokenized_books["test"],
...     processing_class=tokenizer,
...     data_collator=data_collator,
...     compute_metrics=compute_metrics,
... )

>>> trainer.train()
```

Quando o treinamento for concluído, compartilhe seu modelo no Hub com o método [push_to_hub()](/docs/transformers/main/pt/main_classes/trainer#transformers.Trainer.push_to_hub) para que todos possam usá-lo:

```py
>>> trainer.push_to_hub()
```

Para um exemplo mais detalhado de como fazer o ajuste fino de um modelo para tradução, confira o [notebook do PyTorch](https://colab.research.google.com/github/huggingface/notebooks/blob/main/examples/translation.ipynb) correspondente.

## Inferência

Ótimo, agora que você ajustou um modelo, pode usá-lo para inferência!

Pense em algum texto que você gostaria de traduzir para outro idioma. Para o T5, você precisa prefixar sua entrada de acordo com a tarefa em que está trabalhando. Para tradução do inglês para o francês, você deve prefixar sua entrada conforme mostrado abaixo:

```py
>>> text = "translate English to French: Legumes share resources with nitrogen-fixing bacteria."
```

Tokenize o texto e retorne os `input_ids` como tensores do PyTorch:

```py
>>> from transformers import AutoTokenizer

>>> tokenizer = AutoTokenizer.from_pretrained("username/my_awesome_opus_books_model")
>>> inputs = tokenizer(text, return_tensors="pt").input_ids
```

Use o método [generate()](/docs/transformers/main/pt/main_classes/text_generation#transformers.GenerationMixin.generate) para criar a tradução. Para mais detalhes sobre as diferentes estratégias de geração de texto e os parâmetros para controlar a geração, consulte a API de [Text Generation](../main_classes/text_generation).

```py
>>> from transformers import AutoModelForSeq2SeqLM

>>> model = AutoModelForSeq2SeqLM.from_pretrained("username/my_awesome_opus_books_model")
>>> outputs = model.generate(inputs, max_new_tokens=40, do_sample=True, top_k=30, top_p=0.95)
```

Decodifique os ids de tokens gerados de volta para texto:

```py
>>> tokenizer.decode(outputs[0], skip_special_tokens=True)
'Les lignées partagent des ressources avec des bactéries enfixant l'azote.'
```

