Created
March 6, 2020 19:36
-
-
Save aiwithshekhar/dbae0dd5f7988c0b337b608544f53252 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
class Convolution(Conv_Module): | |
def forward(self, img, ker): | |
self.out_h= int((self.img_h-self.ker_h)+(2*self.pad)/self.stride) +1 #output height with same padding(10). | |
self.out_w= int((self.img_w-self.ker_w)+(2*self.pad)/self.stride) +1 #output width with same padding(10). | |
pad_img=np.pad(img, ((0,0),(0,0),(1,1),(1,1)),mode='constant') #pad the input images with zeros around | |
i0=np.repeat(np.arange(self.ker_h), self.ker_h) | |
i1=np.repeat(np.arange(self.img_h), self.img_h) | |
j0=np.tile(np.arange(self.ker_w), self.ker_h) | |
j1=np.tile(np.arange(self.img_h), self.img_w) | |
self.i=i0.reshape(-1,1)+i1.reshape(1,-1) | |
self.j=j0.reshape(-1,1)+j1.reshape(1,-1) | |
self.k=np.repeat(np.arange(self.img_d), self.ker_h*self.ker_w).reshape(-1,1) | |
self.select_img=pad_img[:,:,self.i,self.j].squeeze() #receptive feild pixels are selected based on the index***[1,9,100] reshaped to [9,100] | |
weights=ker.reshape(self.ker_h*self.ker_w, -1) # weights reshaped to [9,1] | |
convolve=weights.transpose()@self.select_img # convolution operation [1,9]*[9,100] ----> [1,100] | |
convolve=convolve.reshape(1,1,10,10) # reshaped in image dimension [1,1,10,10] | |
return convolve | |
def bwd(self, out): | |
out_h= self.img_h + 2 * self.pad #output height with padding(12) | |
out_w= self.img_w + 2 * self.pad #output width with padding(12) | |
db=np.sum(out, axis=(0,2,3)) #bias gradient calculation | |
db=db.reshape(self.ker_b, -1) | |
out_reshape=out.squeeze().reshape(self.ker_b, -1) #[1,100] | |
dw=out_reshape @ self.select_img.T #[1,100] * [100,9]---->[1,9] | |
dw=dw.reshape(ker.shape) #weight gradient caculation | |
ker_reshape=self.ker.reshape(self.ker_b, -1) | |
X= ker_reshape.T @ out_reshape # gradient calculation w.r.t input image | |
#[9,1]*[1,100]----->[9,100] | |
padded=np.zeros((self.img_b, self.img_d, out_h, out_w), dtype=X.dtype) #empty padded array | |
X_reshaped=X.reshape(self.ker_h*self.ker_w, -1, self.ker_b) #[9,100,1] | |
X_reshaped=X_reshaped.transpose(2,0,1) #reshapin [1,9,100] | |
np.add.at(padded, (slice(None), self.k, self.i, self.j), X_reshaped) #gradient are stored in the corresponding locations | |
dX=padded[:,:,self.pad:-self.pad, self.pad:-self.pad] #input image gradient | |
return dX, dw, db |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment