[Implantação de modelo] Tutorial de introdução (3): Explicação detalhada de PyTorch para ONNX

Tutorial introdutório de implantação de modelo (3): Explicação detalhada de PyTorch para ONNX - Zhihu (zhihu.com)

Nos dois tutoriais anteriores , levamos todos a implantar com sucesso o primeiro modelo e resolvemos algumas dificuldades que podem ser encontradas na implantação do modelo. A partir de hoje, apresentaremos o conhecimento relacionado ao ONNX do superficial ao profundo. ONNX é atualmente uma das representações intermediárias mais importantes para implantação de modelos. Depois de aprender os detalhes técnicos do ONNX, você pode evitar muitos problemas de implantação de modelo.
Ao converter um modelo PyTorch em um modelo ONNX, geralmente precisamos chamar apenas uma frase facilmente torch.onnx.export. A interface desta função parece simples, mas existem muitas "regras ocultas" em seu uso. Neste tutorial, apresentaremos o princípio e as precauções de conversão do modelo PyTorch para o modelo ONNX em detalhes. Além disso, também apresentaremos a correspondência do operador entre PyTorch e ONNX para ensiná-lo a lidar com problemas de suporte do operador que podem ser encontrados durante a conversão do modelo PyTorch.

Uma prévia: nos artigos a seguir, continuaremos apresentando como oferecer suporte a mais operadores ONNX no PyTorch, para que todos possam percorrer completamente a rota de implantação do PyTorch para o ONNX; apresentar o conhecimento do próprio ONNX e modificar e depurar o ONNX. abordagem comum para o modelo permite que você resolva a maioria dos problemas de implantação relacionados ao ONNX sozinho. Fique atento ~

torch.onnx.export Discriminação


Nesta seção, apresentaremos a função de conversão de PyTorch para ONNX em detalhes -  torch.onnx.export. Esperamos que você possa usar esta interface de conversão de modelo com mais flexibilidade e entender seu princípio de implementação para lidar melhor com o erro desta função (devido à compatibilidade de implantação de modelo, esta função geralmente relata erros ao implantar modelos complexos).


Método de exportação do gráfico de cálculo

TorchScript  é um formato para serializar e otimizar modelos PyTorch. Durante a otimização, um modelo é convertido em um modelo torch.nn.ModuleTorchScript  . torch.jit.ScriptModuleAgora, o TorchScript também é frequentemente usado como uma representação intermediária. Temos uma introdução detalhada ao TorchScript em outros artigos ( Interpretação do TorchScript (1): Conhecendo o TorchScript pela primeira vez - Zhihu ), e a introdução do TorchScript aqui é usada apenas para ilustrar o princípio de conversão de modelos PyTorch em ONNX.
torch.onnx.exportO modelo necessário é, na verdade, um arquivo torch.jit.ScriptModule. Para converter o modelo PyTorch comum em um modelo TorchScript, existem dois métodos de exportação do gráfico de cálculo: rastreamento e script. Se torch.onnx.exportum modelo PyTorch normal ( torch.nn.Module) for passado, o modelo será exportado usando o método trace por padrão. Esse processo é mostrado na figura abaixo:

Lembre-se do conhecimento do nosso primeiro tutorial : o método de rastreamento só pode exportar o gráfico estático do modelo executando o modelo uma vez, ou seja, não pode identificar o fluxo de controle (como loops) no modelo; o método de gravação pode corretamente registre todo o fluxo de controle. Vamos pegar o código a seguir como exemplo para ver a diferença entre esses dois métodos de conversão:

import torch 
 
class Model(torch.nn.Module): 
    def __init__(self, n): 
        super().__init__() 
        self.n = n 
        self.conv = torch.nn.Conv2d(3, 3, 3) 
 
    def forward(self, x): 
        for i in range(self.n): 
            x = self.conv(x) 
        return x 
 
 
models = [Model(2), Model(3)] 
model_names = ['model_2', 'model_3'] 
 
for model, model_name in zip(models, model_names): 
    dummy_input = torch.rand(1, 3, 10, 10) 
    dummy_output = model(dummy_input) 
    model_trace = torch.jit.trace(model, dummy_input) 
    model_script = torch.jit.script(model) 
 
    # 跟踪法与直接 torch.onnx.export(model, ...)等价 
    torch.onnx.export(model_trace, dummy_input, f'{model_name}_trace.onnx', example_outputs=dummy_output) 
    # 记录法必须先调用 torch.jit.sciprt 
    torch.onnx.export(model_script, dummy_input, f'{model_name}_script.onnx', example_outputs=dummy_output) 

Neste código, definimos um modelo com um loop e o modelo ncontrola o número de vezes que o tensor de entrada é convoluído por meio de parâmetros. Depois, cada um de nós criou um modelo de n=2e n=3. Exportamos esses dois modelos por métodos de rastreamento e gravação, respectivamente.
Vale ressaltar que como os dois modelos ( model_tracemodel_script) aqui são modelos TorchScript, exporta função não precisa rodar o modelo novamente. (Se o modelo for obtido usando o método de rastreamento, torch.jit.traceele será executado uma vez durante a execução; e quando o método de gravação for usado para exportar, o modelo não precisa ser realmente executado) dummy_inputO e` nos parâmetros dummy_outputsão apenas para obter o tipo de tensores de entrada e saída e forma.
Execute o código acima, visualizamos os 4 arquivos onnx obtidos com o Netron:

Primeiro, observe a estrutura do modelo ONNX obtida pelo método de rastreamento. Pode-se ver que  na estrutura do modelo ONNX é diferente para diferentes modelos.

Com o método de gravação, o modelo ONNX final usa  Loop nós para representar loops. Desta forma, mesmo para diferentes  n, os modelos ONNX possuem a mesma estrutura.

A versão do PyTorch usada neste artigo é 1.8.2. De acordo com o feedback, outras versões do PyTorch podem obter resultados diferentes.

Como o mecanismo de inferência suporta melhor gráficos estáticos, geralmente não precisamos converter explicitamente o modelo PyTorch em um modelo TorchScript ao implantar o modelo e podemos exportar diretamente o modelo PyTorch com trace  torch.onnx.export . Entender essa parte do conhecimento é principalmente localizar melhor se o problema ocorre no estágio PyTorch para TorchScript quando o erro de conversão do modelo é relatado.

Explicação do parâmetro

Depois de entender o princípio da função de conversão, vamos apresentar a função dos principais parâmetros da função em detalhes. Apresentaremos principalmente como cada parâmetro deve ser definido em diferentes cenários de implantação de modelo do ponto de vista do aplicativo, em vez de listar todos os métodos de configuração de cada parâmetro. Para obter a documentação API detalhada desta função, consulte:  arch.onnx ‒ A documentação do PyTorch 1.11.0 é definida no arquivo da seguinte forma
torch.onnx.export : torch.onnx.__init__.py

def export(model, args, f, export_params=True, verbose=False, training=TrainingMode.EVAL, 
           input_names=None, output_names=None, aten=False, export_raw_ir=False, 
           operator_export_type=None, opset_version=None, _retain_param_name=True, 
           do_constant_folding=True, example_outputs=None, strip_doc_string=True, 
           dynamic_axes=None, keep_initializers_as_inputs=None, custom_opsets=None, 
           enable_onnx_checker=True, use_external_data_format=False): 

Os três primeiros parâmetros obrigatórios são o modelo, a entrada do modelo e o nome do arquivo onnx exportado. Já estamos familiarizados com esses parâmetros. Vamos nos concentrar em alguns dos parâmetros opcionais comumente usados ​​mais tarde.

export_params

Se os pesos do modelo devem ser armazenados no modelo. Geralmente, a representação intermediária contém dois tipos de informações: estrutura do modelo e peso do modelo.Esses dois tipos de informações podem ser armazenados no mesmo arquivo ou armazenados em arquivos separados. O ONNX usa o mesmo arquivo para representar a estrutura e o peso do modelo de registro.
Geralmente, padronizamos esse parâmetro como True quando implantamos. Se o arquivo onnx for usado para transferir modelos entre estruturas diferentes (como PyTorch para Tensorflow) em vez de implantação, esse parâmetro poderá ser definido como Falso.

nomes_de_entrada, nomes_de_saída

Defina os nomes dos tensores de entrada e saída. Se não for definido, algum nome simples (como um número) será atribuído automaticamente.
Cada tensor de entrada e saída de um modelo ONNX tem um nome. Quando muitos mecanismos de inferência executam arquivos ONNX, eles precisam inserir dados na forma de pares de dados "nome-tensor" e obter dados de saída de acordo com o nome do tensor de saída. Ao fazer configurações relacionadas ao tensor (como adicionar dimensões dinâmicas), você também precisa saber o nome do tensor.
No pipeline de implantação real, todos precisamos definir os nomes dos tensores de entrada e saída e garantir que o ONNX e o mecanismo de inferência usem o mesmo conjunto de nomes.

opset_version

A qual versão do conjunto do operador ONNX se referir ao converter, o padrão é 9. A correspondência do operador entre PyTorch e ONNX será apresentada em detalhes posteriormente.

dynamic_axes

Especifica quais dimensões dos tensores de entrada e saída são dinâmicas.
Para buscar a eficiência, o padrão do ONNX é que todos os tensores envolvidos na operação sejam estáticos (a forma do tensor não muda). Mas em aplicações práticas, esperamos que o tensor de entrada do modelo seja dinâmico, especialmente o modelo totalmente convolucional que não possui restrições de forma. Portanto, precisamos indicar explicitamente quais dimensões dos tensores de entrada e saída são variáveis ​​em tamanho.
Vejamos um dynamic_axesexemplo de configuração:

import torch 
 
class Model(torch.nn.Module): 
    def __init__(self): 
        super().__init__() 
        self.conv = torch.nn.Conv2d(3, 3, 3) 
 
    def forward(self, x): 
        x = self.conv(x) 
        return x 
 
 
model = Model() 
dummy_input = torch.rand(1, 3, 10, 10) 
model_names = ['model_static.onnx',  
'model_dynamic_0.onnx',  
'model_dynamic_23.onnx'] 
 
dynamic_axes_0 = { 
    'in' : [0], 
    'out' : [0] 
} 
dynamic_axes_23 = { 
    'in' : [2, 3], 
    'out' : [2, 3] 
} 
 
torch.onnx.export(model, dummy_input, model_names[0],  
input_names=['in'], output_names=['out']) 
torch.onnx.export(model, dummy_input, model_names[1],  
input_names=['in'], output_names=['out'], dynamic_axes=dynamic_axes_0) 
torch.onnx.export(model, dummy_input, model_names[2],  
input_names=['in'], output_names=['out'], dynamic_axes=dynamic_axes_23) 

Primeiro, exportamos 3 modelos ONNX, que são modelos sem dimensão dinâmica, dinâmica 0-dimensional e dinâmica 2ª e 3ª dimensão.
Neste código, representamos dimensões dinâmicas em uma lista, por exemplo:

dynamic_axes_0 = { 
    'in' : [0], 
    'out' : [0] 
} 


Como o ONNX exige que cada dimensão dinâmica tenha um nome, escrevê-la assim levará a um UserWarning, avisando-nos de que o sistema atribuirá nomes automaticamente se definirmos as dimensões dinâmicas por meio de uma lista. Uma maneira de adicionar explicitamente nomes de dimensões dinâmicas é a seguinte:

dynamic_axes_0 = { 
    'in' : {0: 'batch'}, 
    'out' : {0: 'batch'} 
} 

Como não temos mais operações em dimensões dinâmicas neste código, podemos simplesmente especificar dimensões dinâmicas com uma lista.
Depois disso, vamos usar o seguinte código para dar uma olhada no papel das dimensões dinâmicas:

import onnxruntime 
import numpy as np 
 
origin_tensor = np.random.rand(1, 3, 10, 10).astype(np.float32) 
mult_batch_tensor = np.random.rand(2, 3, 10, 10).astype(np.float32) 
big_tensor = np.random.rand(1, 3, 20, 20).astype(np.float32) 
 
inputs = [origin_tensor, mult_batch_tensor, big_tensor] 
exceptions = dict() 
 
for model_name in model_names: 
    for i, input in enumerate(inputs): 
        try: 
            ort_session = onnxruntime.InferenceSession(model_name) 
            ort_inputs = {'in': input} 
            ort_session.run(['out'], ort_inputs) 
        except Exception as e: 
            exceptions[(i, model_name)] = e 
            print(f'Input[{i}] on model {model_name} error.') 
        else: 
            print(f'Input[{i}] on model {model_name} succeed.') 

Usamos um (1, 3, 10, 10)tensor de forma ao exportar o gráfico de cálculo do modelo. Agora, vamos tentar usar as formas como (1, 3, 10, 10), (2, 3, 10, 10), (1, 3, 20, 20)entrada, executar esses modelos com o ONNX Runtime, ver em que circunstâncias um erro será relatado e salvar as informações de erro correspondentes. A saída resultante deve ser a seguinte:

Input[0] on model model_static.onnx succeed. 
Input[1] on model model_static.onnx error. 
Input[2] on model model_static.onnx error. 
Input[0] on model model_dynamic_0.onnx succeed. 
Input[1] on model model_dynamic_0.onnx succeed. 
Input[2] on model model_dynamic_0.onnx error. 
Input[0] on model model_dynamic_23.onnx succeed. 
Input[1] on model model_dynamic_23.onnx error. 
Input[2] on model model_dynamic_23.onnx succeed. 

Pode-se ver que (1, 3, 10, 10)a entrada com a mesma forma não comete erros em todos os modelos. Para entradas com lote diferente (0ª dimensão) ou comprimento e largura (2ª e 3ª dimensões), nenhum erro ocorrerá até que a dimensão dinâmica correspondente seja definida. Podemos descobrir quais dimensões estão erradas na mensagem de erro. Por exemplo, podemos usar o seguinte código para visualizar a mensagem de erro input[1]em model_static.onnx:

print(exceptions[(1, 'model_static.onnx')]) 
 
# output 
# [ONNXRuntimeError] : 2 : INVALID_ARGUMENT : Got invalid dimensions for input: in for the following indices index: 0 Got: 2 Expected: 1 Please fix either the inputs or the model. 

Esta mensagem de erro nos diz que ina 0ª dimensão da entrada nomeada não corresponde. Originalmente, o comprimento desta dimensão deveria ser 1, mas nossa entrada é 2. Na implantação real, se encontrarmos erros semelhantes, podemos resolver o problema definindo dimensões dinâmicas.

Usar sugestões

Ao aprender o conhecimento anterior, basicamente dominamos  torch.onnx.exporto princípio de realização parcial e o método de configuração de parâmetros da função, o que é suficiente para concluir a conversão do modelo simples. Mas em aplicações práticas, o uso desta função irá pisar em muitas armadilhas. Aqui, nossa equipe de implantação de modelo compartilha com você alguma experiência acumulada em combate real.

Faça com que os modelos se comportem de maneira diferente quando convertidos em ONNX

Às vezes, queremos que o modelo tenha alguns comportamentos diferentes ao ser exportado para ONNX. O modelo tem um conjunto de lógica quando é inferido diretamente com o PyTorch e outro conjunto de lógica no modelo ONNX exportado. Por exemplo, podemos colocar alguma lógica de pós-processamento no modelo para simplificar o código além de executar o modelo. torch.onnx.is_in_onnx_export()Para realizar esta tarefa, a função  torch.onnx.export()só é verdadeira durante a execução. Aqui está um exemplo:

import torch 
 
class Model(torch.nn.Module): 
    def __init__(self): 
        super().__init__() 
        self.conv = torch.nn.Conv2d(3, 3, 3) 
 
    def forward(self, x): 
        x = self.conv(x) 
        if torch.onnx.is_in_onnx_export(): 
            x = torch.clip(x, 0, 1) 
        return x 


Aqui, apenas limitamos o valor do tensor de saída a [0, 1] quando o modelo é exportado. Usá  is_in_onnx_export-lo nos permite adicionar facilmente a lógica relacionada à implantação do modelo no código. No entanto, esses códigos são muito hostis para desenvolvedores e usuários que se preocupam apenas com o treinamento do modelo, e a lógica de implantação abrupta reduzirá a legibilidade geral do código. Ao mesmo tempo, is_in_onnx_exportele só pode ser "corrigido" em todos os locais onde a lógica de implantação precisa ser adicionada, o que dificulta a execução do gerenciamento unificado. Apresentaremos como usar o mecanismo de reescrita do MMDeploy para evitar esses problemas posteriormente.

Operações rastreadas usando tensores de interrupção

O método de exportação de rastreamento de PyTorch para ONNX é uma panacéia? Se fizermos algumas operações "out-of-the-box" no modelo, o método de rastreamento transformará alguns resultados intermediários que dependem da entrada em constantes, de modo que o modelo ONNX exportado seja diferente do modelo original. Aqui está um exemplo do que causaria essa "quebra de rastreamento":

class Model(torch.nn.Module): 
    def __init__(self): 
        super().__init__() 
 
    def forward(self, x): 
        x = x * x[0].item() 
        return x, torch.Tensor([i for i in x]) 
 
model = Model()       
dummy_input = torch.rand(10) 
torch.onnx.export(model, dummy_input, 'a.onnx') 

Se você tentar exportar este modelo, receberá vários avisos, informando que o modelo convertido pode não estar correto. Não é de admirar que, neste modelo, usamos .item()o tensor na tocha para convertê-lo em uma variável Python normal e tentamos percorrer o tensor da tocha e criar um novo tensor da tocha com uma lista. Essas lógicas envolvendo a conversão de tensores e variáveis ​​ordinárias farão com que o modelo ONNX final fique incorreto.
Por outro lado, também podemos usar essa propriedade para ordenar que os resultados intermediários do modelo se tornem constantes sob a premissa de garantir a correção. Essa técnica é frequentemente usada para tornar os modelos estáticos, ou seja, todas as formas de tensor no modelo se tornam constantes. Em tutoriais futuros, detalharemos essas operações "avançadas" em exemplos de implantação.

Use tensores como entrada (PyTorch versão <1.9.0)

Conforme mostrado em nosso primeiro tutorial , o PyTorch mais antigo (< 1.9.0)  torch.onnx.export()lança um erro ao alimentar valores Python em um modelo. Para fins de compatibilidade, ainda recomendamos o uso do tensor como entrada do modelo ao converter o modelo.

Suporte do operador PyTorch para ONNX

Depois de garantir torch.onnx.export()que o método de chamada esteja correto, o problema mais provável ao converter PyTorch para ONNX é que o operador não é compatível. Aqui, apresentaremos como julgar se um operador PyTorch é compatível no ONNX, para ajudá-lo a classificar melhor os erros ao encontrar erros. O método específico de adicionar operadores será apresentado em um artigo posterior.
Ao converter torch.nn.Modulemodelos comuns, o PyTorch usará o método de rastreamento para executar o raciocínio direto e integrar os operadores encontrados em um gráfico de cálculo; por outro lado, o PyTorch também traduzirá cada operador encontrado em operador ONNX. Durante este processo de tradução, as seguintes situações podem ser encontradas:

  • Este operador pode ser traduzido em um operador ONNX um-para-um.
  • Este operador não tem correspondente direto no ONNX e será traduzido em um ou mais operadores ONNX.
  • O operador não define regras para tradução em ONNX, e um erro é reportado.

Então, como verificar a correspondência entre os operadores PyTorch e os operadores ONNX? Como os operadores PyTorch estão alinhados ao ONNX, primeiro examinamos a definição dos operadores ONNX e, em seguida, examinamos o relacionamento de mapeamento do operador definido pelo PyTorch.


Documentação do Operador ONNX

A definição dos operadores ONNX pode ser visualizada na documentação oficial do operador . Este documento é muito importante, temos que "consultar" este documento quando nos deparamos com algum problema relacionado com operadoras ONNX.

A tabela de alteração do operador no início da parte mais importante deste documento. A primeira coluna da tabela é o nome do operador e a segunda coluna é o número da versão do conjunto de operadores que o operador alterou, que é o número da versão do conjunto de operadores que torch.onnx.exportmencionamos anteriormente. opset_versionAo visualizar o número da versão da primeira alteração de um operador, podemos saber a partir de qual versão um operador é suportado; ao visualizar o registro da primeira alteração de um operador menor ou igual, podemos conhecer a versão atual do conjunto de operadores opset_version. regra de definição do operador em .

Ao clicar no link da tabela, podemos visualizar as especificações dos parâmetros de entrada e saída e exemplos de uso de um operador. Por exemplo, a figura acima é a regra de definição de Relu no ONNX, essa definição indica que Relu deve ter uma entrada e uma entrada, sendo que a entrada e a saída são do mesmo tipo, ambas tensoras.

Mapeamento do operador PyTorch para ONNX

No PyTorch, todas as definições relacionadas ao ONNX são colocadas  no torch.onnxdiretório , conforme a figura a seguir:

Entre eles, symbolic_opset{n}.py(arquivo de tabela de símbolos) refere-se ao conteúdo recém-adicionado quando o PyTorch oferece suporte à enésima versão do conjunto de operadores ONNX. Como mencionamos anteriormente, a interpolação bicúbica é suportada na versão 11. Vamos tomar como exemplo para ver como encontrar o mapeamento de operadores.
Primeiro, use a função de pesquisa torch/onnxpara pesquisar "bicúbico" na pasta e você pode encontrar essa interpolação no arquivo de definição da 11ª versão:

Depois, saltamos passo a passo para a função de mapeamento ONNX inferior de acordo com a lógica de chamada do código:

upsample_bicubic2d = _interpolate("upsample_bicubic2d", 4, "cubic") 
 
-> 
 
def _interpolate(name, dim, interpolate_mode): 
    return sym_help._interpolate_helper(name, dim, interpolate_mode) 
 
-> 
 
def _interpolate_helper(name, dim, interpolate_mode): 
    def symbolic_fn(g, input, output_size, *args): 
        ... 
 
    return symbolic_fn 

Por fim, em symbolic_fn, podemos ver como o operador de interpolação é mapeado para vários operadores ONNX. Entre eles, cada um g.opé uma definição de ONNX. Por exemplo,  Resize o operador é escrito assim:

return g.op("Resize", 
                input, 
                empty_roi, 
                empty_scales, 
                output_size, 
                coordinate_transformation_mode_s=coordinate_transformation_mode, 
                cubic_coeff_a_f=-0.75,  # only valid when mode="cubic" 
                mode_s=interpolate_mode,  # nearest, linear, or cubic 
                nearest_mode_s="floor")  # only valid when mode="nearest" 

Ao pesquisar a definição do operador Redimensionar no documento do operador ONNX acima mencionado , podemos saber o significado de cada parâmetro. Usando um método semelhante, podemos consultar os significados dos parâmetros de outros operadores ONNX e, em seguida, saber como os parâmetros no PyTorch são passados ​​para cada operador ONNX passo a passo.
Depois de dominar como consultar a relação entre PyTorch e ONNX, podemos predefinir um número de versão no aplicativo real  torch.onnx.export()e opset_versionverificar o arquivo de tabela de símbolos PyTorch correspondente ao encontrar problemas. Se um operador não existir ou o relacionamento de mapeamento do operador não atender aos nossos requisitos, talvez seja necessário ignorá-lo com outros operadores ou personalizar o operador.

Resumir

Neste tutorial, introduzimos sistematicamente o princípio de conversão de PyTorch para ONNX. Primeiro, nos concentramos em explicar a função arch.onnx.export usada com mais frequência e, em seguida, fornecemos um método para consultar o suporte do PyTorch para operadores ONNX. Por meio deste artigo, esperamos que você consiga converter com êxito a maioria dos modelos ONNX que não precisam adicionar novos operadores e possa localizar com eficiência a causa do problema ao encontrar problemas no operador. Especificamente, depois de ler este artigo, você deve entender o seguinte conhecimento:

  • Qual é a diferença entre o método de rastreamento e o método de gravação na exportação de um gráfico de computação com instruções de controle.
  • torch.onnx.export()Como colocar em  input_names, output_names, dynamic_axes.
  • Use  torch.onnx.is_in_onnx_export()para fazer com que os modelos se comportem de maneira diferente quando convertidos para ONNX.
  • Como consultar a documentação do operador ONNX ( https://github.com/onnx/onnx/blob/main/docs/Operators.md ).
  • Como consultar o suporte do PyTorch para novos recursos de uma determinada versão do ONNX.
  • Como julgar se o PyTorch oferece suporte a um determinado operador ONNX e qual é o método compatível.

O conhecimento introduzido nesta edição é relativamente abstrato, você acha que é um pouco "aguado"? Não importa, no próximo tutorial, apresentaremos uma variedade de métodos para adicionar suporte de operador para PyTorch a ONNX na forma de exemplos de código e remover mais obstáculos para todos no caminho de PyTorch para ONNX. Fique atento!

praticar praticar

  1. O operador Asinh aparece no 9º conjunto de operadores ONNX. Como o PyTorch oferece suporte a esse operador no arquivo de tabela de símbolos da versão 9?
  2. O operador BitShift apareceu no 11º conjunto de operadores ONNX. Como o PyTorch oferece suporte a esse operador no arquivo de tabela de símbolos da versão 11?
  3. No primeiro tutorial , dissemos que o PyTorch (a partir do conjunto de operadores nº 11) não suporta a configuração de fatores de escala dinâmicos na interpolação. A qual parâmetro na relação de mapeamento do operador Redimensionar esse coeficiente corresponde  torch.onnx.symbolic_helper._interpolate_helper? symbolic_fnComo modificamos esse parâmetro?

As respostas dos exercícios serão reveladas no próximo tutorial~ Vamos tentar juntos~

Sejam todos bem-vindos à experiência no MMDeploy~

https://github.com/open-mmlab/mmdeploy​github.com/open-mmlab/mmdeploy

Se nosso compartilhamento trouxer alguma ajuda, seja bem-vindo para curtir, coletar e prestar atenção, amor~

Portal da Série

OpenMMLab: Interpretação do TorchScript (1): Conhecendo o TorchScript pela primeira vez

OpenMMLab: Interpretação do TorchScript (2): Análise de implementação do Torch jit tracer

OpenMMLab: Interpretação do TorchScript (3): reescritor de subgráficos em jit24 Aprovado · 0 Comentários Artigo43 Aprovado · 0 Comentários O artigo está sendo carregado...ReuploadCancelar

OpenMMLab: Interpretação do TorchScript (4): Análise de alias no Torch jit

OpenMMLab: Introdução à implantação de modelo (1): Introdução à implantação de modelo 172 Concordo 22 Comentários 498 Concordo 50 Comentários estão sendo carregados...ReuploadCancel

OpenMMLab: Tutorial de introdução à implantação de modelo (2): Resolvendo os problemas na implantação de modelo

OpenMMLab: Tutorial introdutório para implantação de modelo (3): Explicação detalhada de PyTorch para ONNX

OpenMMLab: Tutorial de implantação de modelo (4): Suporte a mais operadores ONNX no PyTorch 68 Concordo· 19 Comentários 190 Concordo· 53 Comentários estão sendo carregados...ReuploadCancel

OpenMMLab: Introdução ao Tutorial de implantação de modelo (5): Modificação e depuração do modelo ONNX

Acho que você gosta

Origin blog.csdn.net/qq_43456016/article/details/130254810
Recomendado
Clasificación