Pytorch模型量化( 四 )

Quantization Aware Training (边训练边量化)这一部分我用不着,等我需要使用的时候再来补充
保存和加载量化模型我们先把模型量化
import torchfrom torch import nnclass M(torch.nn.Module):    def __init__(self):        super().__init__()        self.linear = nn.Linear(5, 5,bias=True)        self.gru = nn.GRU(input_size=5,hidden_size=5,bias=True,)        self.relu = nn.ReLU()    def forward(self, x):        x = self.linear(x)        x = self.gru(x)        x = self.relu(x)        return xm = M().eval()model_int8 = torch.quantization.quantize_dynamic(    model=m,  # 原始模型    qconfig_spec={nn.Linear,                  nn.GRU},  # 要动态量化的NN算子    dtype=torch.qint8, inplace=True)  # 将权重量化为:float16 \ qint8+保存/加载量化模型 state_dicttorch.save(model_int8.state_dict(), "./state_dict.pth")model_int8.load_state_dict(torch.load("./state_dict.pth"))print(model_int8)保存/加载脚本化量化模型 torch.jit.save 和 torch.jit.loadtraced_model = torch.jit.trace(model_int8, torch.rand(5, 5))torch.jit.save(traced_model, "./traced_quant.pt")quantized_model = torch.jit.load("./traced_quant.pt")print(quantized_model)获取量化模型的参数其实pytorch获取量化后的模型参数是比较困难的,我们还是以上面的量化模型为例来取参数的值
print(model_int8)# M(#   (linear): DynamicQuantizedLinear(in_features=5, out_features=5, dtype=torch.qint8, qscheme=torch.per_tensor_affine)#   (gru): DynamicQuantizedGRU(5, 5)#   (relu): ReLU()# )print(model_int8.linear)print(model_int8.gru)print(model_int8.relu)我们来尝试一下获取线性层的权重和偏置
# print(dir(model_int8.linear))# 获得对象的所有属性和方法print(model_int8.linear.weight().int_repr())# tensor([[ 104,  127,   70,  -94,  121],#         [  98,   53,  124,   74,   38],#         [-103, -112,   38,  117,   64],#         [ -46,  -36,  115,   82,  -75],#         [ -14,  -94,   42,  -25,   41]], dtype=torch.int8)print(model_int8.linear.bias())# tensor([ 0.2437,  0.2956,  0.4010, -0.2818,  0.0950], requires_grad=True)O My God,偏置居然还是浮点类型的,只有权重被量化为了整型 。
好的,我们再来获取GRU的权重和偏置
print(dir(model_int8.gru))print(model_int8.gru.get_weight()["weight_ih_l0"].int_repr())   # int8print(model_int8.gru.get_weight()["weight_hh_l0"].int_repr())   #int8print(model_int8.gru.get_bias()["bias_ih_l0"])  # floatprint(model_int8.gru.get_bias()["bias_hh_l0"])  # float第一,别问我别问我为什么取值这么麻烦,你以为我想???
第二,静态量化不支持GRU就算了,动态量化偏置还不给我量化了,哎,pytorch的量化真的是还有很长的路要走呀!
参考【pytorch官方】Quantization(需要非常细心且耐心的去读)
【pytorch官方】Quantization API
【知乎】PyTorch的量化

推荐阅读