Dynamic Slimmable Network-(CVPR21-ORAL)综合分析

本文介绍了一种动态网络剪枝方法,通过动态宽度可变超网络(DS-Net)和动态宽度门控解决传统剪枝方法的加速问题。DS-Net结合了动态超网络和门控机制,实现不同样本的动态路由。动态门控采用双头结构,通过SandwichGateSparsification(SGS)策略避免门控坍塌。在训练过程中,使用In-place Ensemble Bootstrapping(IEB)策略稳定模型训练。该方法在提高模型性能的同时,增强了网络的动态性和效率。

文章提出了一种动态剪枝策略,通过动态宽度可变超网络(Dynamic Slimmable Supernet),解决了传统剪枝方法硬件实际加速效果很低的问题。并提出了动态宽度门控(Dynamic Slimming Gate)对网络进行瘦身。在这里插入图片描述
下面就文章原理和代码来综合分析:

动态宽度可变超网络

在这里插入图片描述
动态宽度可变网络(DS-Net)通过学习一个宽度可变超网络和一个动态门控机制来实现不同样本的动态路由。如上图所示,DS-Net中的超网络(上图黄色框)是指承担主要任务的整个模块。相比之下,动态门控(上图蓝色框)是一系列预测模块,它们将输入样本路由到超网络的不同宽度的子网络。

1.动态超网络(supernet)和动态可切分(slice-able)卷积
为避免产生稀疏channel,作者提出动态可切分(slice-able)卷积,通过预测出的剪枝率 ,动态的切分使用卷积的前 × n个滤波器(n为总滤波器数)。通过堆叠动态可切分(slice-able)卷积并禁用动态门控,就形成了类似slimmablenetwork的动态超网络。
如下为conv2d的slice方法。

    def forward(self, x):
        if self.prev_channel_choice is None:
            self.prev_channel_choice = self.channel_choice
        if self.mode == 'dynamic' and isinstance(self.channel_choice, tuple):
            weight = self.weight
            if not self.in_chn_static:
                if isinstance(self.prev_channel_choice, int):
                    self.running_inc = self.in_channels_list[self.prev_channel_choice]
                    weight = self.weight[:, :self.running_inc]
                else:
                    self.running_inc = torch.matmul(self.prev_channel_choice[0], self.in_channels_list_tensor)
            if not self.out_chn_static:
                self.running_outc = torch.matmul(self.channel_choice[0], self.out_channels_list_tensor)

            output = F.conv2d(x,
                              weight,
                              self.bias,
                              self.stride,
                              self.padding,
                              self.dilation,
                              self.groups)
            if not self.out_chn_static:
                output = apply_differentiable_gate_channel(output,
                                                           self.channel_choice[0],
                                                           self.out_channels_list)
            self.prev_channel_choice = None
            self.channel_choice = -1
            return output
        else:
            if not self.in_chn_static:
                self.running_inc = x.size(1)
            if not self.out_chn_static:
                self.running_outc = self.out_channels_list[self.channel_choice]
            weight = self.weight[:self.running_outc, :self.running_inc]
            bias = self.bias[:self.running_outc] if self.bias is not None else None
            self.running_groups = 1 if self.groups == 1 else self.running_outc
            self.prev_channel_choice = None
            self.channel_choice = -1
            return F.conv2d(x,
                            weight,
                            bias,
                            self.stride,
                            self.padding,
                            self.dilation,
                            self.running_groups)

2.In-place Ensemble Bootstrapping(IEB)
之前的slimmable network训练使用in-place distillation方法:最宽的子网络学习预测真实标签,同时生成软标签,并通过知识蒸馏的方式来训练其他较窄的子网络。但in-place distillation训练很不稳定,权重在训练早期会大幅突变,并可能导致模型最终训练失败或性能损失。
在这里插入图片描述

为此,作者提出In-place Ensemble Bootstrapping(IEB)策略来稳定动态超网络的训练并最终提高模型性能。首先,使用超网络的滑动平均(EMA)网络来生成训练子网络的软标签,因为EMA网络提供的目标更加稳定和精准。其次,使用包括最宽子网络和随机宽度子网络的多个模型的概率集成(probability ensemble)作为训练最窄网络的目标,因为多模型集成可以提供更多样、更泛化、更精准的软标签。(见上图)
一下代码为IEB策略代码。

    for batch_idx, (input, target) in enumerate(loader):
        last_batch = batch_idx == last_idx
        data_time_m.update(time.time() - end)
        if not args.prefetcher:
            input, target = input.cuda(), target.cuda()

        sample_list = ['largest', 'uniform', 'uniform', 'smallest']
        guide_list = []

        for sample_idx, model_mode in enumerate(sample_list):
            seed = seed + 1
            random.seed(seed)
            np.random.seed(seed)
            torch.manual_seed(seed)
            if hasattr(model, 'module'):
                model.module.set_mode(model_
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值