python三维卷积可以用什么函数? matlab只要用convn

Python016

python三维卷积可以用什么函数? matlab只要用convn,第1张

写了一个输入和卷积核dim=2是一样的(都是3)的卷积函数,可以试试多加一个for循环变成三维卷积

def conv3D(image, filter):

'''

三维卷积

:param image: 输入,shape为 [h,w,c], c=3

:param filter:  卷积核,shape为 [x,y,z], z=3

:return:

'''

h, w, c = image.shape

x, y, z = filter.shape

height_new = h - x + 1  # 输出 h

width_new = w - y + 1  # 输出 w

image_new = np.zeros((height_new, width_new), dtype=np.float)

for i in range(height_new):

for j in range(width_new):

r = np.sum(image[i:i+x, j:j+x, 0] * filter[:,:,0])

g = np.sum(image[i:i+y, j:j+y, 1] * filter[:,:,1])

b = np.sum(image[i:i+z, j:j+z, 2] * filter[:,:,2])

image_new[i, j] = np.sum([r,g,b])

image_new = image_new.clip(0, 255)

image_new = np.rint(image_new).astype('uint8')

return image_new

用keras框架较为方便

首先安装anaconda,然后通过pip安装keras

以下转自wphh的博客。

#coding:utf-8

'''

    GPU run command:

        THEANO_FLAGS=mode=FAST_RUN,device=gpu,floatX=float32 python cnn.py

    CPU run command:

        python cnn.py

2016.06.06更新:

这份代码是keras开发初期写的,当时keras还没有现在这么流行,文档也还没那么丰富,所以我当时写了一些简单的教程。

现在keras的API也发生了一些的变化,建议及推荐直接上keras.io看更加详细的教程。

'''

#导入各种用到的模块组件

from __future__ import absolute_import

from __future__ import print_function

from keras.preprocessing.image import ImageDataGenerator

from keras.models import Sequential

from keras.layers.core import Dense, Dropout, Activation, Flatten

from keras.layers.advanced_activations import PReLU

from keras.layers.convolutional import Convolution2D, MaxPooling2D

from keras.optimizers import SGD, Adadelta, Adagrad

from keras.utils import np_utils, generic_utils

from six.moves import range

from data import load_data

import random

import numpy as np

np.random.seed(1024)  # for reproducibility

#加载数据

data, label = load_data()

#打乱数据

index = [i for i in range(len(data))]

random.shuffle(index)

data = data[index]

label = label[index]

print(data.shape[0], ' samples')

#label为0~9共10个类别,keras要求格式为binary class matrices,转化一下,直接调用keras提供的这个函数

label = np_utils.to_categorical(label, 10)

###############

#开始建立CNN模型

###############

#生成一个model

model = Sequential()

#第一个卷积层,4个卷积核,每个卷积核大小5*5。1表示输入的图片的通道,灰度图为1通道。

#border_mode可以是valid或者full,具体看这里说明:http://deeplearning.net/software/theano/library/tensor/nnet/conv.html#theano.tensor.nnet.conv.conv2d

#激活函数用tanh

#你还可以在model.add(Activation('tanh'))后加上dropout的技巧: model.add(Dropout(0.5))

model.add(Convolution2D(4, 5, 5, border_mode='valid',input_shape=(1,28,28))) 

model.add(Activation('tanh'))

#第二个卷积层,8个卷积核,每个卷积核大小3*3。4表示输入的特征图个数,等于上一层的卷积核个数

#激活函数用tanh

#采用maxpooling,poolsize为(2,2)

model.add(Convolution2D(8, 3, 3, border_mode='valid'))

model.add(Activation('tanh'))

model.add(MaxPooling2D(pool_size=(2, 2)))

#第三个卷积层,16个卷积核,每个卷积核大小3*3

#激活函数用tanh

#采用maxpooling,poolsize为(2,2)

model.add(Convolution2D(16, 3, 3, border_mode='valid')) 

model.add(Activation('relu'))

model.add(MaxPooling2D(pool_size=(2, 2)))

#全连接层,先将前一层输出的二维特征图flatten为一维的。

#Dense就是隐藏层。16就是上一层输出的特征图个数。4是根据每个卷积层计算出来的:(28-5+1)得到24,(24-3+1)/2得到11,(11-3+1)/2得到4

#全连接有128个神经元节点,初始化方式为normal

model.add(Flatten())

model.add(Dense(128, init='normal'))

model.add(Activation('tanh'))

#Softmax分类,输出是10类别

model.add(Dense(10, init='normal'))

model.add(Activation('softmax'))

#############

#开始训练模型

##############

#使用SGD + momentum

#model.compile里的参数loss就是损失函数(目标函数)

sgd = SGD(lr=0.05, decay=1e-6, momentum=0.9, nesterov=True)

model.compile(loss='categorical_crossentropy', optimizer=sgd,metrics=["accuracy"])

#调用fit方法,就是一个训练过程. 训练的epoch数设为10,batch_size为100.

#数据经过随机打乱shuffle=True。verbose=1,训练过程中输出的信息,0、1、2三种方式都可以,无关紧要。show_accuracy=True,训练时每一个epoch都输出accuracy。

#validation_split=0.2,将20%的数据作为验证集。

model.fit(data, label, batch_size=100, nb_epoch=10,shuffle=True,verbose=1,validation_split=0.2)

"""

#使用data augmentation的方法

#一些参数和调用的方法,请看文档

datagen = ImageDataGenerator(

        featurewise_center=True, # set input mean to 0 over the dataset

        samplewise_center=False, # set each sample mean to 0

        featurewise_std_normalization=True, # divide inputs by std of the dataset

        samplewise_std_normalization=False, # divide each input by its std

        zca_whitening=False, # apply ZCA whitening

        rotation_range=20, # randomly rotate images in the range (degrees, 0 to 180)

        width_shift_range=0.2, # randomly shift images horizontally (fraction of total width)

        height_shift_range=0.2, # randomly shift images vertically (fraction of total height)

        horizontal_flip=True, # randomly flip images

        vertical_flip=False) # randomly flip images

# compute quantities required for featurewise normalization 

# (std, mean, and principal components if ZCA whitening is applied)

datagen.fit(data)

for e in range(nb_epoch):

    print('-'*40)

    print('Epoch', e)

    print('-'*40)

    print("Training...")

    # batch train with realtime data augmentation

    progbar = generic_utils.Progbar(data.shape[0])

    for X_batch, Y_batch in datagen.flow(data, label):

        loss,accuracy = model.train(X_batch, Y_batch,accuracy=True)

        progbar.add(X_batch.shape[0], values=[("train loss", loss),("accuracy:", accuracy)] )

"""

上周末利用python简单实现了一个卷积神经网络,只包含一个卷积层和一个maxpooling层,pooling层后面的多层神经网络采用了softmax形式的输出。实验输入仍然采用MNIST图像使用10个feature map时,卷积和pooling的结果分别如下所示。

部分源码如下:

[python] view plain copy

#coding=utf-8

'''''

Created on 2014年11月30日

@author: Wangliaofan

'''

import numpy

import struct

import matplotlib.pyplot as plt

import math

import random

import copy

#test

from BasicMultilayerNeuralNetwork import BMNN2

def sigmoid(inX):

if 1.0+numpy.exp(-inX)== 0.0:

return 999999999.999999999

return 1.0/(1.0+numpy.exp(-inX))

def difsigmoid(inX):

return sigmoid(inX)*(1.0-sigmoid(inX))

def tangenth(inX):

return (1.0*math.exp(inX)-1.0*math.exp(-inX))/(1.0*math.exp(inX)+1.0*math.exp(-inX))

def cnn_conv(in_image, filter_map,B,type_func='sigmoid'):

#in_image[num,feature map,row,col]=>in_image[Irow,Icol]

#features map[k filter,row,col]

#type_func['sigmoid','tangenth']

#out_feature[k filter,Irow-row+1,Icol-col+1]

shape_image=numpy.shape(in_image)#[row,col]

#print "shape_image",shape_image

shape_filter=numpy.shape(filter_map)#[k filter,row,col]

if shape_filter[1]>shape_image[0] or shape_filter[2]>shape_image[1]:

raise Exception

shape_out=(shape_filter[0],shape_image[0]-shape_filter[1]+1,shape_image[1]-shape_filter[2]+1)

out_feature=numpy.zeros(shape_out)

k,m,n=numpy.shape(out_feature)

for k_idx in range(0,k):

#rotate 180 to calculate conv

c_filter=numpy.rot90(filter_map[k_idx,:,:], 2)

for r_idx in range(0,m):

for c_idx in range(0,n):

#conv_temp=numpy.zeros((shape_filter[1],shape_filter[2]))

conv_temp=numpy.dot(in_image[r_idx:r_idx+shape_filter[1],c_idx:c_idx+shape_filter[2]],c_filter)

sum_temp=numpy.sum(conv_temp)

if type_func=='sigmoid':

out_feature[k_idx,r_idx,c_idx]=sigmoid(sum_temp+B[k_idx])

elif type_func=='tangenth':

out_feature[k_idx,r_idx,c_idx]=tangenth(sum_temp+B[k_idx])

else:

raise Exception

return out_feature

def cnn_maxpooling(out_feature,pooling_size=2,type_pooling="max"):

k,row,col=numpy.shape(out_feature)

max_index_Matirx=numpy.zeros((k,row,col))

out_row=int(numpy.floor(row/pooling_size))

out_col=int(numpy.floor(col/pooling_size))

out_pooling=numpy.zeros((k,out_row,out_col))

for k_idx in range(0,k):

for r_idx in range(0,out_row):

for c_idx in range(0,out_col):

temp_matrix=out_feature[k_idx,pooling_size*r_idx:pooling_size*r_idx+pooling_size,pooling_size*c_idx:pooling_size*c_idx+pooling_size]

out_pooling[k_idx,r_idx,c_idx]=numpy.amax(temp_matrix)

max_index=numpy.argmax(temp_matrix)

#print max_index

#print max_index/pooling_size,max_index%pooling_size

max_index_Matirx[k_idx,pooling_size*r_idx+max_index/pooling_size,pooling_size*c_idx+max_index%pooling_size]=1

return out_pooling,max_index_Matirx

def poolwithfunc(in_pooling,W,B,type_func='sigmoid'):

k,row,col=numpy.shape(in_pooling)

out_pooling=numpy.zeros((k,row,col))

for k_idx in range(0,k):

for r_idx in range(0,row):

for c_idx in range(0,col):

out_pooling[k_idx,r_idx,c_idx]=sigmoid(W[k_idx]*in_pooling[k_idx,r_idx,c_idx]+B[k_idx])

return out_pooling

#out_feature is the out put of conv

def backErrorfromPoolToConv(theta,max_index_Matirx,out_feature,pooling_size=2):

k1,row,col=numpy.shape(out_feature)

error_conv=numpy.zeros((k1,row,col))

k2,theta_row,theta_col=numpy.shape(theta)

if k1!=k2:

raise Exception

for idx_k in range(0,k1):

for idx_row in range( 0, row):

for idx_col in range( 0, col):

error_conv[idx_k,idx_row,idx_col]=\

max_index_Matirx[idx_k,idx_row,idx_col]*\

float(theta[idx_k,idx_row/pooling_size,idx_col/pooling_size])*\

difsigmoid(out_feature[idx_k,idx_row,idx_col])

return error_conv

def backErrorfromConvToInput(theta,inputImage):

k1,row,col=numpy.shape(theta)

#print "theta",k1,row,col

i_row,i_col=numpy.shape(inputImage)

if row>i_row or col> i_col:

raise Exception

filter_row=i_row-row+1

filter_col=i_col-col+1

detaW=numpy.zeros((k1,filter_row,filter_col))

#the same with conv valid in matlab

for k_idx in range(0,k1):

for idx_row in range(0,filter_row):

for idx_col in range(0,filter_col):

subInputMatrix=inputImage[idx_row:idx_row+row,idx_col:idx_col+col]

#print "subInputMatrix",numpy.shape(subInputMatrix)

#rotate theta 180

#print numpy.shape(theta)

theta_rotate=numpy.rot90(theta[k_idx,:,:], 2)

#print "theta_rotate",theta_rotate

dotMatrix=numpy.dot(subInputMatrix,theta_rotate)

detaW[k_idx,idx_row,idx_col]=numpy.sum(dotMatrix)

detaB=numpy.zeros((k1,1))

for k_idx in range(0,k1):

detaB[k_idx]=numpy.sum(theta[k_idx,:,:])

return detaW,detaB

def loadMNISTimage(absFilePathandName,datanum=60000):

images=open(absFilePathandName,'rb')

buf=images.read()

index=0

magic, numImages , numRows , numColumns = struct.unpack_from('>IIII' , buf , index)

print magic, numImages , numRows , numColumns

index += struct.calcsize('>IIII')

if magic != 2051:

raise Exception

datasize=int(784*datanum)

datablock=">"+str(datasize)+"B"

#nextmatrix=struct.unpack_from('>47040000B' ,buf, index)

nextmatrix=struct.unpack_from(datablock ,buf, index)

nextmatrix=numpy.array(nextmatrix)/255.0

#nextmatrix=nextmatrix.reshape(numImages,numRows,numColumns)

#nextmatrix=nextmatrix.reshape(datanum,1,numRows*numColumns)

nextmatrix=nextmatrix.reshape(datanum,1,numRows,numColumns)

return nextmatrix, numImages

def loadMNISTlabels(absFilePathandName,datanum=60000):

labels=open(absFilePathandName,'rb')

buf=labels.read()

index=0

magic, numLabels  = struct.unpack_from('>II' , buf , index)

print magic, numLabels

index += struct.calcsize('>II')

if magic != 2049:

raise Exception

datablock=">"+str(datanum)+"B"

#nextmatrix=struct.unpack_from('>60000B' ,buf, index)

nextmatrix=struct.unpack_from(datablock ,buf, index)

nextmatrix=numpy.array(nextmatrix)

return nextmatrix, numLabels

def simpleCNN(numofFilter,filter_size,pooling_size=2,maxIter=1000,imageNum=500):

decayRate=0.01

MNISTimage,num1=loadMNISTimage("F:\Machine Learning\UFLDL\data\common\\train-images-idx3-ubyte",imageNum)

print num1

row,col=numpy.shape(MNISTimage[0,0,:,:])

out_Di=numofFilter*((row-filter_size+1)/pooling_size)*((col-filter_size+1)/pooling_size)

MLP=BMNN2.MuiltilayerANN(1,[128],out_Di,10,maxIter)

MLP.setTrainDataNum(imageNum)

MLP.loadtrainlabel("F:\Machine Learning\UFLDL\data\common\\train-labels-idx1-ubyte")

MLP.initialweights()

#MLP.printWeightMatrix()

rng = numpy.random.RandomState(23455)

W_shp = (numofFilter, filter_size, filter_size)

W_bound = numpy.sqrt(numofFilter * filter_size * filter_size)

W_k=rng.uniform(low=-1.0 / W_bound,high=1.0 / W_bound,size=W_shp)

B_shp = (numofFilter,)

B= numpy.asarray(rng.uniform(low=-.5, high=.5, size=B_shp))

cIter=0

while cIter<maxIter:

cIter += 1

ImageNum=random.randint(0,imageNum-1)

conv_out_map=cnn_conv(MNISTimage[ImageNum,0,:,:], W_k, B,"sigmoid")

out_pooling,max_index_Matrix=cnn_maxpooling(conv_out_map,2,"max")

pool_shape = numpy.shape(out_pooling)

MLP_input=out_pooling.reshape(1,1,out_Di)

#print numpy.shape(MLP_input)

DetaW,DetaB,temperror=MLP.backwardPropogation(MLP_input,ImageNum)

if cIter%50 ==0 :

print cIter,"Temp error: ",temperror

#print numpy.shape(MLP.Theta[MLP.Nl-2])

#print numpy.shape(MLP.Ztemp[0])

#print numpy.shape(MLP.weightMatrix[0])

theta_pool=MLP.Theta[MLP.Nl-2]*MLP.weightMatrix[0].transpose()

#print numpy.shape(theta_pool)

#print "theta_pool",theta_pool

temp=numpy.zeros((1,1,out_Di))

temp[0,:,:]=theta_pool

back_theta_pool=temp.reshape(pool_shape)

#print "back_theta_pool",numpy.shape(back_theta_pool)

#print "back_theta_pool",back_theta_pool

error_conv=backErrorfromPoolToConv(back_theta_pool,max_index_Matrix,conv_out_map,2)

#print "error_conv",numpy.shape(error_conv)

#print error_conv

conv_DetaW,conv_DetaB=backErrorfromConvToInput(error_conv,MNISTimage[ImageNum,0,:,:])

#print "W_k",W_k

#print "conv_DetaW",conv_DetaW