純numpy卷積神經(jīng)網(wǎng)絡(luò)實(shí)現(xiàn)手寫數(shù)字識(shí)別的實(shí)踐_第1頁(yè)
純numpy卷積神經(jīng)網(wǎng)絡(luò)實(shí)現(xiàn)手寫數(shù)字識(shí)別的實(shí)踐_第2頁(yè)
純numpy卷積神經(jīng)網(wǎng)絡(luò)實(shí)現(xiàn)手寫數(shù)字識(shí)別的實(shí)踐_第3頁(yè)
純numpy卷積神經(jīng)網(wǎng)絡(luò)實(shí)現(xiàn)手寫數(shù)字識(shí)別的實(shí)踐_第4頁(yè)
純numpy卷積神經(jīng)網(wǎng)絡(luò)實(shí)現(xiàn)手寫數(shù)字識(shí)別的實(shí)踐_第5頁(yè)
已閱讀5頁(yè),還剩5頁(yè)未讀, 繼續(xù)免費(fèi)閱讀

下載本文檔

版權(quán)說(shuō)明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請(qǐng)進(jìn)行舉報(bào)或認(rèn)領(lǐng)

文檔簡(jiǎn)介

第純numpy卷積神經(jīng)網(wǎng)絡(luò)實(shí)現(xiàn)手寫數(shù)字識(shí)別的實(shí)踐out_w=(W+2*pad-filter_w)//stride+1

col=col.reshape(N,out_h,out_w,C,filter_h,filter_w).transpose(0,3,4,5,1,2)

img=np.zeros((N,C,H+2*pad+stride-1,W+2*pad+stride-1))

foryinrange(filter_h):

y_max=y+stride*out_h

forxinrange(filter_w):

x_max=x+stride*out_w

img[:,:,y:y_max:stride,x:x_max:stride]+=col[:,:,y,x,:,:]

returnimg[:,:,pad:H+pad,pad:W+pad]

classRelu:

def__init__(self):

self.mask=None

defforward(self,x):

self.mask=(x=0)

out=x.copy()

out[self.mask]=0

returnout

defbackward(self,dout):

dout[self.mask]=0

dx=dout

returndx

defsoftmax(x):

ifx.ndim==2:

x=x.T

x=x-np.max(x,axis=0)

y=np.exp(x)/np.sum(np.exp(x),axis=0)

returny.T

x=x-np.max(x)#溢出對(duì)策

returnnp.exp(x)/np.sum(np.exp(x))

defcross_entropy_error(y,t):

ify.ndim==1:

t=t.reshape(1,t.size)

y=y.reshape(1,y.size)

#監(jiān)督數(shù)據(jù)是one-hot-vector的情況下,轉(zhuǎn)換為正確解標(biāo)簽的索引

ift.size==y.size:

t=t.argmax(axis=1)

batch_size=y.shape[0]

return-np.sum(np.log(y[np.arange(batch_size),t]+1e-7))/batch_size

classSoftmaxWithLoss:

def__init__(self):

self.loss=None

self.y=None#softmax的輸出

self.t=None#監(jiān)督數(shù)據(jù)

defforward(self,x,t):

self.t=t

self.y=softmax(x)

self.loss=cross_entropy_error(self.y,self.t)

returnself.loss

defbackward(self,dout=1):

batch_size=self.t.shape[0]

ifself.t.size==self.y.size:#監(jiān)督數(shù)據(jù)是one-hot-vector的情況

dx=(self.y-self.t)/batch_size

else:

dx=self.y.copy()

dx[np.arange(batch_size),self.t]-=1

dx=dx/batch_size

returndx

#Affine層的實(shí)現(xiàn)

classAffine:

def__init__(self,W,b):

self.W=W

self.b=b

self.x=None

self.dW=None

self.db=None

self.original_x_shape=None

defforward(self,x):

#對(duì)于卷積層需要把數(shù)據(jù)先展平

self.original_x_shape=x.shape

x=x.reshape(x.shape[0],-1)

self.x=x

out=np.dot(x,self.W)+self.b

returnout

defbackward(self,dout):

dx=np.dot(dout,self.W.T)

self.dW=np.dot(self.x.T,dout)

self.db=np.sum(dout,axis=0)

#還原輸入數(shù)據(jù)的形狀(對(duì)應(yīng)張量)

dx=dx.reshape(*self.original_x_shape)

returndx

#卷積層的實(shí)現(xiàn)

classConvolution:

def__init__(self,W,b,stride=1,pad=0):

self.W=W

self.b=b

self.stride=stride

self.pad=pad

#中間數(shù)據(jù)(backward時(shí)使用)

self.x=None

self.col=None

self.col_W=None

#權(quán)重和偏置參數(shù)的梯度

self.dW=None

self.db=None

defforward(self,x):

#濾波器的數(shù)目、通道數(shù)、高、寬

FN,C,FH,FW=self.W.shape

#輸入數(shù)據(jù)的數(shù)目、通道數(shù)、高、寬

N,C,H,W=x.shape

#輸出特征圖的高、寬

out_h=int(1+(H+2*self.pad-FH)/self.stride)

out_w=int(1+(W+2*self.pad-FW)/self.stride)

#輸入數(shù)據(jù)使用im2col展開(kāi)

col=im2col(x,FH,FW,self.stride,self.pad)

#濾波器的展開(kāi)

col_W=self.W.reshape(FN,-1).T

out=np.dot(col,col_W)+self.b

#變換輸出數(shù)據(jù)的形狀

#(N,h,w,C)-(N,c,h,w)

out=out.reshape(N,out_h,out_w,-1).transpose(0,3,1,2)

self.x=x

self.col=col

self.col_W=col_W

returnout

defbackward(self,dout):

FN,C,FH,FW=self.W.shape

dout=dout.transpose(0,2,3,1).reshape(-1,FN)

self.db=np.sum(dout,axis=0)

self.dW=np.dot(self.col.T,dout)

self.dW=self.dW.transpose(1,0).reshape(FN,C,FH,FW)

dcol=np.dot(dout,self.col_W.T)

dx=col2im(dcol,self.x.shape,FH,FW,self.stride,self.pad)

returndx

#池化層的實(shí)現(xiàn)

classPooling:

def__init__(self,pool_h,pool_w,stride=1,pad=0):

self.pool_h=pool_h

self.pool_w=pool_w

self.stride=stride

self.pad=pad

self.x=None

self.arg_max=None

defforward(self,x):

#輸入數(shù)據(jù)的數(shù)目、通道數(shù)、高、寬

N,C,H,W=x.shape

#輸出數(shù)據(jù)的高、寬

out_h=int(1+(H-self.pool_h)/self.stride)

out_w=int(1+(W-self.pool_w)/self.stride)

col=im2col(x,self.pool_h,self.pool_w,self.stride,self.pad)

col=col.reshape(-1,self.pool_h*self.pool_w)

#最大值

arg_max=np.argmax(col,axis=1)

out=np.max(col,axis=1)

out=out.reshape(N,out_h,out_w,C).transpose(0,3,1,2)

self.x=x

self.arg_max=arg_max

returnout

defbackward(self,dout):

dout=dout.transpose(0,2,3,1)

pool_size=self.pool_h*self.pool_w

dmax=np.zeros((dout.size,pool_size))

dmax[np.arange(self.arg_max.size),self.arg_max.flatten()]=dout.flatten()

dmax=dmax.reshape(dout.shape+(pool_size,))

dcol=dmax.reshape(dmax.shape[0]*dmax.shape[1]*dmax.shape[2],-1)

dx=col2im(dcol,self.x.shape,self.pool_h,self.pool_w,self.stride,self.pad)

returndx

#SimpleNet

classSimpleConvNet:

def__init__(self,input_dim=(1,28,28),

conv_param={'filter_num':30,'filter_size':5,'pad':0,'stride':1},

hidden_size=100,

output_size=10,

weight_init_std=0.01):

filter_num=conv_param['filter_num']#30

filter_size=conv_param['filter_size']#5

filter_pad=conv_param['pad']#0

filter_stride=conv_param['stride']#1

input_size=input_dim[1]#28

conv_output_size=int((1+input_size+2*filter_pad-filter_size)/filter_stride)#24

#pool默認(rèn)的是2x2最大值池化池化層的大小變?yōu)榫矸e層的一半30*12*12=4320

pool_output_size=int(filter_num*(conv_output_size/2)*(conv_output_size/2))

#權(quán)重參數(shù)的初始化部分濾波器和偏置

self.params={}

#(30,1,5,5)

self.params['W1']=np.random.randn(filter_num,input_dim[0],filter_size,filter_size)*weight_init_std

#(30,)

self.params['b1']=np.zeros(filter_num)

#(4320,100)

self.params['W2']=np.random.randn(pool_output_size,hidden_size)*weight_init_std

#(100,)

self.params['b2']=np.zeros(hidden_size)

#(100,10)

self.params['W3']=np.random.randn(hidden_size,output_size)*weight_init_std

#(10,)

self.params['b3']=np.zeros(output_size)

#生成必要的層

self.layers=OrderedDict()

#(N,1,28,28)-(N,30,24,24)

self.layers['Conv1']=Convolution(self.params['W1'],self.params['b1'],conv_param['stride'],conv_param['pad'])

#(N,30,24,24)

self.layers['Relu1']=Relu()

#池化層的步幅大小和池化應(yīng)用區(qū)域大小相等

#(N,30,12,12)

self.layers['Pool1']=Pooling(pool_h=2,pool_w=2,stride=2)

#全連接層

#全連接層內(nèi)部有個(gè)判斷首先是把數(shù)據(jù)展平

#(N,30,12,12)-(N,4320)-(N,100)

self.layers['Affine1']=Affine(self.params['W2'],self.params['b2'])

#(N,100)

self.layers['Relu2']=Relu()

#(N,100)-(N,10)

self.layers['Affine2']=Affine(self.params['W3'],self.params['b3'])

self.last_layer=SoftmaxWithLoss()

defpredict(self,x):

forlayerinself.layers.values():

x=layer.forward(x)

returnx

defloss(self,x,t):

y=self.predict(x)

returnself.last_layer.forward(y,t)

defgradient(self,x,t):

#forward

self.loss(x,t)

#backward

dout=1

dout=self.last_layer.backward(dout)

layers=list(self.layers.values())

layers.reverse()

forlayerinlayers:

dout=layer.backward(dout)

grads={}

grads['W1']=self.layers['Conv1'].dW

grads['b1']=self.layers['Conv1'].db

grads['W2']=self.layers['Affine1'].dW

grads['b2']=self.layers['Affine1'].db

grads['W3']=self.layers['Affine2'].dW

grads['b3']=self.layers['A

溫馨提示

  • 1. 本站所有資源如無(wú)特殊說(shuō)明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請(qǐng)下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請(qǐng)聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁(yè)內(nèi)容里面會(huì)有圖紙預(yù)覽,若沒(méi)有圖紙預(yù)覽就沒(méi)有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫(kù)網(wǎng)僅提供信息存儲(chǔ)空間,僅對(duì)用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對(duì)用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對(duì)任何下載內(nèi)容負(fù)責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請(qǐng)與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對(duì)自己和他人造成任何形式的傷害或損失。

最新文檔

評(píng)論

0/150

提交評(píng)論