如何将Keras(TensorFlow后端)的.h5模型转换为PyTorch模型?
将Keras(TensorFlow后端)ResNet50模型迁移到PyTorch的方法
你可以通过两种方式将Keras保存的.h5模型/权重转换为PyTorch可用的格式,以下是具体步骤:
一、使用自动转换工具(快速便捷)
针对标准结构的模型(比如你用的ResNet50),可以用keras2torch工具直接完成转换:
- 安装工具
pip install keras2torch
- 加载Keras模型并转换
import tensorflow as tf import torch from keras2torch import convert # 加载完整的Keras模型 keras_model = tf.keras.models.load_model("mymodel.h5") # 转换为PyTorch模型 pytorch_model = convert(keras_model) # 保存PyTorch模型权重 torch.save(pytorch_model.state_dict(), "mymodel_pytorch.pth")
注意:如果模型包含自定义层或特殊操作,自动转换可能失效,此时建议用手动映射的方式。
二、手动映射权重(更可靠,适合标准ResNet50)
因为你使用的是标准ResNet50(include_top=False),可以手动对齐Keras和PyTorch的层结构,逐个映射权重:
- 定义PyTorch版的ResNet50结构(和Keras参数对齐)
import torch import torchvision.models as models # 创建无预训练权重、不含顶层的ResNet50,和Keras参数匹配 pytorch_model = models.resnet50(pretrained=False, num_classes=None)
- 加载Keras权重并映射到PyTorch模型
Keras和PyTorch的卷积核维度顺序不同:Keras是(filters, kernel_h, kernel_w, in_channels),PyTorch是(out_channels, in_channels, kernel_h, kernel_w),需要转置后赋值;批归一化层的参数(gamma、beta、moving_mean、moving_var)可以直接对应赋值。
示例代码(以初始层和第一个残差块为例,其余层可按相同逻辑批量处理):
import h5py # 加载Keras权重文件 with h5py.File("saved_weights.h5", "r") as h5_file: # 处理第一层卷积 keras_conv_weights = h5_file["conv2d_1"]["conv2d_1"]["kernel:0"][()] # 转置维度匹配PyTorch格式 pytorch_conv_weights = keras_conv_weights.transpose(3, 2, 0, 1) pytorch_model.conv1.weight.data = torch.from_numpy(pytorch_conv_weights) # 处理卷积层偏置 keras_conv_bias = h5_file["conv2d_1"]["conv2d_1"]["bias:0"][()] pytorch_model.conv1.bias.data = torch.from_numpy(keras_conv_bias) # 处理第一层批归一化 pytorch_model.bn1.weight.data = torch.from_numpy(h5_file["batch_normalization_1"]["batch_normalization_1"]["gamma:0"][()]) pytorch_model.bn1.bias.data = torch.from_numpy(h5_file["batch_normalization_1"]["batch_normalization_1"]["beta:0"][()]) pytorch_model.bn1.running_mean.data = torch.from_numpy(h5_file["batch_normalization_1"]["batch_normalization_1"]["moving_mean:0"][()]) pytorch_model.bn1.running_var.data = torch.from_numpy(h5_file["batch_normalization_1"]["batch_normalization_1"]["moving_variance:0"][()]) # 处理残差块(以layer1的第一个块为例) # Keras的conv2d_2对应PyTorch的layer1[0].conv1 keras_res_conv_weights = h5_file["conv2d_2"]["conv2d_2"]["kernel:0"][()].transpose(3,2,0,1) pytorch_model.layer1[0].conv1.weight.data = torch.from_numpy(keras_res_conv_weights) # 剩余层可按此逻辑循环处理
- 验证转换效果
输入相同的测试数据(注意调整维度:Keras是(batch, h, w, c),PyTorch是(batch, c, h, w)),比较两个模型的输出,误差在可接受范围内(比如1e-5)则说明转换成功。
关键注意事项
- 确保PyTorch模型的结构和Keras完全一致,包括层数量、通道数、是否包含池化/激活等操作;
- 框架间的浮点计算可能存在微小差异,输出不必完全一致,只要误差在合理范围内即可。
内容的提问来源于stack exchange,提问作者seni
相关产品推荐
相关产品推荐

