怎样将paddlepaddleOCR的模型转换为pytorch模型

目的:将paddlepaddleocr的字符识别模型转换为pytorch的模型

过程:mobilenetv3_small的小模型在转换过程中成功转换了backbone的参数,但是head(两个双向LSTM)转换失败,因为类别数不同,而LSTM中涉及到两个fc层两个lstm层,其中的fc层的参数和类别相关联,所以双向的LSTM参数无法进行转换;

结果:只对backbone的参数进行了转换和拷贝

原始paddlepaddle工程链接:https://github.com/PaddlePaddle/PaddleOCR

简单叙述过程:

1)paddlepaddle的模型参数加载;

def _load_state(path):
    """
    记载paddlepaddle的参数
    :param path:
    :return:
    """
    if os.path.exists(path + '.pdopt'):
        # XXX another hack to ignore the optimizer state
        tmp = tempfile.mkdtemp()
        dst = os.path.join(tmp, os.path.basename(os.path.normpath(path)))
        shutil.copy(path + '.pdparams', dst + '.pdparams')
        state = fluid.io.load_program_state(dst)
        shutil.rmtree(tmp)
    else:
        state = fluid.io.load_program_state(path)
    return state

2)pytorch模型的构建;

3)进行参数拷贝和模型保存;

    def init_model(self):
        for n, m in self.net_pytorch.named_modules():
            if isinstance(m, BatchNorm2d):
                self.bn_init(n, m)
            elif isinstance(m, Conv2d):
                self.conv_init(n, m)
            # elif isinstance(m, Linear):
            #     self.fc_init(n, m)
            # elif isinstance(m, PReLU):
                # self.prelu_init(n, m)
            elif isinstance(m, BatchNorm1d):
                self.bn_init(n, m)

    def bn_init(self, layer , m):
        for key in self.list_layers:
            if (layer in key) and ('bn' in key):
                print(key) #, ' -- shape: ', self.state_pp[key].shape)
                if 'scale' in key:
                    m.weight.data.copy_(torch.FloatTensor(self.state_pp[key]))
                    self.list_layers.remove(key)
                elif 'offset' in key:
                    m.bias.data.copy_(torch.FloatTensor(self.state_pp[key]))
                    self.list_layers.remove(key)
                elif 'mean' in key:
                    m.running_mean.copy_(torch.FloatTensor(self.state_pp[key]))
                    self.list_layers.remove(key)
                elif 'variance' in key:
                    m.running_var.copy_(torch.FloatTensor(self.state_pp[key]))
                    self.list_layers.remove(key)


    def conv_init(self, layer, m):
        # for pr in net.params:
        layer_ = layer+'_'
        for key in self.list_layers:
            if (layer_ in key) and ('bn' not in key):
                print(key) #, ' -- shape: ', self.state_pp[key].shape)
                if 'weights' in key:
                    m.weight.data.copy_(torch.FloatTensor(self.state_pp[key]))
                elif 'offset' in key:
                    m.bias.data.copy_(self.state_pp[key])
                self.list_layers.remove(key)

技术难点:

1)paddlepaddle中怎样读取每层的输出参数;

2)双向LSTM的参数拷贝;

3)验证参数转换是否成功时,读取图片传入后,每层layer处理后的图片特征;

工程链接:https://github.com/maomaoyuchengzi/paddlepaddle_param_to_pyotrch

评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

猫猫与橙子

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值