TensorFlow实现经典深度学习网络(3):TensorFlow实现Google Inception Net

本文介绍如何使用TensorFlow实现Google Inception Net,重点讨论Inception Module的结构和优化,包括非对称卷积、高效降尺寸策略,以及Inception V3的改进,如分解大卷积和增加网络深度,旨在降低计算量和参数数量,提升模型性能。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

TensorFlow实现经典深度学习网络(3):TensorFlow实现Google Inception Net


        Google Inception Net作为ILSVRC 2014比赛中的第一名(这年的Google Inception Net通常被称为Inception V1),其在控制计算量和参数量的同时,获得非常好的分类性能——top-5错误率6.67%,只有AlexNet的一半不到。Inception V1有22层(AlexNet 8层,VGGNet 19层),计算量却只有15亿次浮点运算,500万参数(AlexNet 6000万),准确率却远高于AlexNet。Inception V1降低参数量是因为(1)参数越多模型越庞大,需数据量越大,高质量数据昂贵;(2)参数越多,耗费计算资源越大。Inception V1参数少但效果好的原因除了模型层数更深、表达能力更强外,还有一点就是(1)去除最后全连接层,用全局平均池化层(图片尺寸变1x1),参数大减,模型训练更快,减轻过拟合(《Network in Network》论文);(2)Inception Module提高参数利用效率,大网络中小网络。增加分支网络,NIN级联卷积层、NLPConv层。一般来说卷积层增加输出通道数可以提升表达能力,但缺点是计算量增大和过拟合。每个输出通道对应一个滤波器,同一滤波器共享参数,只能提取一类特征。Google Inception Net发展至今,已成为一个大家族Inception V1(top-5错误率6.67%)、Inception V2(top-5错误率4.8%)、Inception V3(top-5错误率3.5%)、Inception V4(top-5错误率3.08%)。

Inception Module结构图

         Google Inception Net模型参数详细如下:


本文要构建的网络为Inception V3:

• 核心组件
        • 非对称卷积:N x N 分解成 1 x N 、 N x 1
        • 降低参数数量和计算量

        • 使用3×3的已经很小了,那么更小的2×2呢?2×2虽然能使得参数进一步降低,但是不如另一种方式更加有效,那就是Asymmetric方式,即使用1×3和3×1两种来代替3×3。使用2个2×2的话能节省11%的计算量,而使用这种方式则可以节省33%。如下图所示:


• 高效的降尺寸(Grid size)
        • 避免表达瓶颈
                • 降尺寸前增加特征通道
       • 2个并行分支
               • 卷积分支+池化分支
               • 串接分支结果

               • Grid就是图像在某一层的激活值,即feature_map,一般情况下,如果想让图像缩小,可以有如下两种方式:

        右图是正常的缩小,但计算量很大。左图先pooling会导致特征表征遇到瓶颈,违反上面所说的第一个规则,为了同时达到不违反规则且降低计算量的作用,将网络改为下图:

使用两个并行化的模块可以降低计算量

• 取消浅层的辅助分类器
        • 完全无用

• 深层辅助分类器只在训练后期有用

       • 加上BN和Dropout,主分类器Top1性能提升0.4%
       • 正则化作用
       • 用在最后一层17x17后

• 不增加计算量
       • 避免表达瓶颈
       • 增强结构(表达力)

Inception V3网络结构


        图中的Figure 4是指没有进化的Inception,Figure 5是指smaller conv版的Inception,Figure 6是指Asymmetric版的Inception

        V3一个最重要的改进就是分解(也就是Factorization into small convolutions),将一个较大的二维卷积拆成两个较小的一维卷积,比如将7x7分解成两个一维的卷积(1x7,7x1),3x3也是一样(1x3,3x1),这样的好处,既可以加速计算(多余的计算能力可以用来加深网络),又可以将1个conv拆成2个conv,使得网络深度进一步增加,增加了网络的非线性;还有值得注意的地方是V3网络优化了Inception Module的结构,输入从224x224变为了299x299,更加精细设计了35x35/17x17/8x8的模块。

        因使用ImageNet数据集非常耗时,因此本文会对完整的Inception V3网络进行速度测试,评测forward耗时和backward耗时。若读者感兴趣,可自行下载ImageNet数据集进行训练测试。
        在准备工作就绪后,我们就可以搭建网络了。Google Inception Net V3相对比较复杂,为了减少代码量能够构建42层深的Inception V3,  本文将采取一些技巧进行实现。以下代码是根据本人对Incepton V3网络的理解和现有资源(《TensorFlow实战》等)整理而成,代码注释若有错误请指正。
# -*- coding: utf-8 -*-
import os
os.environ['TF_CPP_MIN_LOG_LEVEL'] = '2'

# Inception V3    42层深
# 载入模块、TensorFlow,定义截断正态分布函数trunc_normal
from datetime import datetime
import math
import time
import tensorflow as tf
slim = tf.contrib.slim
trunc_normal = lambda stddev: tf.truncated_normal_initializer(0.0, stddev)

# 定义用来生成网络默认参数的函数inception_v3_arg_scope
def inception_v3_arg_scope(weight_decay=0.00004,
                           stddev=0.1,
                           batch_norm_var_collection='moving_vars'):
    batch_norm_params = {
        'decay': 0.9997,
        'epsilon': 0.001,
        'updates_collections': tf.GraphKeys.UPDATE_OPS,
        'variables_collections': {
            'beta': None,
            'gamma': None,
            'moving_mean': [batch_norm_var_collection],
            'moving_variance': [batch_norm_var_collection],
        }
    }
    # 定义slim.arg_scope给函数的参数自动赋予默认值
    with slim.arg_scope([slim.conv2d, slim.fully_connected],
                        weights_regularizer=slim.l2_regularizer(weight_decay)):
        with slim.arg_scope(
    
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值