

Las traducciones son generadas a través de traducción automática. En caso de conflicto entre la traducción y la version original de inglés, prevalecerá la version en inglés.

# Paralelismo de tensores
<a name="model-parallel-extended-features-pytorch-tensor-parallelism"></a>

El *paralelismo de tensores* es un tipo de paralelismo de modelos en el que las ponderaciones, gradientes y estados del optimizador específicos del modelo se dividen entre los dispositivos. A diferencia del paralelismo por canalización, que mantiene intactos las ponderaciones individuales pero divide el *conjunto* de ponderaciones, el paralelismo de tensores divide las ponderaciones individuales. Por lo general, esto implica el cálculo distribuido de operaciones, módulos o capas específicos del modelo.

El paralelismo de tensores es necesario en los casos en los que un único parámetro consume la mayor parte de la memoria de la GPU (por ejemplo, tablas de incrustación grandes con un gran tamaño de vocabulario o una capa softmax grande con un gran número de clases). En este caso, tratar este gran tensor u operación como una unidad atómica es ineficiente e impide equilibrar la carga de memoria. 

El paralelismo de tensores también es útil para modelos extremadamente grandes en los que una canalización pura simplemente no es suficiente. Por ejemplo, con los modelos a escala GPT-3 que requieren dividir en decenas de instancias, una canalización pura por microlotes es ineficiente porque la profundidad de la canalización es demasiado alta y la sobrecarga se vuelve prohibitivamente grande.

**nota**  
El paralelismo tensorial está disponible PyTorch en la biblioteca de SageMaker modelos de paralelismo v1.6.0 y versiones posteriores.

**Topics**
+ [

# Cómo funciona el paralelismo de tensores
](model-parallel-extended-features-pytorch-tensor-parallelism-how-it-works.md)
+ [

# Ejecute un trabajo de entrenamiento en paralelo de un modelo SageMaker distribuido con Tensor Paralelism
](model-parallel-extended-features-pytorch-tensor-parallelism-examples.md)
+ [

# Soporte listo para usar para modelos Hugging Face Transformer
](model-parallel-extended-features-pytorch-hugging-face.md)
+ [

# Mecanismo de clasificación cuando se utiliza una combinación de paralelismo de canalización y paralelismo de tensores
](model-parallel-extended-features-pytorch-ranking-mechanism.md)

# Cómo funciona el paralelismo de tensores
<a name="model-parallel-extended-features-pytorch-tensor-parallelism-how-it-works"></a>

El paralelismo de tensores tiene lugar a nivel de `nn.Modules`; divide módulos específicos del modelo en rangos paralelos tensoriales. Esto se suma a la división existente del *conjunto de módulos* utilizados en el paralelismo de canalización.

Cuando un módulo se divide mediante paralelismo de tensores, se distribuye su propagación hacia adelante y hacia atrás. La biblioteca gestiona la comunicación necesaria entre los dispositivos para implementar la ejecución distribuida de estos módulos. Los módulos se dividen en varios rangos paralelos de datos. A diferencia de la distribución tradicional de cargas de trabajo, cada rango paralelo de datos **no** tiene la réplica completa del modelo cuando se utiliza el paralelismo de tensores de la biblioteca. En cambio, cada rango paralelo de datos puede tener solo una división de los módulos distribuidos, además de la totalidad de los módulos que no están distribuidos.

**Ejemplo:** considere el paralelismo de tensores en los rangos paralelos de datos, donde el grado de paralelismo de datos es 4 y el grado de paralelismo de tensores es 2. Supongamos que tiene un grupo paralelo de datos que contiene el siguiente árbol de módulos, después de dividir el conjunto de módulos.

```
A
├── B
|   ├── E
|   ├── F
├── C
└── D
    ├── G
    └── H
```

Supongamos que el paralelismo de tensores es compatible con los módulos B, G y H. Un posible resultado de la división tensorial paralela de este modelo podría ser:

```
dp_rank 0 (tensor parallel rank 0): A, B:0, C, D, G:0, H
dp_rank 1 (tensor parallel rank 1): A, B:1, C, D, G:1, H
dp_rank 2 (tensor parallel rank 0): A, B:0, C, D, G:0, H
dp_rank 3 (tensor parallel rank 1): A, B:1, C, D, G:1, H
```

Cada línea representa el conjunto de módulos almacenados en ese `dp_rank`, y la notación `X:y` representa la fracción `y` del módulo `X`. Tenga en cuenta lo siguiente:

1. La división se lleva a cabo en subconjuntos de rangos paralelos de datos, que llamamos `TP_GROUP`, no todo el `DP_GROUP`, de modo que la división exacta del modelo se replica en `dp_rank` 0 y `dp_rank` 2, y de manera similar en `dp_rank` 1 y `dp_rank` 3.

1. Los módulos `E` y `F` ya no forman parte del modelo, ya que su módulo principal `B` está dividido, así como cualquier ejecución que sea normalmente una parte de `E` y `F` se lleva a cabo dentro del módulo `B` (dividido).

1. Si bien `H` es compatible con el paralelismo de tensores, en este ejemplo no está dividido, lo que pone de relieve que la posibilidad de dividir un módulo depende de la entrada del usuario. El hecho de que un módulo sea compatible con el paralelismo de tensores no significa necesariamente que esté dividido.

## Cómo adapta la biblioteca el PyTorch `nn.Linear` paralelismo tensorial al módulo
<a name="model-parallel-extended-for-pytorch-adapt-to-module"></a>

Cuando el paralelismo de tensores se realiza sobre rangos paralelos de datos, un subconjunto de los parámetros, gradientes y estados del optimizador se divide en los dispositivos tensoriales paralelos *para los módulos que están divididos.* En cuanto al resto de módulos, los dispositivos paralelos tensores funcionan de forma paralela y regular. Para ejecutar el módulo dividido, un dispositivo primero recopila las partes necesarias de *todas las muestras de datos* de los dispositivos homólogos del mismo grupo de paralelismo de tensores. Luego, el dispositivo ejecuta la fracción local del módulo en todas estas muestras de datos, seguida de otra ronda de sincronización que combina las partes de la salida de cada muestra de datos y devuelve las muestras de datos combinadas a la fuente de donde se originó la muestra GPUs de datos por primera vez. La siguiente figura muestra un ejemplo de este proceso en un módulo `nn.Linear` dividido. 

![\[Dos figuras que muestran dos conceptos de paralelismo de tensores.\]](http://docs.aws.amazon.com/es_es/sagemaker/latest/dg/images/distributed/model-parallel/tensor-parallel-concept.png)


La primera figura muestra un modelo pequeño con un módulo `nn.Linear`grande con paralelismo de datos en los dos rangos de paralelismo de tensores. El módulo `nn.Linear` se replica en los dos rangos paralelos. 

La segunda figura muestra el paralelismo de tensores aplicado a un modelo más grande mientras se divide el módulo `nn.Linear`. Cada `tp_rank` contiene la mitad del módulo lineal y la totalidad del resto de las operaciones. Mientras se ejecuta el módulo lineal, cada `tp_rank` recopila la mitad correspondiente de todas las muestras de datos y la pasa a través de su mitad del módulo `nn.Linear`. El resultado debe estar disperso y reducido (con la suma como operación de reducción) para que cada rango tenga la salida lineal final de sus propias muestras de datos. El resto del modelo se ejecuta de forma paralela a los datos típicos.

# Ejecute un trabajo de entrenamiento en paralelo de un modelo SageMaker distribuido con Tensor Paralelism
<a name="model-parallel-extended-features-pytorch-tensor-parallelism-examples"></a>

En esta sección, aprenderá lo siguiente:
+ Cómo configurar un SageMaker PyTorch estimador y la opción de paralelismo del SageMaker modelo para utilizar el paralelismo tensorial.
+ Cómo adaptar el script de su entrenamiento mediante los módulos `smdistributed.modelparallel` ampliados para el paralelismo de tensores.

Para obtener más información sobre los `smdistributed.modelparallel` módulos, consulte el [SageMaker modelo parallel APIs](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smd_model_parallel.html) en la *documentación del SDK de SageMaker Python*.

**Topics**
+ [

## Paralelismo tensorial por sí solo
](#model-parallel-extended-features-pytorch-tensor-parallelism-alone)
+ [

## Paralelismo tensorial combinado con paralelismo de canalización
](#model-parallel-extended-features-pytorch-tensor-and-pipeline-parallelism)

## Paralelismo tensorial por sí solo
<a name="model-parallel-extended-features-pytorch-tensor-parallelism-alone"></a>

A continuación se muestra un ejemplo de una opción de entrenamiento distribuido para activar solo el paralelismo de tensores, sin el paralelismo de canalización. Configure los `smp_options` diccionarios `mpi_options` y para especificar las opciones de entrenamiento distribuidas en el SageMaker `PyTorch` estimador.

**nota**  
Las funciones ampliadas de ahorro de memoria están disponibles a través de Deep Learning Containers for PyTorch, que implementa la biblioteca de paralelismo de SageMaker modelos v1.6.0 o posterior.

**Configure un estimador SageMaker PyTorch **

```
mpi_options = {
    "enabled" : True,
    "processes_per_host" : 8,               # 8 processes
    "custom_mpi_options" : "--mca btl_vader_single_copy_mechanism none "
}
               
smp_options = {
    "enabled":True,
    "parameters": {
        "pipeline_parallel_degree": 1,    # alias for "partitions"
        "placement_strategy": "cluster",
        "tensor_parallel_degree": 4,      # tp over 4 devices
        "ddp": True
    }
}
              
smp_estimator = PyTorch(
    entry_point='your_training_script.py', # Specify
    role=role,
    instance_type='ml.p3.16xlarge',
    sagemaker_session=sagemaker_session,
    framework_version='1.13.1',
    py_version='py36',
    instance_count=1,
    distribution={
        "smdistributed": {"modelparallel": smp_options},
        "mpi": mpi_options
    },
    base_job_name="SMD-MP-demo",
)

smp_estimator.fit('s3://my_bucket/my_training_data/')
```

**sugerencia**  
Para encontrar una lista completa de parámetros`distribution`, consulte Parámetros de [configuración para el paralelismo de modelos](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smd_model_parallel_general.html) en la documentación del SDK de SageMaker Python.

**Adapta tu guion de entrenamiento PyTorch **

El siguiente ejemplo de guion de entrenamiento muestra cómo adaptar la biblioteca de paralelismo de SageMaker modelos a un guion de entrenamiento. En este ejemplo, se asume que el script se llama `your_training_script.py`. 

```
import torch
import torch.nn as nn
import torch.nn.functional as F
import torch.optim as optim
from torchnet.dataset import SplitDataset
from torchvision import datasets

import smdistributed.modelparallel.torch as smp

class Net(nn.Module):
    def __init__(self):
        super(Net, self).__init__()
        self.conv1 = nn.Conv2d(1, 32, 3, 1)
        self.conv2 = nn.Conv2d(32, 64, 3, 1)
        self.fc1 = nn.Linear(9216, 128)
        self.fc2 = nn.Linear(128, 10)

    def forward(self, x):
        x = self.conv1(x)
        x = F.relu(x)
        x = self.conv2(x)
        x = F.relu(x)
        x = F.max_pool2d(x, 2)
        x = torch.flatten(x, 1)
        x = self.fc1(x)
        x = F.relu(x)
        x = self.fc2(x)
        return F.log_softmax(x, 1)

def train(model, device, train_loader, optimizer):
    model.train()
    for batch_idx, (data, target) in enumerate(train_loader):
        # smdistributed: Move input tensors to the GPU ID used by
        # the current process, based on the set_device call.
        data, target = data.to(device), target.to(device)
        optimizer.zero_grad()
        output = model(data)
        loss = F.nll_loss(output, target, reduction="mean")
        loss.backward()
        optimizer.step()

# smdistributed: Initialize the backend
smp.init()

# smdistributed: Set the device to the GPU ID used by the current process.
# Input tensors should be transferred to this device.
torch.cuda.set_device(smp.local_rank())
device = torch.device("cuda")

# smdistributed: Download only on a single process per instance.
# When this is not present, the file is corrupted by multiple processes trying
# to download and extract at the same time
if smp.local_rank() == 0:
    dataset = datasets.MNIST("../data", train=True, download=False)
smp.barrier()

# smdistributed: Shard the dataset based on data parallel ranks
if smp.dp_size() > 1:
    partitions_dict = {f"{i}": 1 / smp.dp_size() for i in range(smp.dp_size())}
    dataset = SplitDataset(dataset, partitions=partitions_dict)
    dataset.select(f"{smp.dp_rank()}")

train_loader = torch.utils.data.DataLoader(dataset, batch_size=64)

# smdistributed: Enable tensor parallelism for all supported modules in the model
# i.e., nn.Linear in this case. Alternatively, we can use
# smp.set_tensor_parallelism(model.fc1, True)
# to enable it only for model.fc1
with smp.tensor_parallelism():
    model = Net()

# smdistributed: Use the DistributedModel wrapper to distribute the
# modules for which tensor parallelism is enabled
model = smp.DistributedModel(model)

optimizer = optim.AdaDelta(model.parameters(), lr=4.0)
optimizer = smp.DistributedOptimizer(optimizer)

train(model, device, train_loader, optimizer)
```

## Paralelismo tensorial combinado con paralelismo de canalización
<a name="model-parallel-extended-features-pytorch-tensor-and-pipeline-parallelism"></a>

El siguiente es un ejemplo de una opción de entrenamiento distribuida que permite combinar el paralelismo tensorial con el paralelismo en canalización. Configure los `smp_options` parámetros `mpi_options` y para especificar las opciones paralelas del modelo con paralelismo tensorial al configurar un estimador. SageMaker `PyTorch`

**nota**  
Las funciones ampliadas de ahorro de memoria están disponibles a través de Deep Learning Containers for PyTorch, que implementa la biblioteca de paralelismo de SageMaker modelos v1.6.0 o posterior.

**Configure un estimador SageMaker PyTorch **

```
mpi_options = {
    "enabled" : True,
    "processes_per_host" : 8,               # 8 processes
    "custom_mpi_options" : "--mca btl_vader_single_copy_mechanism none "
}
               
smp_options = {
    "enabled":True,
    "parameters": {
    "microbatches": 4,
        "pipeline_parallel_degree": 2,    # alias for "partitions"
        "placement_strategy": "cluster",
        "tensor_parallel_degree": 2,      # tp over 2 devices
        "ddp": True
    }
}
              
smp_estimator = PyTorch(
    entry_point='your_training_script.py', # Specify
    role=role,
    instance_type='ml.p3.16xlarge',
    sagemaker_session=sagemaker_session,
    framework_version='1.13.1',
    py_version='py36',
    instance_count=1,
    distribution={
        "smdistributed": {"modelparallel": smp_options},
        "mpi": mpi_options
    },
    base_job_name="SMD-MP-demo",
)

smp_estimator.fit('s3://my_bucket/my_training_data/')  
```

<a name="model-parallel-extended-features-pytorch-tensor-and-pipeline-parallelism-script"></a>**Adapta tu guion de entrenamiento PyTorch **

El siguiente ejemplo de guion de entrenamiento muestra cómo adaptar la biblioteca de paralelismo de SageMaker modelos a un guion de entrenamiento. Tenga en cuenta que el script de entrenamiento ahora incluye el decorador `smp.step`: 

```
import torch
import torch.nn as nn
import torch.nn.functional as F
import torch.optim as optim
from torchnet.dataset import SplitDataset
from torchvision import datasets

import smdistributed.modelparallel.torch as smp

class Net(nn.Module):
    def __init__(self):
        super(Net, self).__init__()
        self.conv1 = nn.Conv2d(1, 32, 3, 1)
        self.conv2 = nn.Conv2d(32, 64, 3, 1)
        self.fc1 = nn.Linear(9216, 128)
        self.fc2 = nn.Linear(128, 10)

    def forward(self, x):
        x = self.conv1(x)
        x = F.relu(x)
        x = self.conv2(x)
        x = F.relu(x)
        x = F.max_pool2d(x, 2)
        x = torch.flatten(x, 1)
        x = self.fc1(x)
        x = F.relu(x)
        x = self.fc2(x)
        return F.log_softmax(x, 1)


# smdistributed: Define smp.step. Return any tensors needed outside.
@smp.step
def train_step(model, data, target):
    output = model(data)
    loss = F.nll_loss(output, target, reduction="mean")
    model.backward(loss)
    return output, loss

def train(model, device, train_loader, optimizer):
    model.train()
    for batch_idx, (data, target) in enumerate(train_loader):
        # smdistributed: Move input tensors to the GPU ID used by
        # the current process, based on the set_device call.
        data, target = data.to(device), target.to(device)
        optimizer.zero_grad()
        # Return value, loss_mb is a StepOutput object
        _, loss_mb = train_step(model, data, target)

        # smdistributed: Average the loss across microbatches.
        loss = loss_mb.reduce_mean()

        optimizer.step()

# smdistributed: Initialize the backend
smp.init()

# smdistributed: Set the device to the GPU ID used by the current process.
# Input tensors should be transferred to this device.
torch.cuda.set_device(smp.local_rank())
device = torch.device("cuda")

# smdistributed: Download only on a single process per instance.
# When this is not present, the file is corrupted by multiple processes trying
# to download and extract at the same time
if smp.local_rank() == 0:
    dataset = datasets.MNIST("../data", train=True, download=False)
smp.barrier()

# smdistributed: Shard the dataset based on data parallel ranks
if smp.dp_size() > 1:
    partitions_dict = {f"{i}": 1 / smp.dp_size() for i in range(smp.dp_size())}
    dataset = SplitDataset(dataset, partitions=partitions_dict)
    dataset.select(f"{smp.dp_rank()}")

# smdistributed: Set drop_last=True to ensure that batch size is always divisible
# by the number of microbatches
train_loader = torch.utils.data.DataLoader(dataset, batch_size=64, drop_last=True)

model = Net()

# smdistributed: enable tensor parallelism only for model.fc1
smp.set_tensor_parallelism(model.fc1, True)

# smdistributed: Use the DistributedModel container to provide the model
# to be partitioned across different ranks. For the rest of the script,
# the returned DistributedModel object should be used in place of
# the model provided for DistributedModel class instantiation.
model = smp.DistributedModel(model)

optimizer = optim.AdaDelta(model.parameters(), lr=4.0)
optimizer = smp.DistributedOptimizer(optimizer)

train(model, device, train_loader, optimizer)
```

# Soporte listo para usar para modelos Hugging Face Transformer
<a name="model-parallel-extended-features-pytorch-hugging-face"></a>

El paralelismo tensorial de la biblioteca de paralelismo de SageMaker modelos es compatible con los siguientes modelos de Hugging Face out-of-the-box Transformer:
+ GPT-2, BERT y Ro BERTa (disponibles en la biblioteca de paralelismo de modelos v1.7.0 y versiones posteriores) SageMaker 
+ GPT-J (disponible en la biblioteca de paralelismo de modelos v1.8.0 y versiones posteriores) SageMaker 
+ GPT-neo (disponible en la biblioteca de paralelismo de modelos v1.10.0 y versiones posteriores) SageMaker 

**nota**  
Para cualquier otro modelo de Transformers, debe usar la API [smdistributed.modelparallel.torch.tp\$1register\$1with\$1module ()](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smp_versions/latest/smd_model_parallel_pytorch_tensor_parallel.html#smdistributed.modelparallel.torch.tp_register_with_module) para aplicar el paralelismo de tensores.

**nota**  
Para usar el paralelismo tensorial para entrenar modelos de Hugging Face Transformer, asegúrate de usar Hugging Face Deep Learning Containers, que tengan la biblioteca de paralelismo de modelos PyTorch v1.7.0 y versiones posteriores. SageMaker [Para obtener más información, consulte las notas de versión de la biblioteca de paralelismo de modelos. SageMaker ](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smd_model_parallel_release_notes/smd_model_parallel_change_log.html)

## Modelos compatibles listos para usar
<a name="model-parallel-extended-features-pytorch-hugging-face-out-of-the-box"></a>

Para los modelos de transformadores Hugging Face compatibles con la biblioteca listos para usar, no es necesario implementar ganchos manualmente para traducir APIs Transformer `smdistributed` a capas de transformadores. [Puedes activar el paralelismo tensorial usando el administrador de contexto smdistributed.modelparallel.torch.tensor\$1parallelism () y empaquetando el modelo con [smdistributed.modelparallel.torch](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smp_versions/latest/smd_model_parallel_pytorch_tensor_parallel.html#smdistributed.modelparallel.torch.tensor_parallelism). DistributedModel().](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smp_versions/latest/smd_model_parallel_pytorch.html#smdistributed.modelparallel.torch.DistributedModel) No necesita registrar manualmente los enlaces para el paralelismo de los tensores mediante la API `smp.tp_register`.

Es posible acceder a las funciones de traducción `state_dict` entre Hugging Face Transformers y `smdistributed.modelparallel` de la siguiente manera.
+  `smdistributed.modelparallel.torch.nn.huggingface.gpt2.translate_state_dict_to_hf_gpt2(state_dict, max_seq_len=None)`
+  `smdistributed.modelparallel.torch.nn.huggingface.gpt2.translate_hf_state_dict_to_smdistributed_gpt2(state_dict)` 
+  `smdistributed.modelparallel.torch.nn.huggingface.bert.translate_state_dict_to_hf_bert(state_dict, max_seq_len=None)` 
+  `smdistributed.modelparallel.torch.nn.huggingface.bert.translate_hf_state_dict_to_smdistributed_bert(state_dict)` 
+  `smdistributed.modelparallel.torch.nn.huggingface.roberta.translate_state_dict_to_hf_roberta(state_dict, max_seq_len=None)` 
+  `smdistributed.modelparallel.torch.nn.huggingface.roberta.translate_hf_state_dict_to_smdistributed_roberta(state_dict)` 
+ `smdistributed.modelparallel.torch.nn.huggingface.gptj.translate_state_dict_to_hf_gptj(state_dict, max_seq_len=None)`(Disponible en la biblioteca de paralelismo de SageMaker modelos v1.8.0 y versiones posteriores)
+ `smdistributed.modelparallel.torch.nn.huggingface.gptj.translate_hf_gptj_state_dict_to_smdistributed_gptj`(Disponible en la biblioteca de paralelismo de SageMaker modelos v1.8.0 y versiones posteriores)
+ `smdistributed.modelparallel.torch.nn.huggingface.gptneo.translate_state_dict_to_hf_gptneo(state_dict, max_seq_len=None)`(Disponible en la biblioteca de paralelismo de SageMaker modelos v1.10.0 y versiones posteriores)
+ `smdistributed.modelparallel.torch.nn.huggingface.gptneo.translate_hf_state_dict_to_smdistributed_gptneo(state_dict)`(Disponible en la biblioteca de paralelismo de SageMaker modelos v1.10.0 y versiones posteriores)

**Ejemplo de uso de la característica de traducción GPT-2**

Comience por encapsular el modelo tal y como se muestra en el siguiente código.

```
from transformers import AutoModelForCausalLM

with smp.tensor_parallelism():
    model = AutoModelForCausalLM.from_config(hf_gpt2_config)

model = smp.DistributedModel(model)
```

Dado un `state_dict` del objeto `DistributedModel`, puede cargar las ponderaciones en el modelo original de Hugging Face GPT-2 usando la característica `translate_state_dict_to_hf_gpt2` como se muestra en el siguiente código.

```
from smdistributed.modelparallel.torch.nn.huggingface.gpt2 \
                                      import translate_state_dict_to_hf_gpt2
max_seq_len = 1024

# [... code block for training ...]

if smp.rdp_rank() == 0:
    state_dict = dist_model.state_dict()
    hf_state_dict = translate_state_dict_to_hf_gpt2(state_dict, max_seq_len)

    # can now call model.load_state_dict(hf_state_dict) to the original HF model
```

**Ejemplo de uso de la función de traducción Ro BERTa **

Del mismo modo, dado un HuggingFace modelo compatible`state_dict`, puede utilizar la `translate_hf_state_dict_to_smdistributed` función para convertirla a un formato legible`smp.DistributedModel`. Esto puede ser útil en casos de uso de transferencia de aprendizaje, donde un modelo preentrenado se carga en un `smp.DistributedModel` para un ajuste paralelo modelo.

```
from smdistributed.modelparallel.torch.nn.huggingface.roberta \
                                      import translate_state_dict_to_smdistributed

model = AutoModelForMaskedLM.from_config(roberta_config)
model = smp.DistributedModel(model)

pretrained_model = AutoModelForMaskedLM.from_pretrained("roberta-large")
translated_state_dict =
        translate_state_dict_to_smdistributed(pretrained_model.state_dict())

# load the translated pretrained weights into the smp.DistributedModel
model.load_state_dict(translated_state_dict)

# start fine-tuning...
```

# Mecanismo de clasificación cuando se utiliza una combinación de paralelismo de canalización y paralelismo de tensores
<a name="model-parallel-extended-features-pytorch-ranking-mechanism"></a>

En esta sección se explica cómo funciona el mecanismo de clasificación del paralelismo de modelos con el paralelismo de tensores. Esto es una extensión de los conceptos [básicos de clasificación](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smd_model_parallel_general.html#ranking-basics) para [Características principales de la biblioteca de paralelismo de SageMaker modelos](model-parallel-core-features.md). Con el paralelismo tensorial, la biblioteca presenta tres tipos de clasificación y grupo de procesos: para el rango paralelo `smp.tp_rank()` tensorial, APIs para el rango paralelo de `smp.pp_rank()` canalización y para `smp.rdp_rank()` el rango paralelo de datos reducidos. Los grupos de proceso de comunicación correspondientes son grupo paralelo tensorial (`TP_GROUP`), grupo paralelo de canalización (`PP_GROUP`) y grupo paralelo de datos reducidos (`RDP_GROUP`). Estos grupos se definen de la siguiente manera:
+ Un *grupo paralelo tensorial* (`TP_GROUP`) es un subconjunto uniformemente divisible del grupo paralelo de datos, sobre el cual tiene lugar la distribución tensorial paralela de los módulos. Cuando el grado de paralelismo de la canalización es 1, `TP_GROUP` es el mismo que el del *grupo paralelo modelo* (`MP_GROUP`). 
+ Un *grupo paralelo de canalización* (`PP_GROUP`) es el grupo de procesos sobre los que tiene lugar el paralelismo de canalización. Cuando el grado de paralelismo de tensores es 1, `PP_GROUP` es igual que `MP_GROUP`. 
+ Un *grupo paralelo de datos reducidos* (`RDP_GROUP`) es un conjunto de procesos que contienen las mismas particiones de paralelismo de canalización y las mismas particiones paralelas tensoriales, y realizan paralelismo de datos entre sí. Esto se denomina grupo paralelo de datos reducido porque es un subconjunto de todo el grupo de paralelismo de datos, `DP_GROUP`. Para los parámetros del modelo que se distribuyen dentro del `TP_GROUP`, la operación `allreduce` del gradiente se realiza solo para el grupo paralelo de datos reducidos, mientras que para los parámetros que no están distribuidos, el gradiente `allreduce` se produce en todo el grupo `DP_GROUP`. 
+ Un grupo paralelo de modelos (`MP_GROUP`) se refiere a un grupo de procesos que almacenan colectivamente todo el modelo. Consiste en la unión de los `PP_GROUP`s de todos los rangos que se encuentran en el `TP_GROUP` del proceso actual. Cuando el grado de paralelismo de tensores es 1, `MP_GROUP` equivale a `PP_GROUP`. También es coherente con la definición existente de `MP_GROUP` de versiones anteriores de `smdistributed`. Tenga en cuenta que el actual `TP_GROUP` es un subconjunto del actual `DP_GROUP` y del actual `MP_GROUP`. 

*Para obtener más información sobre el proceso de comunicación APIs en la biblioteca de paralelismo de SageMaker modelos, consulta la [API común](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smp_versions/latest/smd_model_parallel_common_api.html#) y la específica [PyTorchen la documentación del SDK de APIs](https://sagemaker.readthedocs.io/en/v2.199.0/api/training/smp_versions/latest/smd_model_parallel_pytorch.html) PythonSageMaker .*

![\[Mecanismo de clasificación, distribución de parámetros y AllReduce operaciones asociadas del paralelismo tensorial.\]](http://docs.aws.amazon.com/es_es/sagemaker/latest/dg/images/distributed/model-parallel/tensor-parallel-ranking-mechanism.png)


Por ejemplo, considere los grupos de procesos para un solo nodo con 8 GPUs, donde el grado de paralelismo tensorial es 2, el grado de paralelismo de canalización es 2 y el grado de paralelismo de datos es 4. La parte central superior de la figura anterior muestra un ejemplo de un modelo con 4 capas. Las partes inferior izquierda e inferior derecha de la figura ilustran el modelo de 4 capas distribuido en 4 GPUs utilizando tanto el paralelismo de canalización como el paralelismo tensorial, donde el paralelismo tensorial se usa para las dos capas centrales. Estas dos figuras inferiores son copias simples para ilustrar diferentes líneas de límite de grupo. El modelo particionado se replica para lograr un paralelismo de datos entre 0-3 y 4-7. GPUs La figura inferior izquierda muestra las definiciones de `MP_GROUP`, `PP_GROUP` y `TP_GROUP`. La figura inferior derecha muestra`RDP_GROUP`, `DP_GROUP` y sobre el mismo conjunto de. `WORLD` GPUs Los gradientes de las capas y los sectores de capas que tienen el mismo color están agrupados en `allreduce` para obtener un paralelismo de datos. Por ejemplo, en la primera capa (azul claro) se transmiten las operaciones `allreduce` en `DP_GROUP`, mientras que en el segmento naranja oscuro de la segunda capa solo se transmiten las operaciones `allreduce` de dentro del `RDP_GROUP` de su proceso. Las flechas de color rojo oscuro en negrita representan los tensores con el lote completo `TP_GROUP`.

```
GPU0: pp_rank 0, tp_rank 0, rdp_rank 0, dp_rank 0, mp_rank 0
GPU1: pp_rank 1, tp_rank 0, rdp_rank 0, dp_rank 0, mp_rank 1
GPU2: pp_rank 0, tp_rank 1, rdp_rank 0, dp_rank 1, mp_rank 2
GPU3: pp_rank 1, tp_rank 1, rdp_rank 0, dp_rank 1, mp_rank 3
GPU4: pp_rank 0, tp_rank 0, rdp_rank 1, dp_rank 2, mp_rank 0
GPU5: pp_rank 1, tp_rank 0, rdp_rank 1, dp_rank 2, mp_rank 1
GPU6: pp_rank 0, tp_rank 1, rdp_rank 1, dp_rank 3, mp_rank 2
GPU7: pp_rank 1, tp_rank 1, rdp_rank 1, dp_rank 3, mp_rank 3
```

En este ejemplo, el paralelismo de canalización se produce entre los pares de GPU (0,1); (2,3); (4,5) y (6,7). Además, el paralelismo de datos (`allreduce`) tiene lugar en GPUs 0, 2, 4, 6 e independientemente en GPUs 1, 3, 5 y 7. El paralelismo de tensores se produce en subconjuntos de `DP_GROUP`s, en los pares de GPU (0,2); (1,3); (4,6) y (5,7).

  Para este tipo de paralelismo híbrido entre canalización y tensor, la matemática para `data_parallel_degree` sigue siendo `data_parallel_degree = number_of_GPUs / pipeline_parallel_degree`. La biblioteca calcula además el grado de paralelismo de datos reducidos a partir de la siguiente relación `reduced_data_parallel_degree * tensor_parallel_degree = data_parallel_degree`.  