CNN卷积神经网络初探:
这里有一些对多层感知机的概念的重新阐述,
多层感知的特点是一种层间全连接的神经网络,即在信息上是没有损失的。
多层感知的特点是一种层间全连接的神经网络,即在信息上是没有损失的。
卷积神经网络具有如下要讨论的一些特点。
Sparse Connectivity(指稀疏链接),即在设定神经网络的链接时,并不使用
所有数据,而是每个连接元仅仅使用一部分,整合后覆盖整个信息。
这种链接方式的一个特点是,由于有中间隐藏层的存在,在进行训练后,
可以通过隐藏层过滤掉若干不太重要的输入层变量。
所有数据,而是每个连接元仅仅使用一部分,整合后覆盖整个信息。
这种链接方式的一个特点是,由于有中间隐藏层的存在,在进行训练后,
可以通过隐藏层过滤掉若干不太重要的输入层变量。
这与Lasso回归是有相似的特性的,实际这种变量的稀疏化方法给了我一个
启示,Sparse Connectivity是通过训练模型使得对于总体改变较大的
部分变得显著从而起到稀疏化的作用,如果能够通过变量间的相关度量
找到具有代表性的exampler,利用examplers代替总体进行相应的训练
也可以得到稀疏性的结果,相应的算法可以使用AP(相似性传递)算法
完成。或者先利用这种(AP)聚类传递算法进行聚类重排,再对相同
的聚类簇的变量使用Sparse Connectivity进行连接 这样得到的训练模型
的稀疏过滤是具有指导性意义的。
启示,Sparse Connectivity是通过训练模型使得对于总体改变较大的
部分变得显著从而起到稀疏化的作用,如果能够通过变量间的相关度量
找到具有代表性的exampler,利用examplers代替总体进行相应的训练
也可以得到稀疏性的结果,相应的算法可以使用AP(相似性传递)算法
完成。或者先利用这种(AP)聚类传递算法进行聚类重排,再对相同
的聚类簇的变量使用Sparse Connectivity进行连接 这样得到的训练模型
的稀疏过滤是具有指导性意义的。
Shared Weights(输入层与隐藏层的的链接权重共享),这个特点可以利用
限制减少训练参数,减少训练参数有助于算法收敛,这对于卷积神经网络
这种多层模型具有很大的加快作用。
限制减少训练参数,减少训练参数有助于算法收敛,这对于卷积神经网络
这种多层模型具有很大的加快作用。
下面要讨论一些有关卷积的细节,
从概率的角度,卷积的一个直观应用是总体随机变量求和的分布是独立个体
分布的卷积,从数学表达式上来说是一个概率分布利用另一个概率分布为权
重的加权概率平均。从逆向来看是将二者对于某样本的概率分解为若干概率
乘积的和,概率意义是明显的。
从概率的角度,卷积的一个直观应用是总体随机变量求和的分布是独立个体
分布的卷积,从数学表达式上来说是一个概率分布利用另一个概率分布为权
重的加权概率平均。从逆向来看是将二者对于某样本的概率分解为若干概率
乘积的和,概率意义是明显的。
所以卷积的直接意义就是描述一个总体“能量”,这个“能量”可以抽象为
若干个个体“能量”乘积的“和”。也就是“能量”的合成。
若干个个体“能量”乘积的“和”。也就是“能量”的合成。
卷积的例子:
a = [0, 1, 2]
b = [2, 1, 0]
a = [0, 1, 2]
b = [2, 1, 0]
a * b[0] = a[0] * b[0 - 0] = 0
a * b[1] = a[0] * b[1 - 0] + a[1] * b[1 - 1] = 0 + 2 = 2
a * b[2] = a[0] * b[2 - 0] + a[1] * b[2 - 1] + a[2] * b[2 - 2] = 0 + 1 + 4 = 5
a * b[3] = a[1] * b[3 - 1] + a[2] * b[3 - 2] = 0 + 2 = 2
a * b[4] = a[2] * b[4 - 2] = 0
a * b[1] = a[0] * b[1 - 0] + a[1] * b[1 - 1] = 0 + 2 = 2
a * b[2] = a[0] * b[2 - 0] + a[1] * b[2 - 1] + a[2] * b[2 - 2] = 0 + 1 + 4 = 5
a * b[3] = a[1] * b[3 - 1] + a[2] * b[3 - 2] = 0 + 2 = 2
a * b[4] = a[2] * b[4 - 2] = 0
这一部分主要讨论概念,一些具体的例子之后再给出。
后面会对一些例子进行比较详尽的讨论。
后面会对一些例子进行比较详尽的讨论。
一些theano 符号变量(数组变量)具备dimshuffle方法,
其作用是进行增加维度,如 b.dimshuffle('x', 0, 'x', 'x')
相当于在原来b的左侧增加一个维度,在右侧增加两个维度。
左侧是指在整体范围,右侧是指在element范围。
其作用是进行增加维度,如 b.dimshuffle('x', 0, 'x', 'x')
相当于在原来b的左侧增加一个维度,在右侧增加两个维度。
左侧是指在整体范围,右侧是指在element范围。
使用dimshuffle时要注意的是,shared valuable需要使用numpy.ndarray
进行初始化后才能使用,而并不会自动实现转型,其原因也是明显的,
共享变量并不仅仅针对ndarray,而是具备更多使用的情况,例如一般的类。
进行初始化后才能使用,而并不会自动实现转型,其原因也是明显的,
共享变量并不仅仅针对ndarray,而是具备更多使用的情况,例如一般的类。
在进行卷积运算时要注意卷积具有交换律。
像共享变量,由于theano的内存运行环境与python脚本运行环境相独立,
当对共享变量调用eval方法时是比较消耗时间的。
当对共享变量调用eval方法时是比较消耗时间的。
利用Image.open取出图片对象后,可以使用size属性查看图片的宽度及高度。
这里调用了pylab库,该库可以视为matplotlib库的简化接口库,
pylab.axis('off')将输出的视图范围设定为[xmin, xmax, ymin, ymax]
pylab.axis('off')将输出的视图范围设定为[xmin, xmax, ymin, ymax]
下面图中输出的过滤后数组格式为,filtered_img[0,0,:,:]
filtered_img[0,1,:,:]
filtered_img[0,1,:,:]
下面是一种随机数进行卷积的后施加S形曲线变换后的代码:
from __future__ import division
import theano
from theano import tensor as T
from theano.tensor.nnet import conv
import numpy
rng = numpy.random.RandomState(23455)
input = T.tensor4(name = 'input')
w_shp = (2, 3, 9, 9)
w_bound = numpy.sqrt(3*9*9)
W = theano.shared(numpy.asarray(rng.uniform(low = -1.0 / w_bound, high = 1.0 / w_bound, size = w_shp), dtype = input.dtype),
name = 'W')
b_shp = (2,)
b = theano.shared(numpy.asarray(rng.uniform(low = -.5, high = .5, size = b_shp), dtype = input.dtype), name = 'b')
conv_out = conv.conv2d(input, W)
output = T.nnet.sigmoid(conv_out + b.dimshuffle('x', 0, 'x', 'x'))
f = theano.function([input], output)
import numpy
import pylab
from PIL import Image
img = Image.open("3wolfmoon.jpg")
img = numpy.asarray(img, dtype = 'float64') / 256.
img_ = img.transpose(2, 0, 1).reshape(1, 3, 639, 516)
filtered_img = f(img_)
pylab.subplot(1,4,1)
pylab.axis('off')
pylab.imshow(img)
pylab.gray()
pylab.subplot(1,4,2)
pylab.axis('off')
pylab.imshow(filtered_img[0,0,:,:])
pylab.subplot(1,4,3)
pylab.axis('off')
pylab.imshow(filtered_img[0,1,:,:])
pylab.subplot(1,4,4)
pylab.axis("off")
copy_array = filtered_img[0,1,:,:].copy()
mean_value = numpy.mean(copy_array)
print "shape :"
print filtered_img.shape
for x in numpy.nditer(copy_array, op_flags = ['readwrite']):
if x < mean_value:
x[...] = 0
pylab.imshow(copy_array)
pylab.show()
从图上可以看到随机设定的卷积非线性运算的变换效果基本上就是刻画边界,
特别地,对于使用均值进行过滤的最后一个版本表现是明显的。
从而可以看到在图像分割变换(或等价地特征提取上)非线性卷积变换的重要性。
特别地,对于使用均值进行过滤的最后一个版本表现是明显的。
从而可以看到在图像分割变换(或等价地特征提取上)非线性卷积变换的重要性。
这里要指出的是,进行卷积运算的基本函数(非代码中的theano表达式)
一维卷积定义在numpy中的convolve
二维卷积定义在scipy.signal中的convolve2d
一般"full"卷积在一个维数上的维数是M + N - 1(image_shape + filter_shape -1)
而conv.convolve2d所使用的卷积是默认"valid"的形式
output of shape: image_shape - filter_shape + 1
一维卷积定义在numpy中的convolve
二维卷积定义在scipy.signal中的convolve2d
一般"full"卷积在一个维数上的维数是M + N - 1(image_shape + filter_shape -1)
而conv.convolve2d所使用的卷积是默认"valid"的形式
output of shape: image_shape - filter_shape + 1
有关卷积,在scipy-ref文档中有比较详尽的论述,
下面的叙述针对signal.convolve进行
一般(在一维卷积的默认情况)使用的是"full"版本,即将全部元素进行使用
还有两种其它版本,"same"相当与将卷积后的序列中间的与第一个输入序列一样
长的部分序列进行输出。
"valid"指卷积运算需要包含进行滤波(filter)的全部数组的那部分
卷积序列,具有shape image_shape - filter_shape + 1
下面的叙述针对signal.convolve进行
一般(在一维卷积的默认情况)使用的是"full"版本,即将全部元素进行使用
还有两种其它版本,"same"相当与将卷积后的序列中间的与第一个输入序列一样
长的部分序列进行输出。
"valid"指卷积运算需要包含进行滤波(filter)的全部数组的那部分
卷积序列,具有shape image_shape - filter_shape + 1
从上面的讨论中可以得知,conv2d实现的是将对应tensor4最后两个维度(图片的高度及宽度)
进行“适当”的随机数线性卷积滤波,再映射到S曲线上,而对于前两个维度,
nnet.conv.conv2d实现的是signal.conv2d与神经网络连接变换的组合接口,
前两个接口对应的就是神经网络连接变换的接口,具体如下:
进行“适当”的随机数线性卷积滤波,再映射到S曲线上,而对于前两个维度,
nnet.conv.conv2d实现的是signal.conv2d与神经网络连接变换的组合接口,
前两个接口对应的就是神经网络连接变换的接口,具体如下:
conv.conv2d(input,filter)
input [mini-batch size,特征图的数量,图像高度,图像宽度]
filter [m层特征图数量,m-1层特征图数量,过滤器高度,过滤器宽度]
input [mini-batch size,特征图的数量,图像高度,图像宽度]
filter [m层特征图数量,m-1层特征图数量,过滤器高度,过滤器宽度]
所谓特征图指feature map,见前面的讨论Shared Weights
输出output[mini-batch size, m层特征图数量, 卷积输出高度, 卷积输出宽度]
相当于卷积变换后的输出。
相当于卷积变换后的输出。
在卷积神经网络的使用中一般还结合MaxPooling方法,使用该方法的动机是,
减少多层的计算量及提高不同初值变换的不变性。
其具体做法是,将像素数组分割为若干不想交的矩形,对每个矩形求最大值。
可以看到第一个动机是明显可以满足的,对于提高不变性的目的,其一个例证是,
使用2*2 MaxPooling可使得3/8的输出是相同的,使用3*3 MaxPooling可使得5/8
的输出是相同的。
减少多层的计算量及提高不同初值变换的不变性。
其具体做法是,将像素数组分割为若干不想交的矩形,对每个矩形求最大值。
可以看到第一个动机是明显可以满足的,对于提高不变性的目的,其一个例证是,
使用2*2 MaxPooling可使得3/8的输出是相同的,使用3*3 MaxPooling可使得5/8
的输出是相同的。