CNN理解与实现

组成部分

  • Convolution Layer
  • Pool Layer:
    • Max-pooling layer
    • Average-pooling layer
  • Full Connected(FC) Layer

需要的函数

注意

  • 参数\(W\), \(b\)和数据\(X\)它们的维度是一样的, 这个非常重要, 在使用代码实现的时候不至于搞懵; 如果\(X\)是RGB图像, 它的维度假设为\((100, 24, 24, 3)\), 100表示样本数量, 24与24位图像的高与宽(我们人类习惯讲成宽与高, 但是在编程语言领域中, 如Matlab和Python中, 都是先锁定y轴, 再锁定x轴的, 同样迁移过来, 我们应该采用高与宽), 此时的W也是4个维度的, 加入为\((3, 3, 3, 8)\), 这里前两个3表示W(filter)的高与宽, 第三个3位通道数量, 要与X的通道数一致, 8表示W(filter)的个数, 可就是这次过滤器过滤之后得到的结果的通道数, 为b就简单了, 为\((1, 1, 1, 8)\), 每一个filter对应一个b

实现

  • zero_pad: 使用0填充原始图像, 在水平方向与垂直方向添加padding
  • conv_single: 使用一个过滤器\(W\)对原始图像中的slice进行卷积
  • conv_forward: 卷积的前向传播
    • 根据公式计算出过滤之后的维度: \(n_h=int({(n_{hprev}+2p-f)\over{s}}+1)\), \(n_w=int({(n_{wprev}+2p-f)\over{s}}+1)\), 其中\(n_{hprev}\)为上一层的高度, \(n_{wprev}\)为上一层的宽度, \(f\)为filter的维度, filter一般为\(f \times f\), \(p\)为padding, \(n_h\)表示通过过滤器之后得到的结果的高度, \(n_w\)表示通过过滤器之后得到的结果的宽度, \(s\)表示stride, 为步幅
    • 调用zero_pad函数为\(A_{prev}\)添加padding, 使用\(int()\)是为了向下取整
    • 由于卷积比较复杂, 这里不适用矩阵的计算, 而是采用多个嵌套的for循环

      for i in range(m):
      # 获取到一个样本, 因为我们不打算使用矩阵化提高计算速率, 这样简单一点
      a_prev_pad = A_prev_pad[i, :, :, :]
      for h in range(n_h):
      for w in range(n_w):
      for c in range(n_C):
      # 此公式将从原始的a_prev_pad单样本的图像中获取到一个Convolution Window
      vert_start = h * stride
      vert_end = vert_start + f
      horiz_start = w * stride
      horiz_end = horiz_start + f
      # 得到在原始图像中与filter同样大小窗口
      a_slice_prev = a_prev_pad[vert_start:vert_end, horiz_start:horiz_end, :]
      # 调用conv_single进行卷积计算
      Z[i, h, w, c] = conv_single(a_slice_prev, W[:, :, :, c], b[:, :, :, c])
      # 计算激活函数
      A[i, h, w, c] = activate(Z[i, h, w, c])
  • pool_forward: 池化层的前向传播
    • 根据公式计算出\(n_h\)与\(n_w\)
    • 同样不使用矩阵计算, 使用多个for循环迭代, 这样简单

      for i in range(m):
      a_prev = A_prev[i, :, :, :]
      for h in range(n_h):
      for w in range(n_w):
      for c in range(n_c):
      # 计算窗口坐标
      vert_start = h * stride
      vert_end = vert_start + f
      horiz_start = w * stride
      horiz_end = horiz_start + f
      a_slice = a_prev[vert_start:vert_end, horiz_start:horiz_end, c]
      # 这里采用Max-pooling的计算方法
      # 其中A为我们函数的返回矩阵
      A[i, h, w, c] = np.max(a_slice)
  • compute_cost: 计算损失函数\(J\)
  • conv_backward:
    • 计算dA, dW和db

      for i in range(m):
      da_prev_pad = dA_prev_pad[i, :, :, :]
      a_prev_pad = A_prev_pad[i, :, :, :]
      for h in range(n_h):
      for w in range(n_w):
      for c in range(n_C):
      vert_start = h * stride
      vert_end = vert_start + f
      horiz_start = h * stride
      horiz_end = horiz_start + f
      a_slice = a_prev_pad[vert_start:vert_end, horiz_start:horiz_end, :]
      da_prev_pad[vert_start:vert_end, horiz_start:horiz_end, :] += dZ[i, h, w, c] * W[:, :, :, c]
      dW[:, :, :, c] += dZ[i, h, w, c] * a_slice
      db[:, :, :, c] += dZ[i, h, w, c]
      dA_prev[i, :, :, :] = da_prev_pad[pad:-pad, pad:-pad, :]
  • pool_backward:
    • conv_backward类似

    for i in range(m):
    a_prev = A_prev[i, :, :, :]
    for h in range(n_h):
    for w in range(n_w):
    for c in range(n_C):
    vert_start = h * stride
    vert_end = vert_start + f
    horiz_start = w * stride
    horiz_end = horiz_start + f
    a_slice = a_prev[vert_start:vert_end, horiz_start:horiz_end, c]
    mask = create_mask_from_window(a_slice)
    dA_prev[i, vert_start: vert_end, horiz_start: horiz_end, c] += np.multiply(mask, dA[i,h,w,c])

总结反向传播用到的公式

  • 对于单个样本来说, 不使用矩阵表达式
  • \(da += dw \times dz\)
  • \(dw += dz \times a\)
  • \(db += dz\)

使用的结构

  • Conv->ReLU->Pool->Conv->ReLU->Pool->FC

CNN理解与实现的更多相关文章

  1. 卷积神经网络CNN理解

    自今年七月份以来,一直在实验室负责卷积神经网络(Convolutional Neural Network,CNN),期间配置和使用过theano和cuda-convnet.cuda-convnet2. ...

  2. 基于pytorch的CNN、LSTM神经网络模型调参小结

    (Demo) 这是最近两个月来的一个小总结,实现的demo已经上传github,里面包含了CNN.LSTM.BiLSTM.GRU以及CNN与LSTM.BiLSTM的结合还有多层多通道CNN.LSTM. ...

  3. 卷积神经网络CNN介绍:结构框架,源码理解【转】

    1. 卷积神经网络结构 卷积神经网络是一个多层的神经网络,每层都是一个变换(映射),常用卷积convention变换和pooling池化变换,每种变换都是对输入数据的一种处理,是输入特征的另一种特征表 ...

  4. Deep Learning 学习随记(八)CNN(Convolutional neural network)理解

    前面Andrew Ng的讲义基本看完了.Andrew讲的真是通俗易懂,只是不过瘾啊,讲的太少了.趁着看完那章convolution and pooling, 自己又去翻了翻CNN的相关东西. 当时看讲 ...

  5. CNN笔记:通俗理解卷积神经网络【转】

    本文转载自:https://blog.csdn.net/v_july_v/article/details/51812459 通俗理解卷积神经网络(cs231n与5月dl班课程笔记) 1 前言 2012 ...

  6. 理解NLP中的卷积神经网络(CNN)

    此篇文章是Denny Britz关于CNN在NLP中应用的理解,他本人也曾在Google Brain项目中参与多项关于NLP的项目. · 翻译不周到的地方请大家见谅. 阅读完本文大概需要7分钟左右的时 ...

  7. 理解CNN中的通道 channel

    在深度学习的算法学习中,都会提到 channels 这个概念.在一般的深度学习框架的 conv2d 中,如 tensorflow .mxnet ,channels 都是必填的一个参数. channel ...

  8. Deep Visualization:可视化并理解CNN(转)

    转载地址:https://zhuanlan.zhihu.com/p/24833574 一.前言 CNN作为一个著名的深度学习领域的“黑盒”模型,已经在计算机视觉的诸多领域取得了极大的成功,但是,至今没 ...

  9. 理解CNN中的感受野(receptive-field)

    1. 阅读论文:Understanding the Effective Receptive Field in Deep Convolutional Neural Networks 理解感受野 定义:r ...

随机推荐

  1. linux清理磁盘

    https://blog.csdn.net/u012660464/article/details/78923011 有时候,服务突然挂了,再次启动却启动不了.一看,原来是磁盘空间被占满啦,那么,怎么清 ...

  2. 在一般处理程序清理cookie

    清理cookie在ashx里面很奇怪,因为直接设置过期时间并不能成功,cookie还是会存在.所以需要添加一个同名的Cookie设置过期时间覆盖 HttpCookie cookie = null; / ...

  3. WPF 新手引导

    参考了https://www.cnblogs.com/ZXdeveloper/p/8391864.html,自己随便实现了一个,记录下,比较丑 <Window x:Class="Use ...

  4. VisualStudio2017 远程 调试 IIS 服务器 web网站

    小伙伴们,本次测试好好的程序发布到服务器挂到IIS后我勒个*,,, 神马情况,为啥和我本地运行结果不一致,Fuc*... 没遇到的小伙伴估计也看不到此篇文章了吧,Log日志调试,嗯 不错,good i ...

  5. MaxScript镜像函数

    看到有网友需要写的,其实镜像就是缩放改为负数 Fn MirrorObject argObjects argAxisName = ( local axisNames = #(#x,#y,#z) do ( ...

  6. 基于GeoServer切片地图服务的发布

    接着上一篇文章,如何将JPG格式的图片转化为带地理坐标的TIFF格式里提及的最近的一个项目,数据源是一张高分辨率的2.5维图片,现在已经成功转化成了带有地理坐标的TIFF格式.下面将介绍借助GeoSe ...

  7. NOI2009 区间

    题目链接:戳我 60分部分分还是很好拿的,排序(按照左端点为第一关键字,右端点为第二关键字)之后一个\(O(n^2)\),暴力判交,更新最小值,就可以水过前12个测试点. #include<io ...

  8. Python3.5 学习五

    心灵鸡汤电影推荐: 阿甘正传.辛德勒名单.肖申克的救赎.勇敢的心.角斗士.美国丽人.教父.钢琴师.指环王.西雅图不眠夜.廊桥遗梦.可可西里的美丽传说.放牛班的春天.血钻.战争之王.上帝之城.中央车站. ...

  9. java—实现一个监听器HttpServletRequest的创建销毁、在线人数 (56)

    在JavaWeb中的监听器分类 在Javaweb中存在三个被监听对象: HttpServletRequest HttpSessoin ServletContext 监听者 被监听者 监听到事件对象 H ...

  10. Jmeter非GUI运行,生成html报告

    一.JMete执行方式 JMeter执行方式有2种,一种是GUI模式,一种是非GUI模式.GUI模式就是界面模式,非GUI模式就是命令行模式.界面模式主要用来编写和调试脚本用的,项目的真正执行最好是采 ...