Processo de implantação do modelo PyTorch (ONNX Runtime)

A implantação do modelo refere-se ao processo de execução de um modelo de aprendizado profundo treinado em um ambiente específico. Dificuldades enfrentadas na implantação do modelo:

  • O ambiente necessário para executar o modelo é difícil de configurar. Os modelos de aprendizado profundo geralmente são escritos por alguns frameworks, como PyTorch e TensorFlow. Devido às limitações do tamanho da estrutura e do ambiente dependente, a estrutura não é adequada para instalação em ambientes de produção, como telefones celulares e placas de desenvolvimento.
  • A estrutura do modelo de aprendizado profundo geralmente é relativamente grande, exigindo uma grande quantidade de poder de computação para atender aos requisitos de operação em tempo real, e a eficiência da operação precisa ser otimizada.

Devido a essas dificuldades, a implantação do modelo não pode ser realizada por configuração e instalação simples do ambiente. Atualmente, existe um pipeline popular para implantação de modelo:

        Para que o modelo seja finalmente implantado em um determinado ambiente, qualquer estrutura de aprendizado profundo pode ser usada para definir a estrutura da rede, e os parâmetros na rede podem ser determinados por meio de treinamento. Depois disso, a estrutura e os parâmetros do modelo serão convertidos em uma representação intermediária que apenas descreve a estrutura da rede, e algumas otimizações para a estrutura da rede serão realizadas na representação intermediária. Por fim, escrito em uma estrutura de programação de alto desempenho orientada para hardware (como CUDA, OpenCL), o mecanismo de inferência que pode executar com eficiência os operadores na rede de aprendizado profundo converterá a representação intermediária em um formato de arquivo específico e executará o modelo eficientemente na plataforma de hardware correspondente.

Criar um modelo PyTorch

a. Ambiente de configuração

#Crie um ambiente virtual chamado deploy com Python 3.7 pré-instalado
conda create -n deploy python=3.7 -y
# Entre no ambiente virtual
conda activate deploy
# Instale a versão Gpu do PyTorch
# Selecione a configuração apropriada no site oficial e copie o caminho de download --- https://pytorch.org/get-started/locally/
cconda install pytorch archvision cudatoolkit=11.3 -c pytorch
# Install ONNX Runtime, ONNX, OpenCV
pip install onnxruntime onnx opencv-python

b. Criar um modelo PyTorch

import os

import cv2
import numpy as np
import requests
import tocha
import tocha.onnx
da tocha import nn

class SuperResolutionNet(nn.Module):
    def __init__(self, upscale_factor):
        super().__init__()
        self.upscale_factor = upscale_factor
        self. img_upsampler = nn.Upsample(
            scale_factor=self.upscale_factor,
            mode='bicubic',
            align_corners=False)

        self.conv1 = nn.Conv2d(3,64,kernel_size=9,padding=4)
        self.conv2 = nn.Conv2d( 64,32,kernel_size=1,padding=0)
        self.conv3 = nn.Conv2d(32,3,kernel_size=5,padding=2)

        self.relu = nn.ReLU()

    def forward(self, x):
        x = self.img_upsampler(x)
        out = self.relu(self.conv1(x))
        out = self.relu(self.conv2(out) )
        out = self.conv3(out)
        return out

# Baixar ponto de verificação e
urls de imagem de teste = ['https://download.openmmlab.com/mmediting/restorers/srcnn/srcnn_x4k915_1x16_1000k_div2k_20200608-4186f232.pth',
        'https://raw .githubusercontent.com/open-mmlab/mmediting/master/tests/data/face/000001.png']
nomes = ['srcnn.pth', 'face.png']
para url, nome em zip (urls, nomes) :
    se não os.path.exists(name):
        open(name, 'wb').write(requests.get(url).conteúdo)

def init_torch_model():
    arch_model = SuperResolutionNet(upscale_factor=3)

    state_dict = arch.load('srcnn.pth')['state_dict']

    # Adapte o ponto de verificação
    para old_key em list(state_dict.keys()):
        new_key = '.'.join(old_key .split('.')[1:])
        state_dict[new_key] = state_dict.pop(old_key)

    maçarico_model.load_state_dict(state_dict)
    maçarico_model.eval()
    return

maçarico_modelo = init_torch_model()
input_img = cv2.imread('face. png').astype(np.float32)

# HWC para NCHW
input_img = np.transpose(input_img, [2, 0, 1])
input_img = np.expand_dims(input_img, 0)

# Inferência
maçarico_output = model(torch.from_numpy( input_img)).detach().numpy()

# NCHW para HWC
saída_da tocha = np.squeeze(saída_torch, 0)
saída_da tocha = np.clip(saída_torch, 0, 255)
saída_da tocha = np.transpose(saída_torch, [1, 2, 0]).astype(np.uint8)

# Mostrar imagem
cv2.imwrite("face_torch.png", saída_da tocha)

O código cria uma rede clássica de super-resolução SRCNN . O SRCNN primeiro aumenta a resolução da imagem para a resolução correspondente e, em seguida, processa a imagem com 3 camadas convolucionais. Se o script for executado normalmente, uma foto de super resolução do rosto será salva em face_torch.png .

Depois que o modelo PyTorch for testado corretamente, vamos começar a implantar oficialmente o modelo. Nossa próxima tarefa é converter o modelo PyTorch em um modelo descrito pela representação intermediária ONNX.

c. Converter o modelo PyTorch em um modelo descrito por ONNX

ONNX (Open Neural Network Exchange) é um formato lançado em conjunto pelo Facebook e pela Microsoft em 2017 para descrições padrão de gráficos computacionais. Atualmente, sob a manutenção conjunta de várias instituições, o ONNX acoplou-se a vários frameworks de aprendizado profundo e a vários mecanismos de inferência. Portanto, o ONNX é considerado uma ponte da estrutura de aprendizado profundo para o mecanismo de inferência, assim como a linguagem intermediária do compilador. Devido à compatibilidade diferente de várias estruturas, o ONNX geralmente é usado apenas para representar grafos estáticos mais fáceis de implantar.

#  PyTorch 的模型转换成 ONNX 格式的模型
x = torch.randn(1, 3, 256, 256)

with torch.no_grad():
    torch.onnx.export(
        model,
        x,
        "srcnn.onnx",
        opset_version=11,
        input_names=['input'],
        output_names=['output'])

其中torch.onnx.export 是 PyTorch 自带的把模型转换成 ONNX 格式的函数。前三个参数分别是要转换的模型、模型的任意一组输入、导出的 ONNX 文件的文件名。

从 PyTorch 的模型到 ONNX 的模型,PyTorch提供了一种叫做追踪(trace)的模型转换方法:给定一组输入,再实际执行一遍模型,即把这组输入对应的计算图记录下来,保存为 ONNX 格式。export 函数用的就是追踪导出方法,需要给任意一组输入,让模型跑起来。测试图片是三通道256x256 大小的,这里也构造一个同样形状的随机张量。

opset_version 表示 ONNX 算子集的版本。input_names, output_names 是输入、输出 tensor 的名称。代码运行成功,目录下会新增一个 srcnn.onnx 的 ONNX 模型文件

# 验证模型文件是否正确,直接加在前面的代码后面就行
import onnx

onnx_model = onnx.load("srcnn.onnx")
try:
    onnx.checker.check_model(onnx_model)
except Exception:
    print("Model incorrect")
else:
    print("Model correct")

d.ONNX Runtime上运行模型和推理

推理引擎-ONNX Runtime 是由微软维护的一个跨平台机器学习推理加速器。ONNX Runtime 是直接对接ONNX的,即ONNX Runtime可以直接读取并运行.onnx文件,而不需要再把.onnx格式的文件转换成其他格式的文件。也就是说,对于 PyTorch - ONNX - ONNX Runtime 这条部署流水线,只要在目标设备中得到 .onnx 文件,并在 ONNX Runtime 上运行模型,模型部署就算大功告成了。

ONNX Runtime 提供了 Python 接口。

# ONNX Runtime完成模型推理,还是在之前脚本后添加代码
import onnxruntime

ort_session = onnxruntime.InferenceSession("srcnn.onnx")
ort_inputs = {'input': input_img}
ort_output = ort_session.run(['output'], ort_inputs)[0]

ort_output = np.squeeze(ort_output, 0)
ort_output = np.clip(ort_output, 0, 255)
ort_output = np.transpose(ort_output, [1, 2, 0]).astype(np.uint8)
cv2.imwrite("face_ort.png", ort_output)

onnxruntime.InferenceSession 用于获取一个 ONNX Runtime 推理器,其参数是用于推理的 ONNX 模型文件。推理器的 run 方法用于模型推理,其第一个参数为输出张量名的列表,第二个参数为输入值的字典。其中输入值字典的 key 为张量名,value 为 numpy 类型的张量值。输入输出张量的名称需要和 torch.onnx.export 中设置的输入输出名对应。

如果代码正常运行的话,另一幅超分辨率照片会保存在 face_ort.png 中。这幅图片和刚刚得到的 face_torch.png 是一样的。即ONNX Runtime 成功运行了 SRCNN 模型,完成模型部署。

以后再想实现超分辨率的操作,只需要提供一个srcnn.onnx文件,并帮助用户配置好 ONNX Runtime 的 Python 环境,用几行代码就可以运行模型。或者可以利用 ONNX Runtime 编译出一个可以直接执行模型的应用程序。只需给用户提供 ONNX 模型文件,并让用户在应用程序选择要执行的 ONNX 模型文件名就可以运行模型了。

Acho que você gosta

Origin blog.csdn.net/xs1997/article/details/131747242
Recomendado
Clasificación