2023.03.07 - [분류 전체보기] - implement_CNN(pooling)
implement_CNN(pooling)
2023.03.07 - [분류 전체보기] - implement_CNN(start) implement_CNN(start) 시각 피질 안의 뉴런들이 작은 국부 수용장을 가진다. 이는 뉴런들이 시야의 일부 버위 안에 있는 시각 자극에만 반응한다는 뜻이다.
teach-meaning.tistory.com
입력 데이터와 동일한 크기의 합성곱을 수행하는 same_padding 구현
def same_padding_cnn(self, input, filter_size, filter_count):
# 입력 받은 필터의 개수만큼 반복
for i in range(filter_count):
# 필터 크기에 맞는 임의의 가중치 생성
weight = np.random.random(filter_size * filter_size).reshape(filter_size, filter_size)
self.cnn_weight.append(weight)
# 합성곱 연산 결과가 저장된다.
result_arr = []
for col in range(input.shape[0] - weight.shape[0] + 1):
for row in range(input.shape[1] - weight.shape[1] + 1):
result = []
for w_col in range(weight.shape[0]):
for w_row in range(weight.shape[1]):
result.append(input[col + w_col, row + w_row ] * weight[w_col, w_row])
result_arr.append(np.sum(result))
# 연산 결과를 크기에 맞게 바꿔준다.
result_arr = np.array(result_arr).reshape(input.shape[0] - weight.shape[0] + 1, -1)
print(input.shape[0] - result_arr.shape[0])
result_arr = self.pad.padding(result_arr, input.shape[0] - result_arr.shape[0])
# 연산 결과의 저장
self.cnn_result.append(result_arr)
기존과 동일한 합성곱 연산과 입력 데이터 크기와 연산 결과 크기의 차, 패딩 크기를 계산하여 패딩을 수행한다.
class PADDING:
def padding(self, input, padding_size):
"""
input : 입력 데이터
padding_size : padding 연산 후의 데이터 크기
"""
if(padding_size == 0):
return input
padding_matrix = np.zeros((input.shape[0] + padding_size, input.shape[1] + padding_size))
for i in range(input.shape[0]):
for j in range(input.shape[1]):
padding_matrix[i + int(padding_size / 2)][j + int(padding_size / 2)] = input[i][j]
return padding_matrix
패딩 클래스 구현 모습
64개의 필터와 7*7 크기의 필터를 사용,
cnn.same_padding_cnn(input, 7, 64)
print(len(cnn.cnn_result),len(cnn.cnn_weight))
>>>
64, 64
64개의 합성곱 연산 결과와 가중치(7,7)가 생성된 모습
class POOLING:
pad = PADDING()
pool_result = []
def max_pooling(self, input, pooling_size):
"""
input : 입력 데이터
pooling_size : pooling size
"""
self.pool_result = []
pooling_matrix = self.pad.padding(input, input.shape[0] % pooling_size)
for col in range(0, pooling_matrix.shape[0], pooling_size):
for row in range(0, pooling_matrix.shape[1], pooling_size):
pool_arr = []
for pooling_col in range(pooling_size):
for pooling_row in range(pooling_size):
pool_arr.append(pooling_matrix[pooling_col + col, pooling_row + row])
self.pool_result.append(max(pool_arr))
# 연산 결과를 크기에 맞게 바꿔준다.
return np.array(self.pool_result).reshape(int(pooling_matrix.shape[0] / pooling_size), -1)
이후 각 합성곱 연산에 max_pooling 을 수행한다.
def pooling(self, pooling_size):
self.cnn_result_reset()
# 각 합성곱 연산 결과별 pooling 연산을 수행한다.
for i in range(self.data_size):
pooling_result = self.pool.max_pooling(self.layer_result[self.layer - 1][i], pooling_size)
self.cnn_result.append(pooling_result)
self.layer_result.append(self.cnn_result)
# 레이어의 추가
self.layer = self.layer +1
cnn.pooling(2)
cnn.layer_result[1][0].shape
>>>
(14, 14)
pooling 연산 후 2 개의 레이어가 생성되고, 28,28 사이즈의 데이터는 그 반인 (14,14) 사이즈로 감소한 것을 확인할 수 있다.
'implement_ml_models > CNN' 카테고리의 다른 글
implement_CNN(MLP 전 까지) (0) | 2023.03.09 |
---|---|
implement_CNN(수정) (0) | 2023.03.09 |
implement_CNN(pooling) (0) | 2023.03.07 |
implement_CNN(start) (0) | 2023.03.07 |
implement_CNN(pooling) (0) | 2022.12.06 |