空洞卷积运算网络对应的标签怎么生成,就比如空洞率为2,标签怎么生成

入门 | 一文概览深度学习中的卷积结构
入门 | 一文概览深度学习中的卷积结构
选自Medium作者:Paul-Louis Prove机器之心编译参与:路雪、李亚洲本文对三种不同的卷积进行了介绍,同时讲解了各自的优点,对初学者而言,是理解卷积的一篇好文章。卷积首先,我们需要定义卷积层的几个参数。kernel 为 3、stride 为 1,使用 padding 的 2D 卷积卷积核大小:卷积核决定卷积的视野。2D 卷积的常见卷积核为 3,即 3x3 像素。stride:stride 决定卷积核遍历图像时的步子大小。默认值通常为 1,我们可以将 stride 设置成 2,对图像进行类似最大池化的下采样。Padding:padding 决定处理样本时的边界。(半)填充的卷积使输出空间维度等于输入,而未填充的卷积会裁剪部分边界,如果卷积核大于 1 的话。输入&输出通道:卷积层通常需要一定数量的输入通道 (I),计算一定数量的输出通道 (O)。所需参数可以通过 IOK 来计算,K 就是卷积核的值。机器之心曾介绍过用于语义分割中的各种卷积:从全连接层到大型卷积核:深度学习语义分割全指南扩张卷积(又叫空洞卷积)kernel 为 3、扩张率为 2、没有 padding 的 2D 卷积扩张卷积向卷积层引入另一个参数「扩张率」。它决定了卷积核中值之间的空间。3x3 卷积核、扩张率为 2 的卷积视野和 5x5 卷积核的视野相同,并且前者仅使用了 9 个参数。想象一个 5x5 的卷积核,每个都删去第二行和第二列。这种卷积用同样的计算成本生成了更大的视野。扩张卷积在实时分隔领域中尤为流行。如果你需要一个宽阔视野,但无力使用多个卷积或更大的卷积核,那么你可以使用这种卷积。转置卷积(解卷积或微步卷积)解卷积(deconvolution)这种叫法不太合适,因为这并不是解卷积。解卷积确实存在,但在深度学习领域中并不常见。真正的解卷积是卷积过程的逆转。想象一下将一个图像输入到单个卷积层上。再把输出放到黑箱中,然后再次输出的是原始输入图像。这个黑箱就叫作解卷积。这是卷积层执行的数学逆运算。转置卷积与解卷积有一些相似,因为它所输出的空间分辨率反卷积层也能够输出。但是,在这些值上真正进行的数学运算是不一样的。转置卷积层使用的是常规的卷积,但仍然能够进行空间分辨率转换。没有 padding、stride 为 2、卷积核为 3 的 2D 卷积到这里你可能有些疑惑,那么让我们看一下具体的例子吧。一个 5x5 的图像输入到卷积层中,stride 设置为 2,没有 padding,卷积核为 3x3。输出的是 2x2 的图像。如果我们想逆转该过程,则我们需要进行数学逆运算,以使我们输入的每个像素都能够生成 9 个值。之后,我们用值为 2 的 stride 遍历输出图像。这就是解卷积。没有 padding、stride 为 2、kernel 为 3 的转置 2D 卷积转置卷积并不这么做。二者唯一的共同点是输出的都是 5x5 的图像,虽然它执行的仍旧是常规的卷积运算。为了做到这一点,我们需要在输入上执行某种 padding。如同你能想象的,这一步不会从顶部逆转该流程,至少在数值方面不会实现逆转。它只不过是从前面重建了空间分辨率,且完成一个卷积。这可能不是数学意义上的逆转,但对编码器-解码器架构而言,它仍旧非常有帮助。通过这种方式,我们可以将卷积和图像的 upscaling 结合起来,而不是执行两个独立的流程。可分离卷积在可分离卷积中,我们能把卷积核运算分离到多个步骤中。例如,我们可以把一种卷积表达为 y = conv(x, k),其中 y 是输出图像,x 是输入图像,k 是卷积核。下面,假设 k 按 k = k1.dot(k2) 进行计算。这样可使其成为可分离卷积,因为我们不再使用 k 做 2D 卷积,而是通过用 k1 和 k2 做两个 1D 卷积得到同样的结果。Sobel X 与 Y 滤波器拿经常用于图像处理的 Sobel 核为例。你可以通过乘以向量 [1, 0, -1] 和 [1,2,1] 的转置向量获得相同的核。在进行相同操作时,这只需要 6 个参数,而无需 9 个。上述实例展示了空间可分离卷积,据我所知它并不用于深度学习。我只是想让大家在看到这个术语时不会感到困惑。在神经网络中,我们通常使用深度可分离卷积(depthwise separable convolution)。这种卷积将执行空间卷积,同时保持通道分离,接着跟从深度卷积。为了便于理解,我们来看一个实例。假设我们在 16 个输入通道和 32 个输出通道上有一个 3x3 卷积层。每一个输入通道都由 32 个 3x3 内核遍历,产生 512(16x32)个特征图。下一步,我们通过叠加每一个输入通道中的特征图,合并形成一个特征图。由于我们这样做了 32 次,我们得到了 32 个想要的输出通道。对于相同实例上的深度可分离卷积,我们遍历了 16 个通道(每个带有一个 3x3 内核),得到了 16 个特征图。现在,在合并之前,我们遍历了这 16 个特征图(每个带有 32 个 1x1 卷积),然后再把它们叠加在一起。相比于上述的 x3x3)个参数,这产生了 656(16x3x3 + 16x32x1x1)个参数。该实例是深度可分离卷积的特定实现,深度乘数是 1,这是目前这类卷积层的最常见设置。我们这么做是因为假设空间和深度信息可被解耦。看 Xception 模型的表现,该理论似乎是成立的。因其对参数的高效使用,深度可分离卷积也可被用于移动设备。原文地址:https://medium.com/towards-data-science/types-of-convolutions-in-deep-learning-d本文为机器之心编译,转载请联系本公众号获得授权。?------------------------------------------------加入机器之心(全职记者/实习生):投稿或寻求报道:广告&商务合作:
信息过载年代的干净阅读后使用快捷导航没有帐号?
一文了解各种卷积结构原理及优劣
查看: 23721|
评论: 0|来自: 量子位
摘要: 卷积神经网络作为深度学习的典型网络,在图像处理和计算机视觉等多个领域都取得了很好的效果。卷积核大小(Kernel Size):定义了卷积操作的感受野。在二维卷积中,通常设置为3,即卷积核大小为3×3。步幅(Stride) ...
卷积作为的典型网络,在图像处理和计算机视觉等多个领域都取得了很好的效果。Paul-Louis Pröve在Medium上通过这篇文章快速地介绍了不同类型的卷积结构(Convolution)及优势。为了简单起见,本文仅探讨二维卷积结构。卷积首先,定义下卷积层的结构参数。卷积核为3、步幅为1和带有边界扩充的二维卷积结构卷积核大小(Kernel Size):定义了卷积操作的感受野。在二维卷积中,通常设置为3,即卷积核大小为3×3。步幅(Stride):定义了卷积核遍历图像时的步幅大小。其默认值通常设置为1,也可将步幅设置为2后对图像进行下采样,这种方式与较大池化类似。边界扩充(Padding):定义了网络层处理样本边界的方式。当卷积核大于1且不进行边界扩充,输出尺寸将相应缩小;当卷积核以标准方式进行边界扩充,则输出数据的空间尺寸将与输入相等。输入与输出通道(Channels):构建卷积层时需定义输入通道I,并由此确定输出通道O。这样,可算出每个网络层的参数量为I×O×K,其中K为卷积核的参数个数。例,某个网络层有64个大小为3×3的卷积核,则对应K值为 3×3 =9。空洞卷积空洞卷积(atrous convolutions)又名扩张卷积(dilated convolutions),向卷积层引入了一个称为 “扩张率(dilation rate)”的新参数,该参数定义了卷积核处理数据时各值的间距。卷积核为3、扩张率为2和无边界扩充的二维空洞卷积一个扩张率为2的3×3卷积核,感受野与5×5的卷积核相同,而且仅需要9个参数。你可以把它想象成一个5×5的卷积核,每隔一行或一列删除一行或一列。在相同的计算条件下,空洞卷积提供了更大的感受野。空洞卷积经常用在实时图像分割中。当网络层需要较大的感受野,但计算资源有限而无法提高卷积核数量或大小时,可以考虑空洞卷积。转置卷积转置卷积(transposed Convolutions)又名反卷积(deconvolution)或是分数步长卷积(fractially straced convolutions)。反卷积(deconvolutions)这种叫法是不合适的,因为它不符合反卷积的概念。在深度学习中,反卷积确实存在,但是并不常用。实际上,反卷积是卷积操作的逆过程。你可以这么理解这个过程,将某个图像输入到单个卷积层,取卷积层的输出传递到一个黑盒子中,这个黑盒子输出了原始图像。那么可以说,这个黑盒子完成了一个反卷积操作,也就是卷积操作的数学逆过程。转置卷积与真正的反卷积有点相似,因为两者产生了相同的空间分辨率。然而,这两种卷积对输入数据执行的实际数学运算是不同的。转置卷积层只执行了常规的卷积操作,但是恢复了其空间分辨率。卷积核为3、步幅为2和无边界扩充的二维卷积结构举个例子,假如将一张5×5大小的图像输入到卷积层,其中步幅为2,卷积核为3×3,无边界扩充。则卷积层会输出2×2的图像。若要实现其逆过程,需要相应的数学逆运算,能根据每个输入像素来生成对应的9个值。然后,将步幅设为2,遍历输出图像,这就是反卷积操作。卷积核为3×3、步幅为2和无边界扩充的二维转置卷积转置卷积和反卷积的共同点在于两者输出都为5×5大小的图像,不过转置卷积执行的仍是常规的卷积操作。为了实现扩充目的,需要对输入以某种方式进行填充。你可以理解成,至少在数值方面上,转置卷积不能实现卷积操作的逆过程。转置卷积只是为了重建先前的空间分辨率,执行了卷积操作。这不是卷积的数学逆过程,但是用于编码器-解码器结构中,效果仍然很好。这样,转置卷积可以同时实现图像的粗粒化和卷积操作,而不是通过两个单独过程来完成。可分离卷积在可分离卷积(separable convolution)中,可将卷积核操作拆分成多个步骤。卷积操作用y=conv(x, k)来表示,其中输出图像为y,输入图像为x,卷积核为k。接着,假设k可以由下式计算得出:k=k1.dot(k2)。这就实现了一个可分离卷积操作,因为不用k执行二维卷积操作,而是通过k1和k2分别实现两次一维卷积来取得相同效果。X、Y方向上的Sobel滤波器Sobel算子通常被用于图像处理中,这里以它为例。你可以分别乘以矢量[1,0,-1]和[1,2,1]的转置矢量后得到相同的滤波器。完成这个操作,只需要6个参数,而不是二维卷积中的9个参数。这个例子说明了什么叫做空间可分离卷积,这种方法并不应用在深度学习中,只是用来帮你理解这种结构。在神经网络中,我们通常会使用深度可分离卷积结构(depthwise separable convolution)。这种方法在保持通道分离的前提下,接上一个深度卷积结构,即可实现空间卷积。接下来通过一个例子让大家更好地理解。假设有一个3×3大小的卷积层,其输入通道为16、输出通道为32。具体为,32个3×3大小的卷积核会遍历16个通道中的每个数据,从而产生16×32=512个特征图谱。进而通过叠加每个输入通道对应的特征图谱后融合得到1个特征图谱。最后可得到所需的32个输出通道。针对这个例子应用深度可分离卷积,用1个3×3大小的卷积核遍历16通道的数据,得到了16个特征图谱。在融合操作之前,接着用32个1×1大小的卷积核遍历这16个特征图谱,进行相加融合。这个过程使用了16×3×3+16×32×1×1=656个参数,远少于上面的16×32×3×3=4608个参数。这个例子就是深度可分离卷积的具体操作,其中上面的深度乘数(depth multiplier)设为1,这也是目前这类网络层的通用参数。这么做是为了对空间信息和深度信息进行去耦。从Xception模型的效果可以看出,这种方法是比较有效的。由于能够有效利用参数,因此深度可分离卷积也可以用于移动设备中。欢迎加入本站公开兴趣群商业智能与数据分析群兴趣范围包括各种让数据产生价值的办法,实际应用案例分享与讨论,分析工具,ETL工具,数据仓库,数据挖掘工具,报表系统等全方位知识QQ群:
上一篇:下一篇:
dataguru.cn All Right Reserved.拒绝访问 | colabug.com | 百度云加速
请打开cookies.
此网站 (colabug.com) 的管理员禁止了您的访问。原因是您的访问包含了非浏览器特征(43f439c-ua98).
重新安装浏览器,或使用别的浏览器IT 三郎 - 不忘初心,方得始终。
五月 13, 2018
图像语义分割
语义分割方法在处理图像时需要具体到像素级别,也就是说语义分割会将图像中每个像素分配到某个对象类别。
如上图,左图为输入图像、右图为经过语义分割后的图像。语义分割不仅要识别出摩托车和驾驶者,还要标出每个对象的边界。因此与分类目的不同,相关模型要具有像素级的密集预测能力。
2015年UC Berkeley 的Jonathan Long等人将CNN引入图像语义分割领域,开起了深度卷积网络在图像语义分割领域的新篇章。目前大多数图像语义分割都是基于基本的深度卷积网络实现,例如AlexNet、VGG16、ResNet101、Xception等。CNN的发展促进了语义分割的发展,CNN的发展如下图:
VGG网络是在AlexNet网络的基础上发展而来的,其主要贡献在于使用非常小的3*3的卷积核进行网络设计,并且将网络深度增加到16-19层。在2014年ImageNet比赛中,获得了定位第1,分类第2的好成绩,网络具有很好的泛化能力。由牛津大学 Visual Geometry Group(视觉几何组)完成的论文,所以叫VGG。结构图如下:
分为A-LRN、A-E 6种结构,VGG16是指结构C,由13个卷积层和3个全连接层组成。
根据公式 H1 = ( H – kernel + 2 x padding ) / stride + 1
conv3采用 kernel = 3, stride = 1, padding = 1的方式,H1= ( H – 3 + 2 x 1 ) / 1 + 1 = H,故conv3卷积不改变图像(特征图)分辨率。
maxpool采用 kernel = 2, stride = 2, padding = 0的方式,H1 = ( H &# x 0) / 2 + 1 = H / 2 ,故maxpool池化将图像缩小为原来的一半。
VGG输入是224 x 224的RGB图像,在经过5次maxpool后缩小为原来的1/32,变成7 x 7的特征图。
为什么采用conv3?
1.如下图,两个3 x 3的卷积层串联相当于一个5 x 5的卷积层(感受野大小为5 x 5)。而三个3 x 3的卷积层串联的效果则相当于一个7 x 7的卷积层。
2.除此之外,三个串联的3 x 3的卷积层,拥有比一个7 x 7的卷积层更少的参数量,只有后者的(3 x 3 x 3) / (7 x 7) = 55%。
3.三个3 x 3的卷积层拥有比一个7 x 7的卷积层更多的非线性变换(前者可以使用三次ReLU激活函数,而后者只有一次),使得CNN对特征的学习能力更强。
DCNN在语义分割中存在的问题
首先我们应该了解CNN在图像语义分割时需要解决的三个问题:
1.下采样(池化)过程中导致细节的丢失。
2.CNN的空间不变性,对于同一张图进行空间变换分类结果不变,但是语义分割要求随着空间变换,分割的区域不同。
3.多尺度目标的类别预测 。
Deeplab V1
针对CNN存在的两个问题本文采取的解决方案:
1.使用带孔卷积解决下采样问题
2.使用全连接CRF解决空间不变性问题
3.使用MLP结合多尺度特征解决多尺度目标的类别预测
本文采用VGG16修改而成,将VGG16模型中的全连接层全部转换成卷积层,由于VGG16的5次maxpool得到特征图为原图的1/32,作者的目标是得到一个1/8原图的特征图,所以移除最后两个maxpool,但是通过查看源码发现作者并没有移除最后两层maxpool,而是将参数修改成stride = 1 ,padding = 1,根据公式计算( H – 2 + 2 x 1) / 1 + 1 = H + 1,增加1像素,但是作者并没有处理,影响不大。
分辨率比之前提高,会导致最后一个卷积层的感受野相对变小,所以作者的idea是对原卷积核填充0,也就是hole,把kernel试着变大。
maxpool4的stride由2变为1,则紧接着的conv5_1,、conv5_2、conv5_3中hole size为2。
maxpool5由2变为1, 则后面的fc6中hole size为4。
此处实际为空洞卷积,如下图(hole size = 1):
在把VGG的后面的全连接层转换为卷积层之后,比如说第一个全连接层(即原来的FC6)现在的卷积kernel = 7,计算量会很大,作者直接从7×7的范围中抽取一个 4×4 (or 3×3)的范围以此来减小计算量,计算时间比原来减少了2-3倍。
DCNN的输出与GroundTruth下采样8倍做比较,损失函数采用交叉熵训练网络。DCNN模型训练完成后采用双线性插值法恢复到原图分辨率。如下图,得分图可以可靠地预测图像中对象的存在和粗略位置,但不太适合用于刻画精准的轮廓。
然后作者采用Fully Connected CRF改善分割细节。CRF简单来说,能做到的就是在决定一个位置的像素值时(在这个paper里是label),会考虑周围邻居的像素值(label),这样能抹除一些噪音。但是通过CNN得到的特征图在一定程度上已经足够平滑了,所以仅考虑周围邻居的CRF没什么意义。于是作者采用了Fully Connected CRF,这样考虑的就是全局的信息了。
双线性插值法
Fully Connected CRF
全连接的CRF模型使用的能量函数E(x)为:
这分为一元势函数θi(xi)和二元势函数θij(xi,xj)两部分。
一元势函数是定义在观测序列位置i的状态特征函数,用于刻画观测序列对标记变量的影响,故这里P(xi)是取DCNN计算关于像素i的输出的标签分配概率。
二元势函数是描述像素和像素之间的关系,如果比较相似,那可能是一类,否则就裂开,这可以细化边缘。一般的二元势函数只取像素点与周围像素之间的边,这里使用的是全连接,即像素点与其他所有像素之间的关系。
DeepLab由DCNN和CRF组成,训练策略是分段训练,即DCNN的输出是CRF的一元势函数,在训练CRF时是固定的。在对DCNN做了fine-tune后,对CRF做交叉验证。这里使用ω2=3和σγ=3在小的交叉验证集上寻找最佳的ω1,σα,σβ,采用从粗到细的寻找策略。
解决多尺度预测问题
论文还探讨了使用多尺度预测提高边界定位效果。具体的,在输入图像和前四个最大池化层的输出上附加了两层的MLP(第一层是128个3×3卷积,第二层是128个1×1卷积),最终输出的特征映射送到模型的最后一层辅助预测,合起来模型最后的softmax层输入特征多了5×128=640个通道,实验表示多尺度有助于提升预测结果,但是效果不如CRF明显。
DeepLab是结合了深度卷积神经网络(DCNNs)和概率图模型(DenseCRFs)的方法。在实验中发现DCNNs做语义分割时精准度不够的问题,根本原因是DCNNs的高级特征的平移不变性(即高层次特征映射,根源于重复的池化和下采样)。
针对信号下采样或池化降低分辨率,DeepLab是采用的atrous(带孔)算法扩展感受野,获取更多的上下文信息。分类器获取以对象中心的决策是需要空间变换的不变性,这天然的限制了DCNN的定位精度,DeepLab采用完全连接的条件随机场(CRF)提高模型捕获细节的能力。
除空洞卷积和CRFs之外,论文使用的tricks还有Multi-Scale features。其实就是U-Net和FPN的思想,在输入图像和前四个最大池化层的输出上附加了两层的MLP(第一层是128个3×3卷积,第二层是128个1×1卷积),最终输出的特征与主干网的最后一层特征图融合,特征图增加5×128=640个通道,实验表示多尺度有助于提升预测结果,但是效果不如CRF明显。
论文的模型基于VGG16,在Titan GPU上运行速度达到了8FPS,全连接CRF平均推断需要0.5s ,PASCAL VOC-2012 达到71.6% IOU accuracy。
交并比(Intersection-over-Union,IoU),目标检测中使用的一个概念,是产生的候选框(candidate bound)与原标记框(ground truth bound)的交叠率,即它们的交集与并集的比值。最理想情况是完全重叠,即比值为1。
Deeplab V2
Deeplab V2可以看作Deeplab V1 的升级版,主要是增加了ASPP代替MLP解决多尺度目标的类别预测 ,同时V2除了采用VGG16还采用了ResNet101。
以往进行多尺度目标的类别预测,需要将不同尺度的图像输入DCNN,但计算量增加。
作者根据SPP的思想,在给定特征层使用不同的采样率进行重采样,使用具有不同采样率的平行atrous卷积层实现,称为atrous SPP(ASPP)。
ASPP(带洞空间金字塔池化)方法示意图如下图所示:
以VGG16为例,在maxpool5后采用(rate分别为6、12、18、24)空洞卷积,得到特征图后合成,在用softmax分类器分类。
DeepLabv2是相对于DeepLabv1基础上的优化。DeepLabv1在三个方向努力解决,但是问题依然存在:特征分辨率的降低、物体存在多尺度,DCNN的平移不变性。
因DCNN连续池化和下采样造成分辨率降低,DeepLabv2在最后几个最大池化层中去除下采样,取而代之的是使用空洞卷积,以更高的采样密度计算特征映射。 物体存在多尺度的问题,DeepLabv1中是用多个MLP结合多尺度特征解决,虽然可以提供系统的性能,但是增加特征计算量和存储空间。论文受到我们受到spatial pyramid pooling(SPP)的启发,提出了一个类似的结构,在给定的输入上以不同采样率的空洞卷积并行采样,相当于以多个比例捕捉图像的上下文,称为ASPP模块。
DCNN的分类不变形影响空间精度。DeepLabv2是采样全连接的CRF在增强模型捕捉细节的能力。 论文的模型基于ResNet,在NVidia Titan X GPU上运行速度达到了8FPS,全连接CRF平均推断需要0.5s ,在耗时方面和DeepLabv1无差异,但在PASCAL VOC-2012 达到79.7 mIOU。
MSRA何凯明团队的Residual Networks,在2015年ImageNet上大放异彩,在ImageNet的classification、detection、localization以及COCO的detection和segmentation上均斩获了第一名的成绩,而且Deep Residual Learning for Image Recognition也获得了CVPR2016的best paper。
ResNet最根本的动机就是所谓的“退化”问题,即当模型的层次加深时,错误率却提高了,如下图:
但是模型的深度加深,学习能力增强,因此更深的模型不应当产生比它更浅的模型更高的错误率。而这个“退化”问题产生的原因归结于优化难题,当模型变复杂时,SGD的优化变得更加困难,导致了模型达不到好的学习效果。
针对这个问题,作者提出了一个残差的结构,它使用了一种连接方式叫做“shortcut connection”,顾名思义,shortcut就是“抄近道”的意思,:
ResNet提出了两种mapping:第一种是identity mapping,指的就是上中”弯弯的曲线”,第二种residual mapping,指的就是除了”弯弯的曲线“那部分,所以最后的输出是 H(x)=F(x)+x
identity mapping顾名思义,就是指本身,也就是公式中的x,而residual mapping指的是“差”,也就是H(x) – x,所以残差指的就是F(x)部分。
为什么ResNet可以解决“随着网络加深,准确率不下降”的问题?
1.实验方面,实验结果如下图:
2.理论方面,ResNet提供了两种选择方式,也就是identity mapping和residual mapping,如果网络已经到达最优,继续加深网络,residual mapping将被push为0,只剩下identity mapping,这样理论上网络一直处于最优状态了,网络的性能也就不会随着深度增加而降低了。
作者提出了两种残差结构:
这两种结构分别针对ResNet34(左图)和ResNet50/101/152(右图),一般称整个结构为一个”building block“。其中右图又称为”bottleneck design”,目的一目了然,就是为了降低参数的数目,第一个1×1的卷积把256维channel降到64维,然后在最后通过1×1卷积恢复,整体上用的参数数目:1x1x256x64 + 3x3x64x64 + 1x1x64x256 = 69632,而不使用bottleneck的话就是两个3x3x256的卷积,参数数目: 3x3x256x256x2 = 1179648,差了16.94倍。
对于常规ResNet,可以用于34层或者更少的网络中,对于Bottleneck Design的ResNet通常用于更深的如101这样的网络中,目的是减少计算和参数量(实用目的)。
ResNet50/101结构:
F(x) 与 x 通道数不同如何相加,因为F(x)和x是按照通道维度相加的,通道不同怎么相加?
两种Shortcut Connection方式,分别为上图实线、虚线。
实线的Connection部分都是执行3x3x64的卷积,他们的channel个数一致,所以采用计算方式: H(x) = F(x) + x
虚线的Connection部分分别是3x3x64和3x3x128的卷积操作,他们的channel个数不同(64和128),所以采用计算方式: H(x) = F(x) + Ox,其中O是卷积操作1 x 1卷积用来统一通道数。
Deeplab V3
V3和V1 & V2相比改进的地方:
1.所提出的框架是通用的,可以应用于任何网络。
2.最后一个ResNet块(Block 4)的几个副本被复制,并以级联排列。
3.ASPP中使用了Batch Normalization
4.没有使用CRF
讨论多种捕获多尺度信息的方式:
(a). Image Pyramid: 将输入图片放缩成不同比例,分别应用在DCNN上,将预测结果融合得到最终输出。
(b). Encoder-Decoder: 利用Encoder阶段的多尺度特征,运用到Decoder阶段上恢复空间分辨率(代表工作有FCN、SegNet、PSPNet等工作)。
(c). Deeper w. Atrous Convolution: 在原始模型的顶端增加额外的模块,例如DenseCRF,捕捉像素间长距离信息。
(d). Spatial Pyramid Pooling: 空间金字塔池化具有不同采样率和多种视野的卷积核,能够以多尺度捕捉对象。
论文首先探讨将空洞卷积应用在级联模块。具体来说,我们取ResNet中最后一个block,在下图中为block4,并在其后面增加级联模块。
上图(a)所示,整体图片的信息总结到后面非常小的特征映射上,但实验证明这是不利于语义分割的。上图(b)所示,可使用不同采样率的空洞卷积保持输出步幅的为out_stride = 16.这样不增加参数量和计算量同时有效的缩小了步幅。
作者在DeepLabv3中ASPP中添加了BN层。不同采样率的空洞卷积可以有效的捕获多尺度信息,但是,我们发现随着采样率的增加,滤波器的有效权重(权重有效的应用在特征区域,而不是填充0)逐渐变小。如下图所示:
当我们不同采样率的3×3卷积核应用在65×65的特征映射上,当采样率接近特征映射大小时,3×3的滤波器不是捕捉全图像的上下文,而是退化为简单的1×1滤波器,只有滤波器中心点的权重起了作用。为了克服这个问题,我们考虑使用图片级特征。具体来说,我们在模型最后的特征映射上应用全局平均池化,将结果经过1×1的卷积,再双线性上采样得到所需的空间维度。
最终,我们改进的ASPP包括:
一个1×1卷积和三个3×3的采样率为rates={6,12,18}的空洞卷积,滤波器数量为256,包含BN层。
针对output_stride=16的情况。如下图(a)部分Atrous Spatial Pyramid Pooling。
图像级特征,即将特征做全局平均池化,经过卷积,再融合。如下图(b)部分Image Pooling。
改进后的ASPP模块如下图所示:
DeepLab延续到DeepLab V3,依然是在空洞卷积做文章,但是探讨不同结构的方向。
V1-V2都是使用带孔卷积提取密集特征来进行语义分割。但是为了解决分割对象的多尺度问题,deeplabv3设计采用多比例的带孔卷积级联或并行来捕获多尺度背景。
DeepLab V3将修改之前提出的带孔空间金字塔池化模块,该模块用于探索多尺度卷积特征,将全局背景基于图像层次进行编码获得特征,取得当时最优性能,在PASCAL VOC-2012 达到86.9mIOU。
Xception 是基于Inception 发展而来,是Extreme Inception(极端 Inception)的简称。
Inception最初提出的版本,其核心思想就是使用多尺寸卷积核去观察输入数据。举个例子,我们看某个景象由于远近不同,同一个物体的大小也会有所不同,那么不同尺度的卷积核观察的特征就会有这样的效果。于是就有了如下的网络结构图:
于是我们的网络就变胖了,增加了网络的宽度,同时也提高了对于不同尺度的适应程度。但是我们的网络变胖了的同时,计算量也变大了,所以我们就要想办法减少参数量来减少计算量。
我们采用如下方法减少参数量:
1.使用1 x 1卷积核对输入的特征图进行降维处理(PointWise Conv)
2.使用多个小卷积核代替大卷积核
提出了Inception v3,如下图所示:
在Inception基础上为了进一步降低参数量提出了Bottleneck结构
先对数据进行降维,再进行常规卷积核的卷积,最后对数据进行升维,ResNet就是采用了这种思想。
但是发现参数量还是很大,于是提出了Xception主要采用Depthwise Separable Conv方法。
1.分别按不同通道进行一次卷积(生成 输入通道数 张 Feature Maps)- DW
2.再将这些 Feature Maps 一起进行第二次卷积 – PW
Standard Convolution参数量2 x 3 x 3 x 3 = 54
Depthwise Separable Convolution参数量为2 x 3 x 3 + 2 x 1 x 1 x 3 = 18 + 6 = 24
Xception网络结构图:
其中 SeparableConv具体结构如下:
Deeplab V3+
主要贡献:
1. 提出DeepLabv3+,采用Encoder-Decoder结构(其实就是语义分割常用的下采样再上采样);
2. 该网络通过带孔卷积可以任意控制Encoder Feature的大小,有较好的尺度适应性;
3. 采用修改后的 Xception主干网络,并在ASPP(带孔卷积模块)和Decoder模块采用Depthwise Separable Convolution;
如图在Decoder部分,Encoder输出通过双线性上采样x4之后,和浅层通过1x1conv 降低通道数后得到的同尺度的特征图堆叠,之后再通过一个3×3 conv,上采样x4后恢复到原图大小。
与 Xception 不同的几点是:
层数变深了。
所有的最大池化都被替换成了 3×3 with stride 2 的 Separable Convolution。
在每个 3×3 Depthwise Separable Convolution 的后面加了 BN 和 ReLU。
DeepLab V3+继续在模型的架构上作文章,为了融合多尺度信息,引入语义分割常用的Encoder-Decoder。在Encoder-Decoder架构中,引入可任意控制编码器提取特征的分辨率,通过空洞卷积平衡精度和耗时。在语义分割任务中采用Xception 模型,在ASPP和解码模块使用Depthwise Separable Convolution,提高编码器-解码器网络的运行速率和健壮性,在 PASCAL VOC 2012 达到 89.0mIOU。
DeepLab V3+效果测试
源码地址:
本文参考了大量互联网资源,原文链接如下,如有遗漏请联系添加。本文作为个人学习笔记整理,如有错误,还望指正。
三月 29, 2018
1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950import tensorflow as tf
import numpy as np
import matplotlib.pyplot as plt
def add_layer(inputs,in_size,out_size,activation_function=None):
& & &Weights = tf.Variable(tf.random_normal([in_size,out_size]))
& & &biases = tf.Variable(tf.zeros([1,out_size]) +0.1)
& & &Wx_plus_b = tf.matmul(inputs,Weights) + biases
& & &if activation_function is None:
& & & & &outputs = Wx_plus_b
& & &else:
& & & & &outputs = activation_function(Wx_plus_b)
& & &return outputs
x_data = np.linspace(-1,1,300)[:,np.newaxis]
noise = np.random.normal(0,0.05,x_data.shape)
y_data = np.square(x_data) - 0.5 + noise
#y_data = np.square(x_data) - 0.5
xs = tf.placeholder(tf.float32,[None,1])
ys = tf.placeholder(tf.float32,[None,1])
l1 = add_layer(xs,1,10,activation_function=tf.nn.relu)
prediction = add_layer(l1,10,1,activation_function=None)
loss = tf.reduce_mean(tf.reduce_sum(tf.square(ys - prediction),reduction_indices=[1]))
train_step = tf.train.GradientDescentOptimizer(0.05).minimize(loss)
init = tf.global_variables_initializer()
sess = tf.Session()
sess.run(init)
# 绘制数据图像
fig = plt.figure()
ax = fig.add_subplot(1,1,1)
ax.scatter(x_data,y_data)
plt.ion()
plt.show()
for i in range(10000):
& & sess.run(train_step,feed_dict={xs:x_data,ys:y_data})
& & if i%50 == 0:
& & & & print(sess.run(loss,feed_dict={xs:x_data,ys:y_data}))
& & & & try:
& & & & & & ax.lines.remove(lines[0])
& & & & except Exception:
& & & & & & pass
& & & & prediction_value = sess.run(prediction,feed_dict={xs:x_data})
& & & & lines = ax.plot(x_data,prediction_value,'r-',lw=5)
& & & & plt.pause(0.1)
三月 29, 2018
12345678910111213141516171819202122232425262728293031323334import tensorflow as tf
import numpy as np
def add_layer(inputs,in_size,out_size,activation_function=None):
& & &Weights = tf.Variable(tf.random_normal([in_size,out_size]))
& & &biases = tf.Variable(tf.zeros([1,out_size]) +0.1)
& & &Wx_plus_b = tf.matmul(inputs,Weights) + biases
& & &if activation_function is None:
& & & & &outputs = Wx_plus_b
& & &else:
& & & & &outputs = activation_function(Wx_plus_b)
& & &return outputs
x_data = np.linspace(-1,1,300)[:,np.newaxis]
noise = np.random.normal(0,0.5,x_data.shape)
y_data = np.square(x_data) - 0.5 + noise
xs = tf.placeholder(tf.float32,[None,1])
ys = tf.placeholder(tf.float32,[None,1])
l1 = add_layer(xs,1,10,activation_function=tf.nn.relu)
prediction = add_layer(l1,10,1,activation_function=None)
loss = tf.reduce_mean(tf.reduce_sum(tf.square(ys - prediction),reduction_indices=[1]))
train_step = tf.train.GradientDescentOptimizer(0.05).minimize(loss)
init = tf.global_variables_initializer()
sess = tf.Session()
sess.run(init)
for i in range(10000):
& & sess.run(train_step,feed_dict={xs:x_data,ys:y_data})
& & if i%50 == 0:
& & & & print(sess.run(loss,feed_dict={xs:x_data,ys:y_data}))
十二月 1, 2017
理想很丰满,现实很骨感
来都来了,看看吧。。。。
听说研究生院办了个文艺展演活动(蛋疼展演活动)
作为辽大最大的工科学院(辽大是不是工科只有信息学院),我们不能落后啊!!!!
同学们踊跃报名(班委东拼西凑、威逼利诱),我们上了两个节目,《水手》《推销》
说好的华尔兹木有了,想脱单的小伙伴有没有进展啊、啊!!
演员不够、班委来凑、唱的了水手、演的了推销,厉不厉害(报名人不够,我们不上怎么办,下次大家踊跃点呀,拜托拜托!!!)
排练同学们还是很积极的(有活动要守时啊,说好的6点,6点半来了,来了我们也欢迎啊!!!)
班委群为了守时定规矩了,开会迟到一分钟10块钱啊!(你寝室有班委,他要开会的时候,一定要按住了,五五开怎么样~)
排练还是很辛苦哒,(哲理301太冷了!!! 冻脚!冻脚)
在礼堂表演是这样的,快找找你自己,找不着的话问问你前边的妹子为什么要挡住!!(传说水手帽9.9包邮)
排练的时候是这样的,在哲理楼瑟瑟发抖,有对象的回去抱对象,没对象的怎么办。(说好的加分,真的假的,会不会加到空气中,算了原谅色!!)
我说班长和团支书没事,你信不信!!!看看幸福的表情,看看旁边两个羡慕的神态~~~(有事没事我真不知道哈~别来打我~~分布式班长演讲,我问了几个问题她说要打我~~~)
好不容易抢了包辣条,还得挨打,孙悟空的棒子(可能是拖把杆),小胖紧盯着他的辣条,表演完回来就吃了!对他吃的!!!
这是谁,谁这是,用了雕牌护肤水的妹子,我在那举着心,团支书在干吗(莫非是思考人生)
罪魁祸首在这,这几个推销的(我要是他们我早跑了,谁这么听话,在这站着)
感谢2017信息学院全体同学的共同努力,我们拿了一个二等奖一个三等奖(虽然是鼓励奖,有总比没有强吧,毕竟我们排练这么长时间了)
(瞅啥,点它)
就这么多了,没看够,我博客里还有其他的,随便看看啦!!!
十一月 19, 2017
pom.xml文件
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081&project xmlns=&http://maven.apache.org/POM/4.0.0& xmlns:xsi=&http://www.w3.org/2001/XMLSchema-instance&
& xsi:schemaLocation=&http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd&&
& &modelVersion&4.0.0&/modelVersion&
& &groupId&wang.linteng&/groupId&
& &artifactId&es&/artifactId&
& &packaging&war&/packaging&
& &version&1.0-SNAPSHOT&/version&
& &name&es Maven Webapp&/name&
& &url&http://maven.apache.org&/url&
& &properties&
& & &spring.version&4.2.5.RELEASE&/spring.version&
& &/properties&
& &dependencies&
& & &dependency&
& & & &groupId&junit&/groupId&
& & & &artifactId&junit&/artifactId&
& & & &version&3.8.1&/version&
& & & &scope&test&/scope&
& & &/dependency&
& & &dependency&
& & & &groupId&jstl&/groupId&
& & & &artifactId&jstl&/artifactId&
& & & &version&1.2&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.springframework&/groupId&
& & & &artifactId&spring-core&/artifactId&
& & & &version&${spring.version}&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.springframework&/groupId&
& & & &artifactId&spring-beans&/artifactId&
& & & &version&${spring.version}&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.springframework&/groupId&
& & & &artifactId&spring-context&/artifactId&
& & & &version&${spring.version}&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.springframework&/groupId&
& & & &artifactId&spring-web&/artifactId&
& & & &version&${spring.version}&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.springframework&/groupId&
& & & &artifactId&spring-webmvc&/artifactId&
& & & &version&${spring.version}&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.elasticsearch.client&/groupId&
& & & &artifactId&transport&/artifactId&
& & & &version&5.6.4&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.apache.logging.log4j&/groupId&
& & & &artifactId&log4j-to-slf4j&/artifactId&
& & & &version&2.9.1&/version&
& & &/dependency&
& & &dependency&
& & & &groupId&org.slf4j&/groupId&
& & & &artifactId&slf4j-api&/artifactId&
& & & &version&1.7.24&/version&
& & &/dependency&
& &/dependencies&
& & &finalName&es&/finalName&
& &/build&
&/project&
ES操作工具类
123456789101112131415161718192021222324252627282930313233343536373839404142434445package wang.linteng.util;
import org.elasticsearch.client.transport.TransportClient;
import org.elasticsearch.common.settings.Settings;
import org.elasticsearch.common.transport.InetSocketTransportAddress;
import org.elasticsearch.transport.client.PreBuiltTransportClient;
import java.net.InetAddress;
import java.net.UnknownHostException;
public class EsTool {
& & public static final String CLUSTER_NAME =&linteng-es&;
& & public static final String INDEX_NAME = &news&;
& & private static TransportClient client;
& & // 获取客户端
& & public static TransportClient getClient(){
& & & & Settings settings = Settings.builder()
& & & & & & & & .put(&cluster.name&,CLUSTER_NAME)
& & & & & & & & .put(&client.transport.sniff&, true)
& & & & & & & & .build();
& & & & client = new PreBuiltTransportClient(settings);
& & & & try {
& & & & & & client.addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName(&localhost&), 9300));
& & & & } catch (UnknownHostException e) {
& & & & & & e.printStackTrace();
& & & & }
& & & & return client;
& & }
& & // 关闭客户端
& & public static void closeClient(){
& & & & if(client != null){
& & & & & & client.close();
& & & & }
& & }
& & // 获取索引名称
& & public static String getIndexName(){
& & & & return INDEX_NAME;
& & }
项目源码:
十一月 18, 2017
1.首先需要git,没有的话需要先安装
1sudo apt-get install git
2.下载head源码
1git clone git://github.com/mobz/elasticsearch-head.git
3.安装node,因为head是一个基于nodejs的项目,下载的地址:
4.选择适合的版本,解压到相应的目录,然后配置环境变量在/etc/profile,然后执行source /etc/profile,如果运行报错重启系统再试一下
export NODE_HOME=/opt/node-v8.9.1
export PATH=$PATH:$NODE_HOME/bin
5.测试node是否生效,正常会输出版本信息
123echo $NODE_HOME
6.安装grunt,grunt是一个构建工具,head5.x版本是通过grunt启动的,所以要安装,最后检查一下版本
12npm install grunt-cli
grunt -version
7.在下载的目录里执行
1npm install
8.最后启动
12grunt server
nohup grunt server & #后台启动注意终端退出使用exit,否则后台服务会终止
9.访问http://localhost:9100
十一月 18, 2017
elasticsearch5.x版本logstash-input-jdbc的安装方式与以往不同
1.这里要用到的是Logstash的一个插件Logstash-input-jdbc,这个插件可以将数据库中的数据同步到elasticsearch的索引库中,并且还能做实时增量同步。因此要用这个插件首先得下载一个Logstash,下载地址:,这里下载的版本要与elasticsearch一致,所以这里下载的是5.6.4版本
2.下载完解压到指定目录,进入目录输入
./logstash -e 'input { stdin { } } output { stdout {} }'
3.随便输入hello world,会打印出来提示信息,代表可以正常运行
4.logstash是基于ruby开发的,如果没有gem,那么先安装gem,注意使用root用户
1sudo apt-get install gem
5.查看是否gem安装成功
1gem sources -l
6.替换ruby镜像库为国内的库,因为国外的库,国内是访问不到的,然后国内有两个库,淘宝的库已经停止支持了,使用ruby-china的库
1gem sources --add https://gems.ruby-china.org/ --remove https://rubygems.org/
7.查看是否成功
1gem sources -l
8.然后进入bin目录,安装logstash-input-jdbc
1./plugin install logstash-input-jdbc
9.安装成功后进行数据导入,需要mysql的驱动、mysql.conf、mysql.sql三个文件
12345678910111213141516171819202122232425#mysql.conf
input {
& & jdbc {
& & & jdbc_driver_library =& &/opt/elasticsearch/logstash/bin/mysql/mysql-connector-java-5.1.44-bin.jar&
& & & jdbc_driver_class =& &com.mysql.jdbc.Driver& & &
& & & jdbc_connection_string =& &jdbc:mysql://localhost:3306/news&
& & & jdbc_user =& &root&
& & & jdbc_password =& &&
& & & statement_filepath =& &/opt/elasticsearch/logstash/bin/mysql/mysql.sql&
& & & jdbc_paging_enabled =& &true&
& & & jdbc_page_size =& &50000&
& & }
output {
& & stdout {
& & & & codec =& rubydebug
& & }
& & elasticsearch {
& & & & hosts =& &localhost:9200&
& & & & index =& &news&
& & }
这里的sql是mysql的查询语句,article是mysql的表名
12#mysql.sql
SELECT * FROM article
10.执行导入
1./logstash -f ./mysql/mysql.conf
十一月 18, 2017
1.安装ES前要检查是否已经安装过java环境,java -version
2.下载ES,这里选择的是历史版本5.6.4,下载地址:
3.将下载的压缩包解压后复制三份分别命名为es-node1、es-node2、es-node3
4.分别修改三个目录下的elasticsearch.yml
1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192# ======================== Elasticsearch Configuration =========================
# NOTE: Elasticsearch comes with reasonable defaults for most settings.
# & & & Before you set out to tweak and tune the configuration, make sure you
# & & & understand what are you trying to accomplish and the consequences.
# The primary way of configuring a node is via this file. This template lists
# the most important settings you may want to configure for a production cluster.
# Please consult the documentation for further information on configuration options:
# https://www.elastic.co/guide/en/elasticsearch/reference/index.html
# ---------------------------------- Cluster -----------------------------------
# Use a descriptive name for your cluster:
cluster.name: linteng-es
# ------------------------------------ Node ------------------------------------
# Use a descriptive name for the node:
node.name: node-1(修改成对应的名字)
# Add custom attributes to the node:
#node.attr.rack: r1
# ----------------------------------- Paths ------------------------------------
# Path to directory where to store the data (separate multiple locations by comma):
path.data: /opt/elasticsearch/es-node1/data(修改成对应的目录)
# Path to log files:
path.logs: /opt/elasticsearch/es-node1/logs
# ----------------------------------- Memory -----------------------------------
# Lock the memory on startup:
#bootstrap.memory_lock: true
# Make sure that the heap size is set to about half the memory available
# on the system and that the owner of the process is allowed to use this
# Elasticsearch performs poorly when the system is swapping the memory.
# ---------------------------------- Network -----------------------------------
# Set the bind address to a specific IP (IPv4 or IPv6):
#network.host: 0.0.0.0
# Set a custom port for HTTP:
http.port: 9200/9201/9202(三个文件分别修改成不同的端口,避免冲突)
http.cors.enabled: true
http.cors.allow-origin: &*&
transport.tcp.port: 9300/9301/9301
# For more information, consult the network module documentation.
# --------------------------------- Discovery ----------------------------------
# Pass an initial list of hosts to perform discovery when new node is started:
# The default list of hosts is [&127.0.0.1&, &[::1]&]
discovery.zen.ping.unicast.hosts: [&127.0.0.1:9300&,&127.0.0.1:9301&,&127.0.0.1:9302&]
# Prevent the &split brain& by configuring the majority of nodes (total number of master-eligible nodes / 2 + 1):
discovery.zen.minimum_master_nodes: 2
# For more information, consult the zen discovery module documentation.
# ---------------------------------- Gateway -----------------------------------
# Block initial recovery after a full cluster restart until N nodes are started:
#gateway.recover_after_nodes: 3
# For more information, consult the gateway module documentation.
# ---------------------------------- Various -----------------------------------
# Require explicit names when deleting indices:
#node.max_local_storage_nodes: 2
#action.destructive_requires_name: true
十一月 18, 2017
搜狗实验室的中文新闻数据集,数据量大概在129万条左右,下载地址:
数据集的格式:
1234567&doc&
&url&页面URL&/url&
&docno&页面ID&/docno&
&contenttitle&页面标题&/contenttitle&
&content&页面内容&/content&
注意:content字段去除了HTML标签,保存的是新闻正文文本
注意数据集的编码格式为ANSI,在进行数据导入的时候注意格式转换。
采用Navicat导入mysql数据库,导入向导时注意选择编码格式否则会产生乱码。
四月 6, 2017
坐在图书馆看着毕老师的JAVA教程,虽然不是第一次看了,但是想系统的学一遍。看着周围正在准备考研的学弟学妹们,刚过去不久的考研画面,不断地浮现在我的脑海里。考研我并不是一个成功者,但是这段经历一直在影响我,所以我决定写下来,写在我的博客上!
大三刚开学的时候,我一直在犹豫要不要考研。因为一直在孟老师的工作室写程序,大多是一些网站、微信平台,期间也能拿到一些报酬。其实自我感觉良好,关于上是否考研这件事,我想了很久,分析了利弊。其实我感觉如果不参加考研,一直做开发的话,找一个一线的互联网公司可能会有点困难,但是稍微差一点的应该没什么问题。大概大三上学期快结束的时候,我下定决心要考研,当时一心要考学硕,之前有工作室的学长考某某大学,所以刚开始我的目标就很明确,某某大学-计算机应用技术-学硕。考研更重要的是这段经历,我相信每个考研人都会有这样的感觉。寒假开始前我买了一本陈文灯的指南,基本没怎么看,可以说一直在睡觉。
寒假刚开始,因为课设是PHP,之前正好有写过的项目,直接拿过来改一改给魏老师了,他也没为难我。然后跟同学(江西)一起去了一趟哈尔滨,记得刚到哈尔滨的啥时候,江西的手机被冻关机了,开始还说苹果不行,后来走着走着我电话也关机了,第一次感受到了哈尔滨的寒冷。然后寒假回家,书基本没怎么看,但是也不知道从哪开始复习,只知道我要考研。
寒假返校后,我记得我去考研楼(现在属于创新学院,正在装修中)三楼占了个位置,这是我第二次来考研楼,第一次是上一届考研结束的那天晚上,我跟江西过来复习期末考试。英语买了于慧真题100套、数学买了李永乐全套(其实没怎么看),然后每天除了上课就去考研楼看看书,其实效率很低。其实主要看数学这块,看张宇的视频记笔记。但是暑假都开始了,我高数刚看完、线代看了一点点,概率论完全没看,我当时很着急,觉得完了,他们都看得那么多(其实这就是我后来数学没考好的重要原因之一),然后专业课C语言看了一遍,觉得有些细节部分,之前没怎么注意。
暑假刚开始的时候,我就在考研楼二楼占了一个小屋子,两张桌子。暑假除了吃饭、睡觉、就是在那个屋子里面待着。在这给后来人一些建议,如果你要考研,就要考虑一下,你的感情是不是稳定的。在这个期间你的压力是很大的,会经常出现一些不开心的时候,如果你的另一半能体谅你,陪你一起奋斗,那是没有问题,身边就有这种成功的例子。如果你的感情还不稳定,会经常吵架,甚至动不动还会分手,那就早早分开好了!
我的英语很差的,我觉得没有人会比我的差,我考了6次四级,都是400分多一点,曾经跟朋友开玩笑说我的四级成绩可以当服务器错误代码了。最后一次通过是因为考研时复习了,除了于慧100套,还有就是何凯文的公众号,每天晚上都会有推送,事实上最后那100篇,我只研读了50篇不到,考研英语成绩和四六级真的没多少关系。
暑假结束,大概数学第一遍看完了。也开始了专业课复习,买了学长的专业课真题,答案错误的太多,差不多每个题我都会做完发到博客上,10月份开始陆陆续续看了点政治,买了肖秀荣全套。总体来说分配给专业课、政治的时间有点多,这也是我数学成绩差的一个重要原因。
从8月中旬开始一直到考研结束我去过最远的地方是考研报名那个地方,报名的时候我记得是和盟哥一起去的,当时怕去晚了要排队,去的很早,那天雪下的很大,去的时候打车去的,比较偏僻的一个地方,回来的时候坐公交回来的,车上都是去报名的学生,那个时候大家都一样,对未来的结果很憧憬也很怕。中间参加了一次同学聚会,然后在我的记忆里就没出过校门,没做过地铁。考研楼-食堂-寝室,晚上会到2楼的自习室看书,最早凌晨回寝室,晚点可能要凌晨2、3点了。那段时间真的快要扛不住了,感觉还有好多东西不会,越复习感觉希望越渺茫,但是还是坚持了下来,这段时间要感谢珊珊的鼓励、感谢盟哥的陪伴、感谢室友的支持理解。
除了上面说了两个原因,我觉得数学没考好的原因还有就是套题做的不够多,考试前就做了4、5套按照考试时间做的题,然后张宇的题很难,也都做的不怎么样。
快考试的前20天,开始背政治,肖四,每天晚上会到一楼走廊的那个拐角的那个位置背,很冷。大概每天晚上背完政治,看完何凯文的每日一句,在回寝室。那种感觉真的很难用语言去描述,有的时候,我跟室友大概两三天都见不着面,早上他还没醒我就去考研楼了,晚上都是凌晨以后我才回来,回来的时候他已经睡着了。
之前就定了考研的房间,很贵800块住两晚,12月22日 21:49从考研楼出来我发了一条朋友圈。
然后第二天上午,看了会书,和盟哥一起坐大巴车去考场,走的时候。我记得在桌子上留了一个纸条,写的是不管结果如何,都是我人生的一部分,考完试我坦然的面对任何结果!其实结果并不是这样的。去的路上跟之前一样晕车了,没吃晕车药,我怕吃了就背不了题了。盟哥给了我一个苹果,坚持到了酒店,很破,就是小旅馆的水平。
第二天上考场一切很顺利,政治、英语发挥的都很正常。晚上回酒店,感觉很多公式都忘了,背了背,考数学题跟我想象的不太一样,彻底慌了,最后15分钟,根本就写不下去,有的不是不会,我当时觉得完了,没戏了!
中午回来,盟哥在考场那等我,我们都问了对方一句,下午还去吗?我说不想吃饭了,给我妈打了电话说没有希望了。盟哥买了两个苹果,到了酒店躺一会,吃了苹果,退了房间下午去考场,很冷在外面等着。专业课考完了,收完卷,盟哥还有江西坐在我后面,我跟他们说我不甘心,因为专业课发挥的很好,考的虽然难,但是我都会。
找到了回学校的大巴车,背着沉重的书包,那个时候天已经黑了,同样是晕车,我跑到了司机旁边的座位,望着窗外,心里很难受,我永远忘不了那种感觉。下车整个人都不行了,吐了一会,盟哥把我扶上楼,回到寝室,我觉得自己好失败,真的好难受那时候。盟哥买了春饼,室友带了吃的,我吃了一些。后来到放假前基本就是看了一些PHP、Mysql一些比较深入的东西。
2月13号,晚上坐飞机去北京找工作,约了很多家,大概上午一家下午一家。小姑父开车送的我,去的路上,车还碰了一下,刚换的新车,也挺不好意思的。在北京待了三天收到了三个offer,心里还是挺高兴的,期间要特别感谢锡文帮我解决了住宿问题。15号查成绩的时候数学比预想的好一点,其他三门跟想象的差不多,我觉得有希望调剂。拒绝了offer,晚上坐火车回沈阳。。。
然后就是调剂,这绝对是一个痛苦的事情,连续几天就是打电话,问调剂的事情,上网查资料。联系了某很强的211学校,老师表示特别愿意要我,聊得也非常好,短信、邮件沟通了好久。我在网上找了复试的资料,看了一个月。期间除了看调剂群,就是复习复试。调剂群里,真的什么样的同学都有,我觉得每一个考研的同学,在考研前都应该看看上一届的调剂群。有的时候真的是选择大于努力,考研不是一个你努力就可以成功的事情,尤其计算机400多分被刷下来的也有很多。那段日子每天都像赌博一般,生怕错过群里一条有用的信息。
后来准备复试的那个学校老师跟我说,竞争很大,但是可以试一试。也联系了上海的一所普本,还有一所普通的211学校,期间也有其他学校让我填调剂系统,因为不太能接受,都没有填。后来调剂系统开放那天晚上,在电脑前守到了凌晨1点,从12点开始崩溃,然后一直刷,眼睛都不敢离开屏幕。最后事实证明我是对的,填的越早收到复试的可能性越大,有比我分还高的填同一个学校没有收到复试通知。我填了强211、普通211、上海普本,真的跟赌博一样。然后睡觉去了。第二天看到调剂群里很多人都接到了复试通知,我的心开始慌了。一直等到晚上,强211学硕名额为0,专硕少量,本科985,分数高的学生一大批都在盯着,上海普本告诉我一共六个名额,大佬很多,还有本校保护,普通211没有音讯,况且这三个学校48小时之内不能动,但是过了48小时基本就没什么学校了。当时的心情真的难以描述!我吃晚饭的时候收到了普通211的复试通知,心里好像有点底了,其他两个学校后来拒绝我,我改填了别的学校保底。
然后就是复试,笔试是之前初试考过的没什么问题,面试抽的三道题有我准备强211复试的内容也没问题,英语面试我写的自我介绍啥的小蔓蔓帮我改过了,非常感谢,很顺利的通过了。复试完事第二天发了拟录取通知,接受了,我的考研之路也就结束了。
首先要特别感谢恩师孟老师,让我在大学找到了自己的兴趣所在,也为我提供了非常好的实践平台,在考研调剂之路给予我特别大的帮助和支持!
其次要感谢那些帮助支持我的人,就不一一点名了。
最后送给大家两句话:
1.选择和方向永远比努力更重要!
2.相信自己、相信奇迹、不到最后一刻千万不能放弃!}

我要回帖

更多关于 卷积定理 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信