图像处理深度学习_深度学习 图像处理 图像大小 - CSDN
  • 图像处理深度学习

    2018-05-05 22:02:57
    第一种 自我激发型 基于图像处理的方法,如图像增强和图像复原,以及曾经很火的超分辨率算法。都是在不增加额外信息的前提下的实现方式。 1. 图像增强 图像增强是图像预处理中非常重要且常用的一种方法,图像...

    针对模糊图像的处理,个人觉得主要分两条路,一种是自我激发型,另外一种属于外部学习型。接下来我们一起学习这两条路的具体方式。

    第一种 自我激发型

      基于图像处理的方法,如图像增强和图像复原,以及曾经很火的超分辨率算法。都是在不增加额外信息的前提下的实现方式。 
       
    1. 图像增强

      图像增强是图像预处理中非常重要且常用的一种方法,图像增强不考虑图像质量下降的原因,只是选择地突出图像中感兴趣的特征,抑制其它不需要的特征,主要目的就是提高图像的视觉效果。先上一张示例图: 
       
      这里写图片描述 
       
      图像增强中常见的几种具体处理方法为:

    1. 直方图均衡

        在图像处理中,图像直方图表示了图像中像素灰度值的分布情况。为使图像变得清晰,增大反差,凸显图像细节,通常希望图像灰度的分布从暗到亮大致均匀。直方图均衡就是把那些直方图分布不均匀的图像(如大部分像素灰度集中分布在某一段)经过一种函数变换,使之成一幅具有均匀灰度分布的新图像,其灰度直方图的动态范围扩大。用于直方均衡化的变换函数不是统一的,它是输入图像直方图的积分,即累积分布函数。

    2. 灰度变换

        灰度变换可使图像动态范围增大,对比度得到扩展,使图像清晰、特征明显,是图像增强的重要手段之一。它主要利用图像的点运算来修正像素灰度,由输入像素点的灰度值确定相应输出像素点的灰度值,可以看作是“从像素到像素”的变换操作,不改变图像内的空间关系。像素灰度级的改变是根据输入图像f(x,y)灰度值和输出图像g(x,y)灰度值之间的转换函数g(x,y)=T[f(x,y)]进行的。 
        灰度变换包含的方法很多,如逆反处理、阈值变换、灰度拉伸、灰度切分、灰度级修正、动态范围调整等。

    3. 图像平滑

        在空间域中进行平滑滤波技术主要用于消除图像中的噪声,主要有邻域平均法、中值滤波法等等。这种局部平均的方法在削弱噪声的同时,常常会带来图像细节信息的损失。 
        邻域平均,也称均值滤波,对于给定的图像f(x,y)中的每个像素点(x,y),它所在邻域S中所有M个像素灰度值平均值为其滤波输出,即用一像素邻域内所有像素的灰度平均值来代替该像素原来的灰度。 
        中值滤波,对于给定像素点(x,y)所在领域S中的n个像素值数值{f1,f2,…,fn},将它们按大小进行有序排列,位于中间位置的那个像素数值称为这n个数值的中值。某像素点中值滤波后的输出等于该像素点邻域中所有像素灰度的中值。中值滤波是一种非线性滤波,运算简单,实现方便,而且能较好的保护边界。

    4. 图像锐化

        采集图像变得模糊的原因往往是图像受到了平均或者积分运算,因此,如果对其进行微分运算,就可以使边缘等细节信息变得清晰。这就是在空间域中的图像锐化处理,其的基本方法是对图像进行微分处理,并且将运算结果与原图像叠加。从频域中来看,锐化或微分运算意味着对高频分量的提升。常见的连续变量的微分运算有一阶的梯度运算、二阶的拉普拉斯算子运算,它们分别对应离散变量的一阶差分和二阶差分运算。

    2. 图像复原

      这里写图片描述 
       
      其目标是对退化(传播过程中的噪声啊,大气扰动啊好多原因)的图像进行处理,尽可能获得未退化的原始图像。如果把退化过程当一个黑匣子(系统H),图片经过这个系统变成了一个较烂的图。这类原因可能是光学系统的像差或离焦、摄像系统与被摄物之间的相对运动、电子或光学系统的噪声和介于摄像系统与被摄像物间的大气湍流等。图像复原常用二种方法。当不知道图像本身的性质时,可以建立退化源的数学模型,然后施行复原算法除去或减少退化源的影响。当有了关于图像本身的先验知识时,可以建立原始图像的模型,然后在观测到的退化图像中通过检测原始图像而复原图像。 
       
    3. 图像超分辨率   
      一张图我们想脑补细节信息好难,但是相似的多幅图我们就能互相脑洞了。所以,我们可以通过一系列相似的低分辨图来共同脑补出一张高清晰图啊,有了这一张犯罪人的脸,我就可以画通缉令了啊。。。 
      超分辨率复原技术的目的就是要在提高图像质量的同时恢复成像系统截止频率之外的信息,重建高于系统分辨率的图像。继续说超分辨,它其实就是根据多幅低质量的图片间的关系以及一些先验知识来重构一个高分辨的图片。示例图如下: 
    这里写图片描述

    第二种 外部学习型

      外部学习型,就如同照葫芦画瓢一样的道理。其算法主要是深度学习中的卷积神经网络,我们在待处理信息量不可扩充的前提下(即模糊的图像本身就未包含场景中的细节信息),可以借助海量的同类数据或相似数据训练一个神经网络,然后让神经网络获得对图像内容进行理解、判断和预测的功能,这时候,再把待处理的模糊图像输入,神经网络就会自动为其添加细节,尽管这种添加仅仅是一种概率层面的预测,并非一定准确。

      本文介绍一种在灰度图像复原成彩色RGB图像方面的代表性工作:《全局和局部图像的联合端到端学习图像自动着色并且同时进行分类》。利用神经网络给黑白图像上色,使其变为彩色图像。稍作解释,黑白图像,实际上只有一个通道的信息,即灰度信息。彩色图像,则为RGB图像(其他颜色空间不一一列举,仅以RGB为例讲解),有三个通道的信息。彩色图像转换为黑白图像极其简单,属于有损压缩数据;反之则很难,因为数据不会凭空增多。

      搭建一个神经网络,给一张黑白图像,然后提供大量与其相同年代的彩色图像作为训练数据(色调比较接近),然后输入黑白图像,人工智能按照之前的训练结果为其上色,输出彩色图像,先来看一张效果图: 
      这里写图片描述

    1. 本文工作 
      •  用户无干预的灰度图像着色方法。 
      •  一个新颖的端到端网络,联合学习图像的全局和局部特征。 
      •  一种利用分类标签提高性能的学习方法。 
      •  基于利用全局特征的风格转换技术。 
      •  通过用户研究和许多不同的例子深入评估模型,包括百年的黑白照片。

    2. 着色框架 
         
        模型框架包括四个主要组件:低级特征提取网络,中级特征提取网络,全局特征提取网络和着色网络。 这些部件都以端对端的方式紧密耦合和训练。 模型的输出是图像的色度,其与亮度融合以形成输出图像。 
                 这里写图片描述

    3. 与另外两个工作对比

      • Gustav Larsson, Michael Maire, and Gregory Shakhnarovich. Learning Representations for Automatic Colorization. In ECCV 2016. 
      •Richard Zhang, Phillip Isola, and Alexei A. Efros. Colorful Image Colorization. In ECCV 2016.

    这里写图片描述

    参考文献:

    网页: 
    http://hi.cs.waseda.ac.jp/~iizuka/projects/colorization/extra.html

    代码: 
    https://github.com/satoshiiizuka/siggraph2016_colorization

    论文2:  
    http://richzhang.github.io/colorization/

    在线demo: 
    http://demos.algorithmia.com/colorize-photos/

    展开全文
  • 1 深度学习概述 tips:后面实践部分,代码量偏大,若看着不舒服,可以看看文中写的思路,然后在下面这个链接直接下代码细看 链接:https://pan.baidu.com/s/1uixRdG-K5HGYD0gOxZ-86Q 提取码:a55o 最后也有...

    1 深度学习概述

    tips:后面实践部分,代码量偏大,若看着不舒服,可以看看文中写的思路,然后在下面这个链接直接下代码细看

    链接:https://pan.baidu.com/s/1uixRdG-K5HGYD0gOxZ-86Q      提取码:a55o    最后也有二维码供保存 

    1.1 深度学习发展的介绍

    在机器学习中,我们主要处理的分类问题,回归问题的模型都属于浅层结构的简单学习,通常只包含1到3层的非线性特征转换层,例如一些典型的浅层结构:逻辑回归(LR)、支持向量机(SVM)和多层感知器(MLP)等。这些浅层模型对复杂函数的表示能力有限,无法提取到更高维度的特征。比如在图像、语音的处理上,机器学习就很难获得很好的表现。而深度学习可通过学习一种深层非线性网络结构,表征输入数据,实现复杂函数逼近,并展现了强大的从少数样本集中学习数据集本质特征的能力。

    2006年,加拿大多伦多大学教授、机器学习领域泰斗——Geoffrey Hinton和他的学生Ruslan Salakhutdinov在顶尖学术刊物《科学》上发表了一篇文章,开启了深度学习在学术界和工业界的浪潮。自2006年以来,深度学习在学术界持续升温。斯坦福大学、纽约大学、加拿大蒙特利尔大学等成为研究深度学习的重镇。

    1.2 深度学习的定义

    通过前面对深度学习发展的介绍,这里我们给出Google在2013年10月对深度学习的定义,帮助读者更好的理解深度学习。

    “深度学习是机器学习的一系列算法,它试图在多个层次中进行学习,每层对应于不同级别的抽象。它一般使用人工神经网络,学习到的统计模型中的不同层对应于不同级别的概念,高层概念取决于低层概念,而且同一低层的概念有助于确定多个高层概念。”

    1.3 深度学习存在的问题

    深度学习虽然具有强大的特征表达能力,但是依然存在以下问题。

    ①理论问题

    统计学习方面的问题,我们不知道我们需要多少训练样本才能学习到足够好的深度模型。

    计算方面的问题,我们需要多少计算资源才能通过训练得到更好的模型?理想的计算优化方法是什么?由于深度模型都是非凸函数,在这方面的理论研究极其困难。

    ②建模问题

    在推进深度学习的学习理论和计算理论的同时,我们是否可以提出新的分层模型,使其不但具有传统深度模型所具有的强大表示能力,还具有其他的好处,比如更容易做理论分析。另外,针对具体应用问题,我们如何设计一个最适合的深度模型来解决问题?一个更有意思的问题是,是否存在可能建立一个通用的深度模型或深度模型的建模语言,作为统一的框架来处理语音、图像和语言?

    ③工程问题

    如何获取大量的数据,更好的处理数据是各家企业需要解决的问题。如何在工程上利用大规模的并行计算平台来实现海量数据训练,是各家公司从事深度学习技术研发首先要解决的问题。

    1.4 深度学习的前景

    目前我们使用的Android手机中google的语音识别,百度识图,google的图片搜索,都已经使用到了深度学习技术。Facebook在去年名为DeepFace的项目中对人脸识别的准备率第一次接近人类肉眼(97.25% vs 97.5%)。大数据时代,结合深度学习的发展在未来对我们生活的影响无法估量。保守而言,很多目前人类从事的活动都将因为深度学习和相关技术的发展被机器取代,如自动汽车驾驶,无人飞机,以及更加职能的机器人等。深度学习的发展让我们第一次看到并接近人工智能的终极目标。

     

    2 深度学习的分类

    深度学习是基于机器学习延伸出来的一个的领域。因此深度学习的分类与机器学习的分类有着类似的分类方式。以下内容便是对深度学习的分类介绍。

    2.1 有监督学习的深度学习网络结构

    有监督学习是机器学习和深度学习中最常见的形式。举例来说,我们要建立一个系统,它能够对一个包含了一座房子、一辆汽车、一个人或一个宠物的图像进行分类。我们先收集大量的房子,汽车,人与宠物的图像的数据集,并对每个对象标上它的类别。在训练期间,机器会获取一副图片,然后产生一个输出,这个输出以向量形式的分数来表示,每个类别都有一个这样的向量。我们希望所需的类别在所有的类别中具有最高的得分,但是这在训练之前是不太可能发生的。通过计算一个目标函数可以获得输出分数和期望模式分数之间的误差(或距离)。然后机器会修改其内部可调参数,以减少这种误差。这些可调节的参数,通常被称为权值,它们是一些实数,可以被看作是一些“旋钮”,定义了机器的输入输出功能。在典型的深度学习系统中,有可能有数以百万计的样本和权值,和带有标签的样本,用来训练机器。为了正确地调整权值向量,该学习算法计算每个权值的梯度向量,表示了如果权值增加了一个很小的量,那么误差会增加或减少的量。权值向量然后在梯度矢量的相反方向上进行调整。我们的目标函数,所有训练样本的平均,可以被看作是一种在权值的高维空间上的多变地形。负的梯度矢量表示在该地形中下降方向最快,使其更接近于最小值,也就是平均输出误差低最低的地方。

    常见的有监督深度学习网络结构有cnn(卷积神经网络)、rnn(循环神经网络),接下来对这两种网络进行介绍。

    • CNN(Convolutional Neural Network卷积神经网络)

    CNN是图像处理上最常用的一种深度网络结构,它结构图如图:

                                                                    图 2.1

    从图2.1中可以看出cnn主要包括四个部分:卷积层、激励层、池化层和全连接层,这四个部分构建了cnn的基本网络结构。接下来讲讲这几个层的内涵。

    卷积层,何为卷积操作?对图像(不同的数据窗口数据)和滤波矩阵(一组固定的权重:因为每个神经元的权重固定,所以又可以看做一个恒定的滤波器filter)做内积(逐个元素相乘再求和)的操作就是所谓的『卷积』操作,也是卷积神经网络的名字来源。卷积层通过卷积运算的作用是可用来获取图像的特征,通过堆叠这些模块,用不同的卷积核来获取更高阶的特征,堆叠起来的深度结构中,卷积核的权重参数是共享的,使得深度结构能获取更高维特征,但是参数量不会大幅增多。

    激励层,在图15.2.1中没有显式的指明激励层,激励层通常用在卷积运算之后,选择一个合适的激励函数(如sigmoid、ReLU等激励函数)来对卷积运算的结果进行处理。激活函数的作用是把“激活的神经元的特征”通过函数把特征保留并映射出来(保留特征,去除一些数据中是的冗余),解决网络结构的非线性问题。

    池化层,对数据进行下采样(数据压缩),可以避免过拟合,减少数据特征、数据计算量等操作。池化层一般有两种方式:Max pooling(常用,多用)和 Averarg pooling。

    全连接层,这一层的连接即为神经网络结构中神经元在每一层之间的连接。全连接层在整个卷积神经网络中起到“分类器”的作用。如果说卷积层、池化层和激活函数层等操作是将原始数据映射到隐层特征空间的话,全连接层则起到将学到的“分布式特征表示”映射到样本标记空间的作用。通过这一层之后可接自定义的一层结构用来做分类或者回归问题。

    CNN在计算机视觉上取得了长足的进步,通过深度网络结构获取到更多高维度图像的特征用来处理图像,并且通过卷积运算使得参数得以控制。近几年CNN在计算机视觉取得了广泛的应用。

    • RNN(Recurrent Neural Networks 循环神经网络)

    RNNs在众多自然语言处理(Natural Language Processing, NLP)中取得了巨大成功以及广泛应用。RNNs的目的使用来处理序列数据。在传统的神经网络模型中,是从输入层到隐含层再到输出层,层与层之间是全连接的,每层之间的节点是无连接的。但是这种普通的神经网络对于很多问题却无能无力。例如,你要预测句子的下一个单词是什么,一般需要用到前面的单词,因为一个句子中前后单词并不是独立的。RNNs之所以称为循环神经网路,即一个序列当前的输出与前面的输出也有关。具体的表现形式为网络会对前面的信息进行记忆并应用于当前输出的计算中,即隐藏层之间的节点不再无连接而是有连接的,并且隐藏层的输入不仅包括输入层的输出还包括上一时刻隐藏层的输出。理论上,RNNs能够对任何长度的序列数据进行处理。但是在实践中,为了降低复杂性往往假设当前的状态只与前面的几个状态相关,图2.1-2便是一个典型的RNNs:

                                                                        图 2.1-2

    图2.1-2将循环神经网络进行展开成一个全神经网络。例如,对一个包含5个单词的语句,那么展开的网络便是一个五层的神经网络,每一层代表一个单词。对于该网络的计算过程如下:

    • xt表示第t,t=1,2,3...步(step)的输入。比如,x1为第二个词的one-hot向量(根据图15.2.1-2,x0为第一个词); 
      在使用计算机对自然语言进行处理,需要将自然语言处理成为机器能够识别的符号,加上在机器学习过程中,需要将其进行数值化。而词是自然语言理解与处理的基础,因此需要对词进行数值化,词向量便是一种可行又有效的方法。何为词向量,即使用一个指定长度的实数向量v来表示一个词。有一种种最简单的表示方法,就是使用One-hot vector表示单词,即根据单词的数量|V|生成一个|V| * 1的向量,当某一位为一的时候其他位都为零,然后这个向量就代表一个单词。
    • st为隐藏层的第t步的状态,它是网络的记忆单元。 st根据当前输入层的输出与上一步隐藏层的状态进行计算。st=f(Uxt+Wst−1),其中f一般是非线性的激活函数,如tanhReLU,在计算s0时,即第一个单词的隐藏层状态,需要用到s−1,但是其并不存在,在实现中一般置为0向量;
    • ot是第t步的输出,如下一个单词的向量表示,ot=softmax(Vst). 
      需要注意的是:

    ①你可以认为隐藏层状态st是网络的记忆单元. st包含了前面所有步的隐藏层状态。而输出层的输出ot只与当前步的st有关,在实践中,为了降低网络的复杂度,往往st只包含前面若干步而不是所有步的隐藏层状态;

    ②在传统神经网络中,每一个网络层的参数是不共享的。而在RNNs中,每输入一步,每一层各自都共享参数U,V,W。其反应者RNNs中的每一步都在做相同的事,只是输入不同,因此大大地降低了网络中需要学习的参数。

    ③上图中每一步都会有输出,但是每一步都要有输出并不是必须的。比如,我们需要预测一条语句所表达的情绪,我们仅仅需要关系最后一个单词输入后的输出,而不需要知道每个单词输入后的输出。同理,每步都需要输入也不是必须的。RNNs的关键之处在于隐藏层,隐藏层能够捕捉序列的信息。

    RNNs在自然语言处理中有很多成功的应用,比如在机器翻译、语音识别、图像描述等方面都表现出不错的效果。

    2.2 无监督学习的深度学习网络结构

    无监督的学习方法,这种方法可以创建一些网络层来检测特征而不使用带标签的数据,这些网络层可以用来重构或者对特征检测器的活动进行建模。通过预训练过程,深度网络的权值可以被初始化为有意思的值。然后一个输出层被添加到该网络的顶部,并且使用标准的反向传播算法进行微调。这个工作对手写体数字的识别以及行人预测任务产生了显著的效果,尤其是带标签的数据非常少的时候。接下来介绍两种无监督的网络结构模型。

    受限玻尔兹曼机(Restricted Boltzmann Machine,简称RBM)是由Hinton和Sejnowski于1986年提出的一种生成式随机神经网络(generative stochastic neural network),该网络由一些可见单元(visible unit,对应可见变量,亦即数据样本)和一些隐藏单元(hidden unit,对应隐藏变量)构成,可见变量和隐藏变量都是二元变量,亦即其状态取{0,1}。整个网络是一个二部图,只有可见单元和隐藏单元之间才会存在边,可见单元之间以及隐藏单元之间都不会有边连接,如图2.2-1:

                                                                      图 2.2-1

    图2.2-1所示的RBM含有12个可见单元(构成一个向量v)和3个隐藏单元(构成一个向量h),W是一个12*3的矩阵,表示可见单元和隐藏单元之间的边的权重。

    RBM的权重的学习算法:

    • 取一个样本数据,把可见变量的状态设置为这个样本数据。随机初始化W。
    • 根据式子-9的第一个公式来更新隐藏变量的状态,亦即hj以P(hj=1|v)的概率设置为状态1,否则为0。然后对于每个边vihj,计算Pdata(vihj)=vi*hj(注意,vi和hj的状态都是取{0,1})。
    • 根据h的状态和式子-9的第二个公式来重构v1,并且根据v1和式子-9的第一个公式来求得h1,计算Pmodel(v1ih1j)=v1i*h1j。
    • 更新边vihj的权重Wij为Wij=Wij+L*(Pdata(vihj)=Pmodel(v1ih1j))。
    • 取下一个数据样本,重复1-4的步骤。
    • 以上过程迭代K次。

    对应上述权重学习方法,可参考图2.2-2进行理解:

                                                                         图 2.2-2

    RBF是一种非监督学习的网络结构,它的用处在于降低维度, 分类, 回归, 特征学习。

     

    深度信念网络由 Geoffrey Hinton 在 2006 年提出。它是一种生成模型,通过训练其神经元间的权重,我们可以让整个神经网络按照最大概率来生成训练数据。多个Restricted Boltzmann Machines堆叠而成。DBN的网络结构如图2.2-3:

                                                                       图 2.2-3

    DBN训练过程: 

    1) 首先充分训练第一个 RBM; 

    2) 固定第一个 RBM 的权重和偏移量,然后使用其隐性神经元的状态,作为第二个 RBM 的输入向量; 

    3) 充分训练第二个 RBM 后,将第二个 RBM 堆叠在第一个 RBM 的上方; 

    4) 重复以上三个步骤任意多次; 

    5) 如果训练集中的数据有标签,那么在顶层的 RBM 训练时,这个 RBM 的显层中除了显性神经元,还需要有代表分类标签的神经元,一起进行训练: 

    a) 假设顶层 RBM 的显层有 500 个显性神经元,训练数据的分类一共分成了 10 类; 

    b) 那么顶层 RBM 的显层有 510 个显性神经元,对每一训练训练数据,相应的标签神经元被打开设为 1,而其他的则被关闭设为 0。

    DBN的几点说明:

    1. 每层的神经元不与本层的其他神经元交流。
    2. 最后一层通常是classification layer (比如Softmax)。
    3. 除了第一层和最后一层,每层都有两个作用:对于前一层作为隐藏层,对于后一层作为输入层。

    DBN多用在降低维度, 图像搜索(压缩), 数据压缩, 信息检索。

     

    3 项目实战

    在这里将分别介绍上述两种深度网络结构的示例,采用mnist手写数字数据集以及tensorflow框架进行实战,mnist数据可在官网这进行下载(http://yann.lecun.com/exdb/mnist/)。

    3.1 使用RBM对mnist数据集进行生成

    实例:RBM深度网络结构的实现

    • 首先我们用一个基类来存放受限玻尔兹曼机RBM的模型结构。创建一个模块命名为rbm.py用来构建RBM网络结构。
    1. from __future__ import print_function  
    2.   
    3. import tensorflow as tf  
    4. import numpy as np  
    5. import sys  
    6.   
    7. def tf_xavier_init(fan_in, fan_out, *, const=1.0, dtype=np.float32):  
    8.     ''''' 该函数对权重w参数进行初始化 '''  
    9.     k = const * np.sqrt(6.0 / (fan_in + fan_out))  
    10.     return tf.random_uniform((fan_in, fan_out), minval=-k, maxval=k, dtype=dtype)  
    11.   
    12.   
    13. class RBM:  
    14.     ''''' 用一个类来存放受限玻尔兹曼机RBM模型结构 '''  
    15.     def __init__(self,  
    16.                  n_visible,     # 可见变量数  
    17.                  n_hidden,      # 隐藏层数目  
    18.                  learning_rate=0.01,    # 学习速率  
    19.                  momentum=0.95,         # 动量参数  
    20.                  xavier_const=1.0,      # 初始化设置参数  
    21.                  err_function='mse',    # 损失函数选择参数  
    22.                  use_tqdm=False,    
    23.                  tqdm=None):  
    24.         if not 0.0 <= momentum <= 1.0:  
    25.             raise ValueError('momentum should be in range [0, 1]')  
    26.   
    27.         if err_function not in {'mse''cosine'}:  
    28.             raise ValueError('err_function should be either \'mse\' or \'cosine\'')  
    29.   
    30.         self._use_tqdm = use_tqdm  
    31.         self._tqdm = None  
    32.   
    33.         if use_tqdm or tqdm is not None:  
    34.             from tqdm import tqdm  
    35.             self._tqdm = tqdm  
    36.   
    37.         self.n_visible = n_visible  
    38.         self.n_hidden = n_hidden  
    39.         self.learning_rate = learning_rate  
    40.         self.momentum = momentum  
    41.   
    42.         self.x = tf.placeholder(tf.float32, [None, self.n_visible])  
    43.         self.y = tf.placeholder(tf.float32, [None, self.n_hidden])  
    44.   
    45.         self.w = tf.Variable(tf_xavier_init(self.n_visible, self.n_hidden, const=xavier_const), dtype=tf.float32)  
    46.         self.visible_bias = tf.Variable(tf.zeros([self.n_visible]), dtype=tf.float32)  
    47.         self.hidden_bias = tf.Variable(tf.zeros([self.n_hidden]), dtype=tf.float32)  
    48.   
    49.         self.delta_w = tf.Variable(tf.zeros([self.n_visible, self.n_hidden]), dtype=tf.float32)  
    50.         self.delta_visible_bias = tf.Variable(tf.zeros([self.n_visible]), dtype=tf.float32)  
    51.         self.delta_hidden_bias = tf.Variable(tf.zeros([self.n_hidden]), dtype=tf.float32)  
    52.   
    53.         self.update_weights = None  
    54.         self.update_deltas = None  
    55.         self.compute_hidden = None  
    56.         self.compute_visible = None  
    57.         self.compute_visible_from_hidden = None  
    58.   
    59.         self._initialize_vars()  
    60.   
    61.         assert self.update_weights is not None  
    62.         assert self.update_deltas is not None  
    63.         assert self.compute_hidden is not None  
    64.         assert self.compute_visible is not None  
    65.         assert self.compute_visible_from_hidden is not None  
    66.   
    67.         if err_function == 'cosine':  
    68.             x1_norm = tf.nn.l2_normalize(self.x, 1)  
    69.             x2_norm = tf.nn.l2_normalize(self.compute_visible, 1)  
    70.             cos_val = tf.reduce_mean(tf.reduce_sum(tf.mul(x1_norm, x2_norm), 1))  
    71.             self.compute_err = tf.acos(cos_val) / tf.constant(np.pi)  
    72.         else:  
    73.             self.compute_err = tf.reduce_mean(tf.square(self.x - self.compute_visible))  
    74.   
    75.         init = tf.global_variables_initializer()  
    76.         self.sess = tf.Session()  
    77.         self.sess.run(init)  
    78.   
    79.     def _initialize_vars(self):  
    80.         pass  
    81.   
    82.     def get_err(self, batch_x):  
    83.         return self.sess.run(self.compute_err, feed_dict={self.x: batch_x})  
    84.   
    85.     def reconstruct(self, batch_x):  
    86.         ''''' 
    87.         该函数根据训练参数返回可见层节点 
    88.         '''  
    89.         return self.sess.run(self.compute_visible, feed_dict={self.x: batch_x})  
    90.   
    91.     def partial_fit(self, batch_x):  
    92.         self.sess.run(self.update_weights + self.update_deltas, feed_dict={self.x: batch_x})  
    93.   
    94.     # 该方法对输入数据进行训练,学习  
    95.     def fit(self,  
    96.             data_x,  
    97.             n_epoches=10,  
    98.             batch_size=10,  
    99.             shuffle=True,  
    100.             verbose=True):  
    101.         assert n_epoches > 0  
    102.   
    103.         n_data = data_x.shape[0]  
    104.   
    105.         if batch_size > 0:  
    106.             n_batches = n_data // batch_size + (0 if n_data % batch_size == 0 else 1)  
    107.         else:  
    108.             n_batches = 1  
    109.   
    110.         if shuffle: #是否将数据打乱处理  
    111.             data_x_cpy = data_x.copy()  
    112.             inds = np.arange(n_data)  
    113.         else:  
    114.             data_x_cpy = data_x  
    115.   
    116.         errs = []  
    117.   
    118.         # 开始每一轮的训练  
    119.         for e in range(n_epoches):  
    120.             if verbose and not self._use_tqdm:  
    121.                 print('Epoch: {:d}'.format(e))  
    122.   
    123.             epoch_errs = np.zeros((n_batches,))  
    124.             epoch_errs_ptr = 0  
    125.   
    126.             if shuffle:  
    127.                 np.random.shuffle(inds)  
    128.                 data_x_cpy = data_x_cpy[inds]  
    129.   
    130.             r_batches = range(n_batches)  
    131.   
    132.             if verbose and self._use_tqdm:  
    133.                 r_batches = self._tqdm(r_batches, desc='Epoch: {:d}'.format(e), ascii=True, file=sys.stdout)  
    134.   
    135.             # 对每一个batch进行loss的计算,并更新参数  
    136.             for b in r_batches:  
    137.                 batch_x = data_x_cpy[b * batch_size:(b + 1) * batch_size]  
    138.                 self.partial_fit(batch_x) # 对参数进行更新  
    139.                 batch_err = self.get_err(batch_x)  
    140.                 epoch_errs[epoch_errs_ptr] = batch_err  
    141.                 epoch_errs_ptr += 1  
    142.   
    143.             # 对训练过程错误输出处理  
    144.             if verbose:  
    145.                 err_mean = epoch_errs.mean()  
    146.                 if self._use_tqdm:  
    147.                     self._tqdm.write('Train error: {:.4f}'.format(err_mean))  
    148.                     self._tqdm.write('')  
    149.                 else:  
    150.                     print('Train error: {:.4f}'.format(err_mean))  
    151.                     print('')  
    152.                 sys.stdout.flush()  
    153.   
    154.             errs = np.hstack([errs, epoch_errs])  
    155.   
    156.         return errs  
    • 在rbm.py的模块基础上创建一个伯努利-伯努利的RBM深度网络结构,这里同样用一个类来保存结构,并且该类继承于rbm类,根据不同的受限玻尔兹曼机的模型结构进行不一样的参数初始化,创建一个名为bbrbm.py的模块保存。
    1. import tensorflow as tf  
    2. from .rbm import RBM  
    3.   
    4. def sample_bernoulli(probs):  
    5.     return tf.nn.relu(tf.sign(probs - tf.random_uniform(tf.shape(probs))))  
    6.   
    7. class BBRBM(RBM):  
    8.     def __init__(self, *args, **kwargs):  
    9.         RBM.__init__(self, *args, **kwargs)  
    10.   
    11.     def _initialize_vars(self):  
    12.         ''''' 
    13.         对伯努利-伯努利受限玻尔兹曼机变量进行初始化 
    14.         '''  
    15.         hidden_p = tf.nn.sigmoid(tf.matmul(self.x, self.w) + self.hidden_bias)  
    16.         visible_recon_p = tf.nn.sigmoid(tf.matmul(sample_bernoulli(hidden_p), tf.transpose(self.w)) + self.visible_bias)  
    17.         hidden_recon_p = tf.nn.sigmoid(tf.matmul(visible_recon_p, self.w) + self.hidden_bias)  
    18.   
    19.         positive_grad = tf.matmul(tf.transpose(self.x), hidden_p)  
    20.         negative_grad = tf.matmul(tf.transpose(visible_recon_p), hidden_recon_p)  
    21.   
    22.         def f(x_old, x_new):  
    23.             ''''' 
    24.             函数f用来计算参数的变化量 
    25.             '''  
    26.             return self.momentum * x_old +\  
    27.                    self.learning_rate * x_new * (1 - self.momentum) / tf.to_float(tf.shape(x_new)[0])  
    28.   
    29.         # 计算参数的变化量  
    30.         delta_w_new = f(self.delta_w, positive_grad - negative_grad)  
    31.         delta_visible_bias_new = f(self.delta_visible_bias, tf.reduce_mean(self.x - visible_recon_p, 0))  
    32.         delta_hidden_bias_new = f(self.delta_hidden_bias, tf.reduce_mean(hidden_p - hidden_recon_p, 0))  
    33.   
    34.         # 对bbrbm模型参数进行初始化更新  
    35.         update_delta_w = self.delta_w.assign(delta_w_new)  
    36.         update_delta_visible_bias = self.delta_visible_bias.assign(delta_visible_bias_new)  
    37.         update_delta_hidden_bias = self.delta_hidden_bias.assign(delta_hidden_bias_new)  
    38.   
    39.         update_w = self.w.assign(self.w + delta_w_new)  
    40.         update_visible_bias = self.visible_bias.assign(self.visible_bias + delta_visible_bias_new)  
    41.         update_hidden_bias = self.hidden_bias.assign(self.hidden_bias + delta_hidden_bias_new)  
    42.   
    43.         # 将更新的参数添加到模型结构的参数中  
    44.         self.update_deltas = [update_delta_w, update_delta_visible_bias, update_delta_hidden_bias]  
    45.         self.update_weights = [update_w, update_visible_bias, update_hidden_bias]  
    46.   
    47.         self.compute_hidden = tf.nn.sigmoid(tf.matmul(self.x, self.w) + self.hidden_bias)  
    48.         self.compute_visible = tf.nn.sigmoid(tf.matmul(self.compute_hidden, tf.transpose(self.w)) + self.visible_bias)  
    49.         self.compute_visible_from_hidden = tf.nn.sigmoid(tf.matmul(self.y, tf.transpose(self.w)) + self.visible_bias)  

     

    • 创建主模块训练这个网络结构。

    导入相应的包:

    1. import numpy as np  
    2. import matplotlib.pyplot as plt  
    3. from example_tfrbm import bbrbm  
    4. from tensorflow.examples.tutorials.mnist import input_data  

    导入minist手写数据集:

    1. mnist = input_data.read_data_sets('/home/tony/dl_cv/dataset/mnist/', one_hot=True)  # 这里填写下载好的数据集地址
    2. mnist_images = mnist.train.images  

    显示导入的数据:

    1. IMAGE = 1  
    2. def show_digit(x):  
    3.     plt.imshow(x.reshape((28, 28)), cmap=plt.cm.gray)  
    4.     plt.show()  
    5.   
    6. image = mnist_images[IMAGE]  
    7. show_digit(image)  

    开始训练bbrbm模型:

    1. # 初始化模型  
    2. model = bbrbm.BBRBM(n_visible=784, n_hidden=64, learning_rate=0.01, momentum=0.95, use_tqdm=True)  
    3. # 训练模型,返回训练loss  
    4. errs = model.fit(mnist_images, n_epoches=30, batch_size=10)  

    训练过程输出:

    ... ... ... ......................................

    ... ... ... ......................................

     

    查看训练过程loss收敛图像:

    1. # 画出训练的loss图像  
    2. plt.plot(errs)  
    3. plt.show()  

    收敛结果图像:

    生成训练结果图像:

    1. # 根据训练输出的节点,用图像进行输出  
    2. image_rec = model.reconstruct(image.reshape(1,-1))  
    3. show_digit(image_rec)  

    生成结果如图:

    至此,整个模型训练完成,得到的图像与生成的图像相似度还比较满意。

    3.2 深度卷积网络识别mnist手写数字

    在没有使用深度网络结构,在mnist手写数字识别中,svm一直是表现最好的模型,直到2012年AlexNet深度卷积网络的出现,让mnist手写数字识别到了一个更高的准确度。到现在例如GoogLeNet、ResNet等深度网络结构不断地在提高识别度,有些甚至比人眼更精确。

    • AlexNet的实现讲解

    创建一个文件名为AlexNet.py实现该网络结构。

    1. #coding=utf-8  
    2. from __future__ import print_function  
    3. from tensorflow.examples.tutorials.mnist import input_data  
    4. mnist = input_data.read_data_sets('/home/tony/dl_cv/dataset/mnist/', one_hot=True)  
    5. import tensorflow as tf  
    6. # 定义网络超参数  
    7. learning_rate = 0.001  
    8. training_iters = 200000  
    9. batch_size = 64  
    10. display_step = 20  
    11.   
    12. # 定义网络参数  
    13. n_input = 784 # 输入的维度  
    14. n_classes = 10 # 标签的维度  
    15. dropout = 0.8 # Dropout 的概率  
    16.   
    17. # 占位符输入  
    18. x = tf.placeholder(tf.float32, [None, n_input])  
    19. y = tf.placeholder(tf.float32, [None, n_classes])  
    20. keep_prob = tf.placeholder(tf.float32)  
    21.   
    22. # 卷积操作  
    23. def conv2d(name, l_input, w, b):  
    24.     return tf.nn.relu(tf.nn.bias_add(tf.nn.conv2d(l_input, w, strides=[1, 1, 1, 1], padding='SAME'),b), name=name)  
    25.   
    26. # 最大下采样操作  
    27. def max_pool(name, l_input, k):  
    28.     return tf.nn.max_pool(l_input, ksize=[1, k, k, 1], strides=[1, k, k, 1], padding='SAME', name=name)  
    29.   
    30. # 归一化操作  
    31. def norm(name, l_input, lsize=4):  
    32.     return tf.nn.lrn(l_input, lsize, bias=1.0, alpha=0.001 / 9.0, beta=0.75, name=name)  
    33.   
    34. # 定义整个网络   
    35. def alex_net(_X, _weights, _biases, _dropout):  
    36.     # 向量转为矩阵  
    37.     _X = tf.reshape(_X, shape=[-1, 28, 28, 1])  
    38.   
    39.     # 卷积层  
    40.     conv1 = conv2d('conv1', _X, _weights['wc1'], _biases['bc1'])  
    41.     # 下采样层  
    42.     pool1 = max_pool('pool1', conv1, k=2)  
    43.     # 归一化层  
    44.     norm1 = norm('norm1', pool1, lsize=4)  
    45.     # Dropout  
    46.     norm1 = tf.nn.dropout(norm1, _dropout)  
    47.   
    48.     # 卷积  
    49.     conv2 = conv2d('conv2', norm1, _weights['wc2'], _biases['bc2'])  
    50.     # 下采样  
    51.     pool2 = max_pool('pool2', conv2, k=2)  
    52.     # 归一化  
    53.     norm2 = norm('norm2', pool2, lsize=4)  
    54.     # Dropout  
    55.     norm2 = tf.nn.dropout(norm2, _dropout)  
    56.   
    57.     # 卷积  
    58.     conv3 = conv2d('conv3', norm2, _weights['wc3'], _biases['bc3'])  
    59.     # 下采样  
    60.     pool3 = max_pool('pool3', conv3, k=2)  
    61.     # 归一化  
    62.     norm3 = norm('norm3', pool3, lsize=4)  
    63.     # Dropout  
    64.     norm3 = tf.nn.dropout(norm3, _dropout)  
    65.   
    66.     # 全连接层,先把特征图转为向量  
    67.     dense1 = tf.reshape(norm3, [-1, _weights['wd1'].get_shape().as_list()[0]])   
    68.     dense1 = tf.nn.relu(tf.matmul(dense1, _weights['wd1']) + _biases['bd1'], name='fc1')   
    69.     # 全连接层  
    70.     dense2 = tf.nn.relu(tf.matmul(dense1, _weights['wd2']) + _biases['bd2'], name='fc2')   
    71.   
    72.     # 网络输出层  
    73.     out = tf.matmul(dense2, _weights['out']) + _biases['out']  
    74.     return out  
    75.   
    76. # 存储所有的网络参数  
    77. weights = {  
    78.     'wc1': tf.Variable(tf.random_normal([3, 3, 1, 64])),  
    79.     'wc2': tf.Variable(tf.random_normal([3, 3, 64, 128])),  
    80.     'wc3': tf.Variable(tf.random_normal([3, 3, 128, 256])),  
    81.     'wd1': tf.Variable(tf.random_normal([4*4*256, 1024])),  
    82.     'wd2': tf.Variable(tf.random_normal([1024, 1024])),  
    83.     'out': tf.Variable(tf.random_normal([1024, 10]))  
    84. }  
    85. biases = {  
    86.     'bc1': tf.Variable(tf.random_normal([64])),  
    87.     'bc2': tf.Variable(tf.random_normal([128])),  
    88.     'bc3': tf.Variable(tf.random_normal([256])),  
    89.     'bd1': tf.Variable(tf.random_normal([1024])),  
    90.     'bd2': tf.Variable(tf.random_normal([1024])),  
    91.     'out': tf.Variable(tf.random_normal([n_classes]))  
    92. }  
    93.   
    94. # 构建模型  
    95. pred = alex_net(x, weights, biases, keep_prob)  
    96. # 定义损失函数和学习步骤  
    97. cost = tf.reduce_mean(tf.nn.softmax_cross_entropy_with_logits(logits = pred, labels = y))  
    98. optimizer = tf.train.AdamOptimizer(learning_rate=learning_rate).minimize(cost)  
    99. # 测试网络  
    100. correct_pred = tf.equal(tf.argmax(pred,1), tf.argmax(y,1))  
    101. accuracy = tf.reduce_mean(tf.cast(correct_pred, tf.float32))  
    102. # 初始化所有的共享变量  
    103. init = tf.initialize_all_variables()  
    104. # 开启一个训练  
    105. with tf.Session() as sess:  
    106.     sess.run(init)  
    107.     step = 1  
    108.     # Keep training until reach max iterations  
    109.     while step * batch_size < training_iters:  
    110.         batch_xs, batch_ys = mnist.train.next_batch(batch_size)  
    111.         # 获取批数据  
    112.         sess.run(optimizer, feed_dict={x: batch_xs, y: batch_ys, keep_prob: dropout})  
    113.         if step % display_step == 0:  
    114.             # 计算精度  
    115.             acc = sess.run(accuracy, feed_dict={x: batch_xs, y: batch_ys, keep_prob: 1.})  
    116.             # 计算损失值  
    117.             loss = sess.run(cost, feed_dict={x: batch_xs, y: batch_ys, keep_prob: 1.})  
    118.             print ("Iter " + str(step*batch_size) + ", Minibatch Loss= " + "{:.6f}".format(loss) + ", Training Accuracy = " + "{:.5f}".format(acc))  
    119.         step += 1  
    120.     print ("Optimization Finished!")  
    121.     # 计算测试精度  
    122.     print ("Testing Accuracy:", sess.run(accuracy, feed_dict={x: mnist.test.images[:256], y: mnist.test.labels[:256], keep_prob: 1.}))  
    • 实验运行结果

    网络训练过程:

    1. Iter 1280, Minibatch Loss= 86770.125000, Training Accuracy = 0.35938  
    2. Iter 2560, Minibatch Loss= 64896.742188, Training Accuracy = 0.39062  
    3. Iter 3840, Minibatch Loss= 34028.277344, Training Accuracy = 0.50000  
    4. Iter 5120, Minibatch Loss= 30742.812500, Training Accuracy = 0.59375  
    5. .......................................................
    6. .......................................................
    7. .......................................................
    8. Iter 190720, Minibatch Loss= 896.383911, Training Accuracy = 0.96875  
    9. Iter 192000, Minibatch Loss= 2677.220215, Training Accuracy = 0.93750  
    10. Iter 193280, Minibatch Loss= 610.773926, Training Accuracy = 0.96875  
    11. Iter 194560, Minibatch Loss= 1569.147217, Training Accuracy = 0.95312  
    12. Iter 195840, Minibatch Loss= 40.134521, Training Accuracy = 0.98438  
    13. Iter 197120, Minibatch Loss= 2792.126953, Training Accuracy = 0.93750  
    14. Iter 198400, Minibatch Loss= 380.154297, Training Accuracy = 0.95312  
    15. Iter 199680, Minibatch Loss= 1328.015381, Training Accuracy = 0.93750  
    16. Optimization Finished!  
    17. Testing Accuracy: 0.972656 

    从AlexNet训练中我们可以看到整个网络训练时,整体Loss是在不断下降的,学到更多数据的特征信息,到后面整个网络收敛,表现出不错的准确率。测试的结果高达97%以上。

    练习:在ImageNet上下载猫狗等数据集,用InceptionV3、ResNet等训练模型进行识别。

    代码链接:

    展开全文
  • 图像处理(卷积)

    2018-08-24 22:41:48
    图像处理(卷积)作者太棒了,写的很好,推荐阅读 &nbsp; 原文&nbsp; http://blog.sina.com.cn/s/blog_4bdb170b01019atv.html 图像处理-线性滤波-1 基础(相关算子、卷积算子、边缘效应) 这里讨论...

    图像处理(卷积)作者太棒了,写的很好,推荐阅读

     

    图像处理-线性滤波-1 基础(相关算子、卷积算子、边缘效应)

    这里讨论利用输入图像中像素的小邻域来产生输出图像的方法,在信号处理中这种方法称为滤波(filtering)。其中,最常用的是线性滤波:输出像素是输入邻域像素的加权和。

     

    1.相关算子(Correlation Operator)

           定义:image image ,其中h称为相关核(Kernel).

            

      步骤:

            1)滑动核,使其中心位于输入图像g的(i,j)像素上

            2)利用上式求和,得到输出图像的(i,j)像素值

            3)充分上面操纵,直到求出输出图像的所有像素值

     

      例:

    A = [17  24      15            h = [8     6
         23      14  16                         7
             13  20  22                         2]
         10  12  19  21             
         11  18  25     9]

    计算输出图像的(2,4)元素=image

    image

    Matlab 函数:imfilter(A,h)

     

    2.卷积算子(Convolution)

    定义:image image ,其中

       步骤:

            1)将核围绕中心旋转180度

            2)滑动核,使其中心位于输入图像g的(i,j)像素上

            3)利用上式求和,得到输出图像的(i,j)像素值

            4)充分上面操纵,直到求出输出图像的所有像素值

           例:计算输出图像的(2,4)元素=image

           image

    Matlab 函数:Matlab 函数:imfilter(A,h,’conv’)% imfilter默认是相关算子,因此当进行卷积计算时需要传入参数’conv’

    3.边缘效应

    当对图像边缘的进行滤波时,核的一部分会位于图像边缘外面。

    image

    常用的策略包括:

    1)使用常数填充:imfilter默认用0填充,这会造成处理后的图像边缘是黑色的。

    2)复制边缘像素:I3 = imfilter(I,h,’replicate’);

    image

       

    4.常用滤波

    fspecial函数可以生成几种定义好的滤波器的相关算子的核。

    例:unsharp masking 滤波

    1
    2
    3
    4
    5
    I = imread(’moon.tif’);
    h = fspecial(’unsharp’);
    I2 = imfilter(I,h);
    imshow(I), title(’Original Image’)
    figure, imshow(I2), title(’Filtered Image’)
     
     

    图像处理-线性滤波-2 图像微分(1、2阶导数和拉普拉斯算子)

    更复杂些的滤波算子一般是先利用高斯滤波来平滑,然后计算其1阶和2阶微分。由于它们滤除高频和低频,因此称为带通滤波器(band-pass filters)。

    在介绍具体的带通滤波器前,先介绍必备的图像微分知识。

    1 一阶导数

    连续函数,其微分可表达为image ,或image                         (1.1)

    对于离散情况(图像),其导数必须用差分方差来近似,有

                                       image,前向差分 forward differencing                  (1.2)

                                       image ,中心差分 central differencing                     (1.3)

    1)前向差分的Matlab实现

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    function dimg = mipforwarddiff(img,direction)
    % MIPFORWARDDIFF     Finite difference calculations 
    %
      DIMG = MIPFORWARDDIFF(IMG,DIRECTION)
    %
     Calculates the forward-difference for a given direction
     IMG       : input image
     DIRECTION : ’dx’ or 'dy'
     DIMG      : resultant image
    %
      See also MIPCENTRALDIFF MIPBACKWARDDIFF MIPSECONDDERIV
      MIPSECONDPARTIALDERIV
      
      Omer Demirkaya, Musa Asyali, Prasana Shaoo, ... 9/1/06
      Medical Image Processing Toolbox
      
    imgPad = padarray(img,[1 1],’symmetric’,'both');%将原图像的边界扩展
    [row,col] = size(imgPad);
    dimg = zeros(row,col);
    switch (direction)   
    case 'dx',
       dimg(:,1:col-1) = imgPad(:,2:col)-imgPad(:,1:col-1);%x方向差分计算,
    case 'dy',
       dimg(1:row-1,:) = imgPad(2:row,:)-imgPad(1:row-1,:); 
    otherwise, disp(’Direction is unknown’);
    end;
    dimg = dimg(2:end-1,2:end-1);

    2)中心差分的Matlab实现

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    function dimg = mipcentraldiff(img,direction)
    % MIPCENTRALDIFF     Finite difference calculations 
    %
      DIMG = MIPCENTRALDIFF(IMG,DIRECTION)
    %
     Calculates the central-difference for a given direction
     IMG       : input image
     DIRECTION : ’dx’ or 'dy'
     DIMG      : resultant image
    %
      See also MIPFORWARDDIFF MIPBACKWARDDIFF MIPSECONDDERIV
      MIPSECONDPARTIALDERIV
      
      Omer Demirkaya, Musa Asyali, Prasana Shaoo, ... 9/1/06
      Medical Image Processing Toolbox
      
    img = padarray(img,[1 1],’symmetric’,'both');
    [row,col] = size(img);
    dimg = zeros(row,col);
    switch (direction)
        case 'dx',
            dimg(:,2:col-1) = (img(:,3:col)-img(:,1:col-2))/2;
        case 'dy',
            dimg(2:row-1,:) = (img(3:row,:)-img(1:row-2,:))/2;
        otherwise,
            disp(’Direction is unknown’);
    end
    dimg = dimg(2:end-1,2:end-1);
    1   

    实例:技术图像x方向导数

    1
    2
    I = imread(’coins.png’); figure; imshow(I);
    Id = mipforwarddiff(I,’dx’); figure, imshow(Id);

          image image

        原图像                                                   x方向1阶导数

     

    2 图像梯度(Image Gradient)

    图像I的梯度定义为image  ,其幅值为image 。出于计算性能考虑,幅值也可用image 来近似。

    Matlab函数

    1)gradient:梯度计算

    2)quiver:以箭头形状绘制梯度。注意放大下面最右侧图可看到箭头,由于这里计算横竖两个方向的梯度,因此箭头方向都是水平或垂直的。

    实例:仍采用上面的原始图像

    1
    2
    3
    4
    5
    I = double(imread('coins.png'));
    [dx,dy]=gradient(I);
    magnitudeI=sqrt(dx.^2+dy.^2);
    figure;imagesc(magnitudeI);colormap(gray);%梯度幅值
    hold on;quiver(dx,dy);%叠加梯度方向

            image image

                             梯度幅值                                   梯度幅值+梯度方向

     

    3 二阶导数

    对于一维函数,其二阶导数image ,即image 。它的差分函数为

                                     image                  (3.1)

     

    3.1 普拉斯算子(laplacian operator)

    3.1.2 概念

    拉普拉斯算子是n维欧式空间的一个二阶微分算子。它定义为两个梯度向量算子的内积

                              image       (3.2)

    其在二维空间上的公式为:    image                (3.3)

     

    对于1维离散情况,其二阶导数变为二阶差分

    1)首先,其一阶差分为image

    2)因此,二阶差分为

              image

    3)因此,1维拉普拉斯运算可以通过1维卷积核image 实现

     

    对于2维离散情况(图像),拉普拉斯算子是2个维上二阶差分的和(见式3.3),其公式为:

    image   (3.4)

    上式对应的卷积核为

                           image

    常用的拉普拉斯核有:

                          image

    3.1.2 应用

    拉普拉斯算子会突出像素值快速变化的区域,因此常用于边缘检测。

     

     

    Matlab里有两个函数

    1)del2

    计算公式:image image  

    2)fspecial:图像处理中一般利用Matlab函数fspecial

    h = fspecial(‘laplacian’, alpha) returns a 3-by-3 filter approximating the shape of the two-dimensional Laplacian operator.
    The parameter alpha controls the shape of the Laplacian and must be in the range 0.0 to 1.0. The default value for alpha is 0.2.

     

    3.1.3 资源

    http://fourier.eng.hmc.edu/e161/lectures/gradient/node8.html (非常清晰的Laplacian Operator介绍,本文的主要参考)

    http://homepages.inf.ed.ac.uk/rbf/HIPR2/log.htm

     

     
     
     
     

    sift算法

     

    尺度不变特征转换(Scale-invariant feature transform 或 SIFT)是一种电脑视觉的算法用来侦测与描述影像中的局部性特征,它在空间尺度中寻找极值点,并提取出其位置、尺度、旋转不变量,此算法由 David Lowe 在1999年所发表,2004年完善总结。

    Sift算法就是用不同尺度(标准差)的高斯函数对图像进行平滑,然后比较平滑后图像的差别,
    差别大的像素就是特征明显的点。

    sift可以同时处理亮度,平移,旋转,尺度的变化,利用特征点来提取特征描述符,最后在特征描述符之间寻找匹配


    五个步骤

    1构建尺度空间,检测极值点,获得尺度不变性

    2特征点过滤并进行经确定位,剔除不稳定的特征点

    3 在特征点处提取特征描述符,为特征点分配方向直

    4声称特征描述子,利用特征描述符寻找匹配点

    5计算变换参数

    当2幅图像的sift特征向量生成以后,下一步就可以采用关键点特征向量的欧式距离来作为2幅图像中关键点的相似性判定量度


    尺度空间:

    尺度就是受delta这个参数控制的表示

    而不同的L(x,y,delta)就构成了尺度空间,实际上具体计算的时候即使连续的高斯函数,都要被离散为矩阵来和数字图像进行卷积操作

    L(x,y,delta)=G(x,y,e)*i(x,y)

    尺度空间=原始图像(卷积)一个可变尺度的2维高斯函数G(x,y,e)


    G(x,y,e) = [1/2*pi*e^2] * exp[ -(x^2 + y^2)/2e^2] 


    为了更有效的在尺度空间检测到稳定的关键点,提出了高斯差分尺度空间,利用不同尺度的高斯差分核与原始图像i(x,y)卷积生成

    D(x,y,e)=(G(x,y,ke)-G(x,y,e))*i(x,y)

    =L(x,y,ke)-L(x,y,e)

    (为避免遍历每个像素点)


    高斯卷积:

    在组建一组尺度空间后,再组建下一组尺度空间,对上一组尺度空间的最后一幅图像进行二分之一采样,得到下一组尺度空间的第一幅图像,然后进行像建立第一组尺度空间那样的操作,得到第二组尺度空间,公式定义为
             L(x,y,e) = G(x,y,e)*I(x,y)

        图像金字塔的构建:图像金字塔共O组,每组有S层,下一组的图像由上一组图像降采样得到、

    高斯差分

        在尺度空间建立完毕后,为了能够找到稳定的关键点,采用高斯差分的方法来检测那些在局部位置的极值点,即采用俩个相邻的尺度中的图像相减,即公式定义为:
            D(x,y,e) = ((G(x,y,ke) - G(x,y,e)) * I(x,y) 
                     = L(x,y,ke) - L(x,y,e)
     咱们再来具体阐述下构造D(x,y,e)的详细步骤:
        1、首先采用不同尺度因子的高斯核对图像进行卷积以得到图像的不同尺度空间,将这一组图像作为金子塔图像的第一层。
        2、接着对第一层图像中的2倍尺度图像(相对于该层第一幅图像的2倍尺度)以2倍像素距离进行下采样来得到金子塔图像的第二层中的第一幅图像,对该图像采用不同尺度因子的高斯核进行卷积,以获得金字塔图像中第二层的一组图像。
        3、再以金字塔图像中第二层中的2倍尺度图像(相对于该层第一幅图像的2倍尺度)以2倍像素距离进行下采样来得到金字塔图像的第三层中的第一幅图像,对该图像采用不同尺度因子的高斯核进行卷积,以获得金字塔图像中第三层的一组图像。这样依次类推,从而获得了金字塔图像的每一层中的一组图像,
     4、对上图得到的每一层相邻的高斯图像相减,就得到了高斯差分图像,如下述第一幅图所示。下述第二幅图中的右列显示了将每组中相邻图像相减所生成的高斯差分图像的结果,限于篇幅,图中只给出了第一层和第二层高斯差分图像的计算
    sift算法
     

     

    图像处理之卷积概念

     

    我们来看一下一维卷积的概念.
    连续空间的卷积定义是 f(x)与g(x)的卷积是 f(t-x)g(x) 在t从负无穷到正无穷的积分值.t-x要在f(x)定义域内,所以看上去很大的积分实际上还是在一定范围的.
    实际的过程就是f(x) 先做一个Y轴的反转,然后再沿X轴平移t就是f(t-x),然后再把g(x)拿来,两者乘积的值再积分.想象一下如果g(x)或者f(x)是个单位的阶越函数. 那么就是f(t-x)与g(x)相交部分的面积.这就是卷积了.
    把积分符号换成求和就是离散空间的卷积定义了.

     

    么在图像中卷积卷积地是什么意思呢,就是图像f(x),模板g(x),然后将模版g(x)在模版中移动,每到一个位置,就把f(x)与g(x)的定义域相交的元素进行乘积并且求和,得出新的图像一点,就是被卷积后的图像. 模版又称为卷积核.卷积核做一个矩阵的形状.


    卷积定义上是线性系统分析经常用到的.线性系统就是一个系统的输入和输出的关系是线性关系.就是说整个系统可以分解成N多的无关独立变化,整个系统就是这些变化的累加.
    如 x1->y1, x2->y2; 那么A*x1 + B*x2 -> A*y1 + B*y2 这就是线性系统. 表示一个线性系统可以用积分的形式 如 Y = Sf(t,x)g(x)dt S表示积分符号,就是f(t,x)表示的是A B之类的线性系数.
    看上去很像卷积呀,,对如果f(t,x) = F(t-x) 不就是了吗.从f(t,x)变成F(t-x)实际上是说明f(t,x)是个线性移不变,就是说 变量的差不变化的时候,那么函数的值不变化. 实际上说明一个事情就是说线性移不变系统的输出可以通过输入和表示系统线性特征的函数卷积得到.

     

    http://dept.wyu.edu.cn/dip/DIPPPT2005/����������ϵͳ.ppt


     
     
     
     
     
    谈起卷积分当然要先说说冲击函数—-这个倒立的小蝌蚪,卷积其实就是为它诞生的。”冲击函数”是狄拉克为了解决一些瞬间作用的物理现象而提出的符号。
    古人曰:”说一堆大道理不如举一个好例子”,冲量这一物理现象很能说明”冲击函数”。在t时间内对一物体作用F的力,我们可以让作用时间t很小,作用力F很大,但让Ft的乘积不变,即冲量不变。于是在用t做横坐标、F做纵坐标的坐标系中,就如同一个面积不变的长方形,底边被挤的窄窄的,高度被挤的高高的,在数学中它可以被挤到无限高,但即使它无限瘦、无限高、但它仍然保持面积不变(它没有被挤没!),为了证实它的存在,可以对它进行积分,积分就是求面积嘛!于是”卷积” 这个数学怪物就这样诞生了。说它是数学怪物是因为追求完美的数学家始终在头脑中转不过来弯,一个能瘦到无限小的家伙,竟能在积分中占有一席之地,必须将这个细高挑清除数学界。但物理学家、工程师们确非常喜欢它,因为它解决了很多当时数学家解决不了的实际问题。最终追求完美的数学家终于想通了,数学是来源于实际的,并最终服务于实际才是真。于是,他们为它量身定做了一套运作规律。于是,妈呀!你我都感觉眩晕的卷积分产生了。
    例子:
    有一个七品县令,喜欢用打板子来惩戒那些市井无赖,而且有个惯例:如果没犯大罪,只打一板,释放回家,以示爱民如子。
    有一个无赖,想出人头地却没啥指望,心想:既然扬不了善名,出恶名也成啊。怎么出恶名?炒作呗!怎么炒作?找名人呀!他自然想到了他的行政长官——县令。
    无赖于是光天化日之下,站在县衙门前撒了一泡尿,后果是可想而知地,自然被请进大堂挨了一板子,然后昂首挺胸回家,躺了一天,嘿!身上啥事也没有!第二天如法炮制,全然不顾行政长管的仁慈和衙门的体面,第三天、第四天……每天去县衙门领一个板子回来,还喜气洋洋地,坚持一个月之久!这无赖的名气已经和衙门口的臭气一样,传遍八方了!
    县令大人噤着鼻子,呆呆地盯着案子上的惊堂木,拧着眉头思考一个问题:这三十个大板子怎么不好使捏?……想当初,本老爷金榜题名时,数学可是得了满分,今天好歹要解决这个问题:
    ——人(系统!)挨板子(脉冲!)以后,会有什么表现(输出!)?
    ——费话,疼呗!
    ——我问的是:会有什么表现?
    ——看疼到啥程度。像这无赖的体格,每天挨一个板子啥事都不会有,连哼一下都不可能,你也看到他那得意洋洋的嘴脸了(输出0);如果一次连揍他十个板子,他可能会皱皱眉头,咬咬牙,硬挺着不哼
    (输出1);揍到二十个板子,他会疼得脸部扭曲,象猪似地哼哼(输出3);揍到三十个板子,他可能会象驴似地嚎叫,一把鼻涕一把泪地求你饶他一命(输出5);揍到四十个板子,他会大小便失禁,勉
    强哼出声来(输出1);揍到五十个板子,他连哼一下都不可能(输出0)——死啦!
    县令铺开坐标纸,以打板子的个数作为X轴,以哼哼的程度(输出)为Y轴,绘制了一条曲线:
    ——呜呼呀!这曲线象一座高山,弄不懂弄不懂。为啥那个无赖连挨了三十天大板却不喊绕命呀?
    —— 呵呵,你打一次的时间间隔(Δτ=24小时)太长了,所以那个无赖承受的痛苦程度一天一利索,没有叠加,始终是一个常数;如果缩短打板子的时间间隔(建议 Δτ=0.5秒),那他的痛苦程度可就迅速叠加了;等到这无赖挨三十个大板(t=30)时,痛苦程度达到了他能喊叫的极限,会收到最好的惩戒效果,再多打就显示不出您的仁慈了。
    ——还是不太明白,时间间隔小,为什么痛苦程度会叠加呢?
    ——这与人(线性时不变系统)对板子(脉冲、输入、激励)的响应有关。什么是响应?人挨一个板子后,疼痛的感觉会在一天(假设的,因人而异)内慢慢消失(衰减),而不可能突然消失。这样一来,只要打板子的时间间隔很小,每一个板子引起的疼痛都来不及完全衰减,都会对最终的痛苦程度有不同的贡献:
    t个大板子造成的痛苦程度=Σ(第τ个大板子引起的痛苦*衰减系数)
    [衰减系数是(t-τ)的函数,仔细品味]
    数学表达为:y(t)=∫T(τ)H(t-τ)
    ——拿人的痛苦来说卷积的事,太残忍了。除了人以外,其他事物也符合这条规律吗?
    ——呵呵,县令大人毕竟仁慈。其实除人之外,很多事情也遵循此道。好好想一想,铁丝为什么弯曲一次不折,快速弯曲多次却会轻易折掉呢?
    ——恩,一时还弄不清,容本官慢慢想来——但有一点是明确地——来人啊,将撒尿的那个无赖抓来,狠打40大板!
    卷积及拉普拉斯变换的通俗解释–对于我这类没学过信号系统的人来说太需要了
    卷积(convolution, 另一个通用名称是德文的Faltung)的名称由来,是在于当初定义它时,定义成 integ(f1(v)*f2(t-v))dv,积分区间在0到t之间。举个简单的例子,大家可以看到,为什么叫”卷积”了。比方说在(0,100)间积分,用简单的辛普生积分公式,积分区间分成100等分,那么看到的是f1(0)和f2(100)相乘,f1(1)和f2(99)相乘,f1(2)和f2 (98)相乘,……… 等等等等,就象是在坐标轴上回卷一样。所以人们就叫它”回卷积分”,或者”卷积”了。
    为了理解”卷积”的物理意义,不妨将那个问题”相当于它的时域的信号与系统的单位脉冲响应的卷积”略作变化。这个变化纯粹是为了方便表达和理解,不影响任何其它方面。将这个问题表述成这样一个问题:一个信号通过一个系统,系统的响应是频率响应或波谱响应,且看如何理解卷积的物理意义。
    假设信号函数为f, 响应函数为g。f不仅是时间的函数(信号时有时无),还是频率的函数(就算在某一固定时刻,还有的地方大有的地方小);g也是时间的函数(有时候有反应,有时候没反应),同时也是频率的函数(不同的波长其响应程度不一样)。那我们要看某一时刻 t 的响应信号,该怎么办呢?
    这就需要卷积了。
    要看某一时刻 t 的响应信号,自然是看下面两点:
    1。你信号来的时候正赶上人家”系统”的响应时间段吗?
    2。就算赶上系统响应时间段,响应有多少?
    响 应不响应主要是看 f 和 g 两个函数有没有交叠;响应强度的大小不仅取决于所给的信号的强弱,还取决于在某频率处对单位强度响应率。响应强度是信号强弱和对单位强度信号响应率的乘积。”交叠”体现在f(t1)和g(t-t1)上,g之所以是”(t-t1)”就是看两个函数错开多少。
    由于 f 和 g 两个函数都有一定的带宽分布(假若不用开头提到的”表述变化”就是都有一定的时间带宽分布),这个信号响应是在一定”范围”内广泛响应的。算总的响应信号,当然要把所有可能的响应加起来,实际上就是对所有可能t1积分了。积分范围虽然一般在负无穷到正无穷之间;但在没有信号或者没有响应的地方,积也是白积,结果是0,所以往往积分范围可以缩减。
    这就是卷积及其物理意义啊。并成一句话来说,就是看一个时有时无(当然作为特例也可以永恒存在)的信号,跟一个响应函数在某一时刻有多大交叠。
    *********拉普拉斯*********
    拉普拉斯(1729-1827) 是法国数学家,天文学家,物理学家。他提出拉普拉斯变换(Laplace Transform) 的目的是想要解决他当时研究的牛顿引力场和太阳系的问题中涉及的积分微分方程。
    拉普拉斯变换其实是一个数学上的简便算法;想要了解其”物理”意义 — 如果有的话 — 请看我举这样一个例子:
    问题:请计算十万乘以一千万。
    对于没学过指数的人,就只会直接相乘;对于学过指数的人,知道不过是把乘数和被乘数表达成指数形式后,两个指数相加就行了;如果要问究竟是多少,把指数转回来就是。
    “拉 普拉斯变换” 就相当于上述例子中把数转换成”指数” 的过程;进行了拉普拉斯变换之后,复杂的微分方程(对应于上例中”复杂”的乘法) 就变成了简单的代数方程,就象上例中”复杂”的乘法变成了简单的加减法。再把简单的代数方程的解反变换回去(就象把指数重新转换会一般的数一样),就解决了原来那个复杂的微分方程。
    所以要说拉普拉斯变换真有” 物理意义”的话,其物理意义就相当于人们把一般的有理数用指数形式表达一样。
    另外说两句题外话:
    1 。拉普拉斯变换之所以现在在电路中广泛应有,根本原因是电路中也广泛涉及了微分方程。
    2。拉普拉斯变换与Z变换当然有紧密联系;其本质区别在于拉氏变换处理的是时间上连续的问题,Z变换处理的是时间上分立的问题。
    Signals, Linear Systems, and Convolution
    Download from here
     
    我们都知道卷积公式,但是它有什么物理意义呢?平时我们用卷积做过很多事情,信号处理时,输出函数是输入函数和系统函数的卷积;在图像处理时,两组幅分辨率不同的图卷积之后得到的互相平滑的图像可以方便处理。卷积甚至可以用在考试作弊中,为了让照片同时像两个人,只要把两人的图像卷积处理即可,这就是一种平滑的过程,可是我们怎么才能真正把公式和实际建立起一种联系呢?生活中就有实例:
         比如说你的老板命令你干活,你却到楼下打台球去了,后来被老板发现,他非常气愤,扇了你一巴掌(注意,这就是输入信号,脉冲),于是你的脸上会渐渐地(贱贱地)鼓起来一个包,你的脸就是一个系统,而鼓起来的包就是你的脸对巴掌的响应。
          好,这样就和信号系统建立起来意义对应的联系。下面还需要一些假设来保证论证的严谨:假定你的脸是线性时不变系统,也就是说,无论什么时候老板打你一巴掌,打在你脸的同一位置(这似乎要求你的脸足够光滑,如果你说你长了很多青春痘,甚至整个脸皮处处连续处处不可导,那难度太大了,我就无话可说了),你的脸上总是会在相同的时间间隔内鼓起来一个相同高度的包来,并且假定以鼓起来的包的大小作为系统输出。好了,那么,下面可以进入核心内容——卷积了!
          如果你每天都到楼下去打台球,那么老板每天都要扇你一巴掌,不过当老板打你一巴掌后,你5分钟就消肿了,所以时间长了,你甚至就适应这种生活了……如果有一天,老板忍无可忍,以0.5秒的间隔开始不间断的扇你的过程,这样问题就来了:第一次扇你鼓起来的包还没消肿,第二个巴掌就来了,你脸上的包就可能鼓起来两倍高,老板不断扇你,脉冲不断作用在你脸上,效果不断叠加了,这样这些效果就可以求和了,结果就是你脸上的包的高度岁时间变化的一个函数了(注意理解)!
          如果老板再狠一点,频率越来越高,以至于你都辨别不清时间间隔了,那么,求和就变成积分了。可以这样理解,在这个过程中的某一固定的时刻,你的脸上的包的鼓起程度和什么有关呢?和之前每次打你都有关!但是各次的贡献是不一样的,越早打的巴掌,贡献越小,这就是说,某一时刻的输出是之前很多次输入乘以各自的衰减系数之后的叠加而形成某一点的输出,然后再把不同时刻的输出点放在一起,形成一个函数,这就是卷积。卷积之后的函数就是你脸上的包的大小随时间变化的函数。本来你的包几分钟就可以消肿,可是如果连续打,几个小时也消不了肿了,这难道不是一种平滑过程么?反映到公式上,f(a)就是第a个巴掌,g(x-a)就是第a个巴掌在x时刻的作用程度,乘起来再叠加就ok了,这就是卷积!
         最后提醒各位,请勿亲身尝试……

    卷积的物理意义?
    在信号与系统中,两个函数所要表达的物理含义是什么?例如,一个系统,其单位冲激响应为h(t),当输入信号为f(t)时,该系统的输出为y(t)。为什么y(t)是f(t)和h(t)的卷积?(从数学推导我明白,但其物理意义不明白。)y(t)是f(t)和h(t)的卷积表达了一个什么意思?

    卷积(convolution, 另一个通用名称是德文的Faltung)的名称由来,是在于当初定义它时,定义成 integ(f1(v)*f2(t-v))dv,积分区间在0到t之间。举个简单的例子,大家可以看到,为什么叫“卷积”了。比方说在(0,100)间积分,用简单的辛普生积分公式,积分区间分成100等分,那么看到的是f1(0)和f2(100)相乘,f1(1)和f2(99)相乘,f1(2)和f2(98)相乘,……… 等等等等,就象是在坐标轴上回卷一样。所以人们就叫它“回卷积分”,或者“卷积”了。
    为了理解“卷积”的物理意义,不妨将那个问题“相当于它的时域的信号与系统的单位脉冲响应的卷积”略作变化。这个变化纯粹是为了方便表达和理解,不影响任何其它方面。将这个问题表述成这样一个问题:一个信号通过一个系统,系统的响应是频率响应或波谱响应,且看如何理解卷积的物理意义。
    假设信号函数为f, 响应函数为g。f不仅是时间的函数(信号时有时无),还是频率的函数(就算在某一固定时刻,还有的地方大有的地方小);g也是时间的函数(有时候有反应,有时候没反应),同时也是频率的函数(不同的波长其响应程度不一样)。那我们要看某一时刻 t 的响应信号,该怎么办呢?
    这就需要卷积了。
    其实卷积积分应用广泛用在信号里面,一个是频域一个是时域
     

    卷积是个啥?我忽然很想从本质上理解它。于是我从抽屉里翻出自己珍藏了许多年,每每下决心阅读却永远都读不完的《应用傅立叶变换》。
     
    3.1 一维卷积的定义
     
    函数f(x)与函数h(x)的卷积,由函参量的无穷积分

      定义。这里参量x和积分变量α皆为实数;函数f和h可实可复。
     
    定义虽然找到了,但我还是一头雾水。卷积是个无穷积分吗?那它是干啥用的?再往后翻:几何说明、运算举例、基本性质,一堆的公式,就是没有说它是干啥用的。我于是坐在那呆想,忽然第二个困扰我的问题冒了出来:傅立叶变换是个啥?接着就是第三个、第四个、……、第N个问题。
     
    傅立叶变换是个啥?听说能将时域上的东东变到频域上分析?哎?是变到频域上还是空间域上来着?到底啥是时域,频域,空间域?
     
    上网查傅立叶变换的物理意义,没发现明确答案,倒发现了许多和我一样晕着问问题的人。结果又多出了许多名词,能量?功率谱?图像灰度域?……没办法又去翻那本教材。
     
    1.1 一维傅立叶变换的定义与傅立叶积分定理
     
    设f(x)是实变量x的函数,该函数可实可复,称积分

    为函数f(x)的傅立叶变换。
     
    吐血,啥是无穷积分来着?积分是啥来着?还能记起三角函数和差化积、积化和差公式吗?我忽然有种想把高中课本寻来重温的冲动。
     
    卷积主要是为了将信号运算从时域转换为频域。
    信号的时域的卷积等于频域的乘积。
    利用这个性质以及特殊的δ函数可以通过抽样构造简单的调制电路
     
     
    我比较赞同卷积的相关性的作用  在通信系统中的接收机部分MF匹配滤波器等就是本质上的相关
    匹配滤波器最简单的形式就是原信号反转移位相乘积分得到的近似=相关
    相关性越好得到的信号越强   这个我们有一次大作业做的  做地做到呕吐  呵呵
    还有解调中一些东西本质就是相关
     

    卷积公式  解释  卷积公式是用来求随机变量和的密度函数(pdf)的计算公式。  定义式:  z(t)=x(t)*y(t)= ∫x(m)y(t-m)dm.   已知x,y的pdf,x(t),y(t).现在要求z=x+y的pdf. 我们作变量替显,令  z=x+y,m=x. 雅可比行列式=1.那么,z,m联合密度就是f(z,m)=x(m)y(z-m)*1. 这样,就可以很容易求Z的在(z,m)中边缘分布  即fZ(z)=∫x(m)y(z-m)dm….. 由于这个公式和x(t),y(t)存在一一对应的关系。为了方便,所以记 ∫x(m)y(z-m)dm=x(t)*y(t)   长度为m的向量序列u和长度为n的向量序列v,卷积w的向量序列长度为(m+n-1),   u(n)与v(n)的卷积w(n)定义为: w(n)=u(n)@v(n)=sum(v(m)*u(n-m)),m from 负无穷到正无穷;   当m=n时w(1) = u(1)*v(1)   w(2) = u(1)*v(2)+u(2)*v(1)   w(3) = u(1)*v(3)+u(2)*v(2)+u(3)*v(1)   …   w(n) = u(1)*v(n)+u(2)*v(n-1)+ … +u(n)*v(1)   …   w(2*n-1) = u(n)*v(n)   当m≠n时,应以0补齐阶次低的向量的高位后进行计算  这是数学中常用的一个公式,在概率论中,是个重点也是一个难点。

      卷积公式是用来求随机变量和的密度函数(pdf)的计算公式。
      定义式:
      z(t)=x(t)*y(t)= ∫x(m)y(t-m)dm.
      已知x,y的pdf,x(t),y(t).现在要求z=x+y的pdf. 我们作变量替显,令
      z=x+y,m=x. 雅可比行列式=1.那么,t,m联合密度就是f(z,m)=x(m)y(z-m)*1. 这样,就可以很容易求Z的在(z,m)中边缘分布
      即fZ(z)=∫x(m)y(z-m)dm….. 由于这个公式和x(t),y(t)存在一一对应的关系。为了方便,所以记 ∫x(m)y(z-m)dm=x(t)*y(t)
     
    卷积是一种线性运算,图像处理中常见的mask运算都是卷积,广泛应用于图像滤波。castlman的书对卷积讲得很详细。
    高斯变换就是用高斯函数对图像进行卷积。高斯算子可以直接从离散高斯函数得到:
    for(i=0; i<N; i++)
    {
    for(j=0; j<N; j++)
    {
    g[i*N+j]=exp(-((i-(N-1)/2)^2+(j-(N-1)/2)^2))/(2*delta^2));
    sum += g[i*N+j];
    }
    }
    再除以 sum 得到归一化算子
    N是滤波器的大小,delta自选
    首先,再提到卷积之前,必须提到卷积出现的背景。卷积是在信号与线性系统的基础上或背景中出现的,脱离这个背景单独谈卷积是没有任何意义的,除了那个所谓褶反公式上的数学意义和积分(或求和,离散情况下)。
    信号与线性系统,讨论的就是信号经过一个线性系统以后发生的变化(就是输入输出和所经过的所谓系统,这三者之间的数学关系)。所谓线性系统的含义,就是,这个所谓的系统,带来的输出信号与输入信号的数学关系式之间是线性的运算关系。
    因此,实际上,都是要根据我们需要待处理的信号形式,来设计所谓的系统传递函数,那么这个系统的传递函数和输入信号,在数学上的形式就是所谓的卷积关系。
    卷积关系最重要的一种情况,就是在信号与线性系统或数字信号处理中的卷积定理。利用该定理,可以将时间域或空间域中的卷积运算等价为频率域的相乘运算,从而利用FFT等快速算法,实现有效的计算,节省运算代价。


    展开全文
  • 热身: 《机器学习工程师》微专业 体验课(第三章就好) ...深度学习理论 斯坦福大学 吴恩达”机器学习”课程, 全部学习,但并非每个知识点都要很透彻知道。不要卡在某个知识点不动,不懂的话就百度。再不懂也要看...

    热身:

    备注:这一部分粗略看就好,不要拘泥细节。大概了解概念就好,有个感性认识。

    正式入门:
    深度学习理论

    • 斯坦福大学 吴恩达”机器学习”课程,全部学习,但并非每个知识点都要很透彻知道。不要卡在某个知识点不动,不懂的话就百度。再不懂也要看下去。全部学习完。
    • 莫凡 有趣的机器学习 全部看完。目的是比较全面了解机器学习,深度学习的内容。
    • 莫凡 TensorFlow 主要学一些用TensorFlow写的机器学习小例程
    • 深度学习基础课程,了解深度学习基础内容
    • 吴恩达 深度学习工程师,全部看完,全面深入了解卷积神经网络(对于反向传播部分,不用自己实际写代码,原理大概懂就好)。主要是看1到4章,这是关于图像的。第五章是关于语音的。

    备注:这一部分的重点是“1”和“5”,也就是吴恩达的两个视频。其他是作为辅助的。“1”要学的是机器学习这个大范围。“5”学的是卷积神经网络这个小范围。

    深度学习图像处理:

    备注:主要是“2”,重要,看到26课时就差不多了。

    编程语言

    找实习或者找工作~
    其他资料:
    - 台湾大学林轩田《机器学习基石》与《机器学习技巧》,重数学理论推导。
    - 台湾大学李宏毅视频教程,口语话,形象生动。网址

    致谢
    谢谢本文所引用到的视频/文本等资料的老师,谢谢给我支持的各位同学。希望对大家有所帮助。

    展开全文
  • 多标签图像分类(Multi-label Image Classification)任务中图片的标签不止一个,因此评价不能用普通单标签图像分类的标准,即mean accuracy,该任务采用的是和信息检索中类似的方法—mAP(mean Average Precision)...
  • https://zhuanlan.zhihu.com/p/32177354一方面为做资料整理用,方便后期回顾,另一方面转需--------------------------------------------------第一个重境界: 图像识别如果你开始了解深度学习图像处理,...
  • 利用深度学习技术,分析图像与视频,并且将之应用在诸如自动驾驶,无人机等等领域已经成为最新研究方向。在最新的一篇名为“A Neural Algorithm of Artistic Style”[1508.06576] A Neural Algorithm of Artistic ...
  • 个人总结知识点 ...3,问:深度学习与逻辑回归的区别 在计算y=wx时,将逻辑回归的函数变成几十个函数的嵌套,然后利用链式求导法则对嵌套的几十个函数进行反向求导,得出损失函数 4,问:过拟合的原...
  • 深度学习算法现在是图像处理软件库的组成部分。在他们的帮助下,可以学习和训练复杂的功能;但他们的应用也不是万能的。 “机器学习”和“深度学习”有什么区别? 在机器视觉和深度学习中,人类视觉的力量和对...
  • 某博客专家根据论文写的深度学习,机器学习方面的学习笔记: http://blog.csdn.net/hjimce/article/details/50573444 网上某神写的R-CNN详细笔记: http://blog.csdn.net/column/details/ym-alanyannick.html ...
  • 2006年,加拿大多伦多大学教授、机器学习领域的泰斗Geoffrey Hinton和他的学生在《科学》上发表了一篇文章,开启了深度学习在学术界和工业界的浪潮。...那么,深度学习算法在遥感图像处理领域是否也能发...
  • 深度学习技术应用于图像处理,推荐阅读《深度学习技术图像处理入门》,基于理论讲解,由浅入深地引出若干个经典案例,讲解当前深度神经网络在图像处理领域的应用。提供了基于云GPU容器(Docker)的完整在线开发...
  • 深度学习图像处理领域中的应用综述[J].高教学刊,2018(09):72-74 1.特征表达/提取方法->特征学习 图像特征是指图像的原始特性或属性,可以分为视觉特征或统计特征。视觉特征主要是人的视觉直觉感受的自然特征...
  • 顺序不是排名OpenCV 图像处理 计算机视觉1、浅墨_毛星云 南京航空航天大学 硕士毕业 博客专栏:[OpenCV]入门教程 很适合没有基础的同学入门 http://blog.csdn.net/column/details/opencv-tutorial.html2、赵春江 ...
  • 本文参考了三篇深度学习在医学图像处理中的三篇综述性的文章,旨在对于深度学习和医学图像相结合的现有情况做一个小总结,并探讨一下未来的一些发展趋势和自身的一些思考 医学影像深度学习工具 深度学习模型 ...
  • 如果你开始了解深度学习图像处理, 你接触的第一个任务一定是图像识别 : 比如把你的爱猫输入到一个普通的CNN网络里, 看看它是喵咪还是狗狗。   一个最普通的CNN, 比如像这样几层的CNN鼻祖Lenet, 如果...
  • 相信,阅读以下这些经典的图像处理书籍能够助你一臂之力。赶紧紧随大圣众包威客平台的脚步吧! 《数字图像处理基础》  随着台式计算机的处理能力日益增强,各种图像拍摄的设备(例如平板电脑、...
  • 深度学习图像处理领域的发展过程; 解析经典的卷积神经网络; 垃圾分类实战。本课程将使用Pytorch深度学习框架进行实战,并在ubuntu系统上进行演示,包括:不同标注文件下的数据集读取、...
  • 图像处理的入门主要在毛星云所写的《OpenCV3编程入门》的帮助下入门的,图书的内容博客上都有,为了方便的同学可以购买图书,我也买了。博客链接在这里https://blog.csdn.net/linqianbi/article/details/79166422 ...
  • 深度学习和大数据学习需要依赖海量数据,遥感卫星也是深度学习的一个关键场景。后续我会支持更新我们在这个领域的进展,分享今天收集和整理的数据和项目,期待中国航天行业也能有更好的开放性。地理空间和环境数据集...
1 2 3 4 5 ... 20
收藏数 110,893
精华内容 44,357
关键字:

图像处理深度学习