转载请注明出处:

https://www.cnblogs.com/darkknightzh/p/9410540.html

论文:

MobileNets: Efficient Convolutional Neural Networks for Mobile Vision Applications

网址:

https://arxiv.org/abs/1704.04861?context=cs

非官方的pytorch代码:

https://github.com/marvis/pytorch-mobilenet

1. 深度可分离卷积

mobilenetV1使用的是深度可分离卷积(Depthwise Separable Convolution,DSC),DSC包含两部分:depthwise convolution(DWC)+ pointwise convolution(PWC)。DWC对输入的通道进行滤波,其不增加通道的数量,PWC用于将PWC不同的通道进行连接,其可以增加通道的数量。通过这种分解的方式,可以明显的减少计算量。

如下图所示,传统的卷积(a),卷积核参数为${{D}_{K}}\centerdot {{D}_{K}}\centerdot M\centerdot N$,其中${{D}_{K}}$为卷积核大小,M为输入的通道数,N为输出的通道数。DWC(b)中卷积核参数为${{D}_{K}}\centerdot {{D}_{K}}\centerdot 1\centerdot M$,其中M个${{D}_{K}}\centerdot {{D}_{K}}$的核和输入特征的对应通道进行卷积,如下式所示。PWC(c)中卷积核参数为$1\centerdot 1\centerdot M\centerdot N$,每个卷积核在特征维度上分别对输入的M个特征进行加权,最终得到N个特征(M≠N时,完成了升维或者降维)。

${{\mathbf{\hat{G}}}_{k,l,m}}=\sum\limits_{i,j}{{{{\mathbf{\hat{K}}}}_{k,l,m}}\centerdot {{\mathbf{F}}_{k+i-1,l+j-1,m}}}$

传统卷积的计算量为:

${{D}_{K}}\centerdot {{D}_{K}}\centerdot M\centerdot N\centerdot {{D}_{F}}\centerdot {{D}_{F}}$

DSC总共的计算量为:

${{D}_{K}}\centerdot {{D}_{K}}\centerdot M\centerdot {{D}_{F}}\centerdot {{D}_{F}}+M\centerdot N\centerdot {{D}_{F}}\centerdot {{D}_{F}}$

当使用3*3的卷积核时,DSC可将计算量降低为原来的1/8到1/9。

需要说明的是,DWC,PWC后面均有BN和ReLU。如下图所示,传统的卷积层为3*3conv+BN+ReLU,Depthwise Separable convolutions为3*3DWC+BN+ReLU+1*1conv+BN+ReLU。

2. 网络结构

mobileNetV1的网络结构如下图所示。其中第一个卷积层为传统的卷积;前面的卷积层均有bn和relu,最后一个全连接层只有BN,无ReLU。

mobileNetV1使用RMSprop训练;由于参数很少,DWC使用比较小的或者不使用weight decay(l2 regularization)。

3. 宽度缩放因子(width multiplier)

文中引入了$\alpha $作为宽度缩放因子,其作用是在整体上对网络的每一层维度(特征数量)进行瘦身。$\alpha $影响模型的参数数量及前向计算时的乘加次数。此时网络每一层的输入为$\alpha M$维,输出为$\alpha N$维。此时DSC的计算量变为:

${{D}_{K}}\centerdot {{D}_{K}}\centerdot \alpha M\centerdot {{D}_{F}}\centerdot {{D}_{F}}+\alpha M\centerdot \alpha N\centerdot {{D}_{F}}\centerdot {{D}_{F}}$

$\alpha \in (0,1]$,典型值为1,0.75,0.5,0.25。

4. 分辨率缩放因子(resolution multiplier)

该因子即为$\rho $,用于降低输入图像的分辨率(如将224*224降低到192*192,160*160,128*128)。

此时DSC的计算量变为:

${{D}_{K}}\centerdot {{D}_{K}}\centerdot \alpha M\centerdot \rho {{D}_{F}}\centerdot \rho {{D}_{F}}+\alpha M\centerdot \alpha N\centerdot \rho {{D}_{F}}\centerdot \rho {{D}_{F}}$

5. pytorch代码

pytorch代码见参考网址中benchmark.py

 class MobileNet(nn.Module):
def __init__(self):
super(MobileNet, self).__init__() def conv_bn(inp, oup, stride): # 第一层传统的卷积:conv3*3+BN+ReLU
return nn.Sequential(
nn.Conv2d(inp, oup, 3, stride, 1, bias=False),
nn.BatchNorm2d(oup),
nn.ReLU(inplace=True)
) def conv_dw(inp, oup, stride): # 其它层的depthwise convolution:conv3*3+BN+ReLU+conv1*1+BN+ReLU
return nn.Sequential(
nn.Conv2d(inp, inp, 3, stride, 1, groups=inp, bias=False),
nn.BatchNorm2d(inp),
nn.ReLU(inplace=True), nn.Conv2d(inp, oup, 1, 1, 0, bias=False),
nn.BatchNorm2d(oup),
nn.ReLU(inplace=True),
) self.model = nn.Sequential(
conv_bn( 3, 32, 2), # 第一层传统的卷积
conv_dw( 32, 64, 1), # 其它层depthwise convolution
conv_dw( 64, 128, 2),
conv_dw(128, 128, 1),
conv_dw(128, 256, 2),
conv_dw(256, 256, 1),
conv_dw(256, 512, 2),
conv_dw(512, 512, 1),
conv_dw(512, 512, 1),
conv_dw(512, 512, 1),
conv_dw(512, 512, 1),
conv_dw(512, 512, 1),
conv_dw(512, 1024, 2),
conv_dw(1024, 1024, 1),
nn.AvgPool2d(7),
)
self.fc = nn.Linear(1024, 1000) # 全连接层 def forward(self, x):
x = self.model(x)
x = x.view(-1, 1024)
x = self.fc(x)
return x

(原)MobileNetV1的更多相关文章

  1. 【原】谈谈对Objective-C中代理模式的误解

    [原]谈谈对Objective-C中代理模式的误解 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 这篇文章主要是对代理模式和委托模式进行了对比,个人认为Objective ...

  2. 【原】FMDB源码阅读(三)

    [原]FMDB源码阅读(三) 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 FMDB比较优秀的地方就在于对多线程的处理.所以这一篇主要是研究FMDB的多线程处理的实现.而 ...

  3. 【原】Android热更新开源项目Tinker源码解析系列之一:Dex热更新

    [原]Android热更新开源项目Tinker源码解析系列之一:Dex热更新 Tinker是微信的第一个开源项目,主要用于安卓应用bug的热修复和功能的迭代. Tinker github地址:http ...

  4. 多线程爬坑之路-学习多线程需要来了解哪些东西?(concurrent并发包的数据结构和线程池,Locks锁,Atomic原子类)

    前言:刚学习了一段机器学习,最近需要重构一个java项目,又赶过来看java.大多是线程代码,没办法,那时候总觉得多线程是个很难的部分很少用到,所以一直没下决定去啃,那些年留下的坑,总是得自己跳进去填 ...

  5. 【原】FMDB源码阅读(二)

    [原]FMDB源码阅读(二) 本文转载请注明出处 -- polobymulberry-博客园 1. 前言 上一篇只是简单地过了一下FMDB一个简单例子的基本流程,并没有涉及到FMDB的所有方方面面,比 ...

  6. 【原】FMDB源码阅读(一)

    [原]FMDB源码阅读(一) 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 说实话,之前的SDWebImage和AFNetworking这两个组件我还是使用过的,但是对于 ...

  7. 【原】AFNetworking源码阅读(六)

    [原]AFNetworking源码阅读(六) 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 这一篇的想讲的,一个就是分析一下AFSecurityPolicy文件,看看AF ...

  8. 【原】AFNetworking源码阅读(五)

    [原]AFNetworking源码阅读(五) 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 上一篇中提及到了Multipart Request的构建方法- [AFHTTP ...

  9. 【原】AFNetworking源码阅读(四)

    [原]AFNetworking源码阅读(四) 本文转载请注明出处 —— polobymulberry-博客园 1. 前言 上一篇还遗留了很多问题,包括AFURLSessionManagerTaskDe ...

随机推荐

  1. VMvare虚拟机如何删除安装的ubuntu操作系统

    VMvare虚拟机如何删除安装的ubuntu操作系统呢??? 这个问题其实在我刚开始接触虚拟机和ubuntu操作系统的时候对于如何删除操作系统是一件很苦恼的事情,因为按照书本的步骤,根本看不懂如何操作 ...

  2. 解决/bin/sh: 1: syntax error: "(" unexpected错误,以及更换bash仍然无法解决的问题

    编译文件的时候出现 /bin/sh: 1: syntax error: "(" unexpected 错误. 网上查到的资料都是: (1)在脚本前写#!/bin/bash (2)执 ...

  3. python全栈开发day32-进程创建,进程同步,进程间的通信,进程池

    一.内容总结 1.进程创建 1) Process:两种创建一个新进程的方法: 1.实例化Process,通过args=(,)元组形式传参,2创建类继承Process,类初始化的时候传参数 2) p.j ...

  4. HDU2473 Junk-Mail Filter 并查集

    欢迎访问~原文出处——博客园-zhouzhendong 去博客园看该题解 题目传送门 - HDU2473 题意概括 一堆点. 要你支持合并两组点.分离某组点中的一个,这两种操作. 点数<=100 ...

  5. fmod()函数 (对浮点数取模)

    头文件:#include <math.h> fmod() 用来对浮点数进行取模(求余),其原型为:    double fmod (double x); 设返回值为 ret,那么 x = ...

  6. ubuntu server 18.04 lts 终端中文显示为乱码的解决方案

    .最近安装ubuntu server 18.04 lts版本发现系统自带的终端下无论是编辑中文,还是显示中文均出现乱码,还是老毛病, 今天无意中发现通过ssh,远程访问,在windows中安装开源的p ...

  7. HDU1789 Doing Homework again 做作业【贪心】

    题目链接:https://vjudge.net/problem/HDU-1789 题目大意: 给出N个作业的截至日期,和N个作业不交所扣掉的分数,要求输出扣除分数做少的方案. 解析: 与上一道销售商品 ...

  8. @ConfigurationProperties和@Value 注入

    我这里使用的Spring Boot 2.0.1 版本 配置文件是 yml 格式文件 @ConfigurationProperties 在yml配置文件中: 在实体类中: 重点是实体类上的两个注解: @ ...

  9. class.forName的作用?

    调用该访问 返回一个以字符串指定类名的类的对象. 返回字节码,返回字节码的方式有几种: ①:这份字节码曾经被加载过已经存在java虚拟机中了直接返回. ②:java虚拟机中还没有这份字节码,用类加载器 ...

  10. C# 设置MDI子窗体只能弹出一个的方法

    Windows程序设计中的MDI(Multiple Document Interface)官方解释就是所谓的多文档界面,与此对应就有单文档界面 (SDI), 它是微软公司从Windows .0下的Mi ...