Source code for dragon.search_space.bricks.pooling

import numpy as np
import torch.nn as nn
from dragon.search_space.cells import Brick

[docs] class AVGPooling2D(Brick): def __init__(self, input_shape, pool, stride=None): super(AVGPooling2D, self).__init__(input_shape) c, h, w = input_shape self.pool_size=(pool,pool) if stride is None: stride = pool self.stride = stride self.pooling = nn.AvgPool2d(kernel_size=self.pool_size, stride=self.stride)
[docs] def forward(self, X): if (self.pool_size[0]>X.shape[-2]) or (self.pool_size[1] > X.shape[-1]): X = self.pad(X) X = self.pooling(X) return X
[docs] def pad(self,X): diff0 = self.pool_size[0] - X.shape[-2] sign0 = diff0 / np.abs(diff0) if diff0!=0 else 1 diff1 = self.pool_size[1] - X.shape[-1] sign1 = diff1 / np.abs(diff1) if diff1!=0 else 1 pad = (int(sign1 * np.ceil(np.abs(diff1)/2)), int(sign1 * np.floor(np.abs(diff1))/2), int(sign0 * np.ceil(np.abs(diff0)/2)), int(sign0 * np.floor(np.abs(diff0))/2)) return nn.functional.pad(X, pad)
[docs] def modify_operation(self, input_shape): pass
[docs] class MaxPooling2D(Brick): def __init__(self, input_shape, pool, stride=None): super(MaxPooling2D, self).__init__(input_shape) c, h, w = input_shape self.pool_size = (pool,pool) if stride is None: stride = pool self.stride = stride self.pooling = nn.MaxPool2d(kernel_size=self.pool_size, stride=self.stride)
[docs] def forward(self, X): if (self.pool_size[0]>X.shape[-2]) or (self.pool_size[1] > X.shape[-1]): X = self.pad(X) X = self.pooling(X) return X
[docs] def pad(self,X): diff0 = self.pool_size[0] - X.shape[-2] sign0 = diff0 / np.abs(diff0) if diff0!=0 else 1 diff1 = self.pool_size[1] - X.shape[-1] sign1 = diff1 / np.abs(diff1) if diff1!=0 else 1 pad = (int(sign1 * np.ceil(np.abs(diff1)/2)), int(sign1 * np.floor(np.abs(diff1))/2), int(sign0 * np.ceil(np.abs(diff0)/2)), int(sign0 * np.floor(np.abs(diff0))/2)) return nn.functional.pad(X, pad)
[docs] def modify_operation(self, input_shape): pass
class AVGPooling3D(nn.Module): def __init__(self, input_shape, pool, p2=None, p3=None, s1=None, s2=None, s3=None): super(AVGPooling3D, self).__init__() if p2 is None: p2 = pool if p3 is None: p3 = p2 self.pool_size = (pool, p2, p3) if s1 is None: s1 = pool if s2 is None: s2 = p2 if s3 is None: s3 = p3 self.stride = (s1, s2, s3) self.pooling = nn.AvgPool3d(kernel_size=self.pool_size, stride=self.stride) def forward(self, X): if (self.pool_size[0]>X.shape[-3]) or (self.pool_size[1] > X.shape[-2]) or (self.pool_size[2] > X.shape[-1]): X = self.pad(X) X = self.pooling(X) return X def pad(self,X): diff0 = self.pool_size[0] - X.shape[-3] if diff0<=0: diff0 = 0 diff1 = self.pool_size[1] - X.shape[-2] if diff1<=0: diff1 = 0 diff2 = self.pool_size[2] - X.shape[-1] if diff2<=0: diff2 = 0 pad = (int(np.ceil(np.abs(diff2)/2)), int(np.floor(np.abs(diff2))/2), int(np.ceil(np.abs(diff1)/2)), int(np.floor(np.abs(diff1))/2), int(np.ceil(np.abs(diff0)/2)), int(np.floor(np.abs(diff0))/2)) return nn.functional.pad(X, pad) def modify_operation(self, input_shape): pass class MaxPooling3D(nn.Module): def __init__(self, input_shape, pool, p2=None, p3=None, s1=None, s2=None, s3=None): super(MaxPooling3D, self).__init__() if p2 is None: p2 = pool if p3 is None: p3 = p2 self.pool_size = (pool, p2, p3) if s1 is None: s1 = pool if s2 is None: s2 = p2 if s3 is None: s3 = p3 self.stride = (s1, s2, s3) self.pooling = nn.MaxPool3d(kernel_size=self.pool_size, stride=self.stride) def forward(self, X): if (self.pool_size[0]>X.shape[-3]) or (self.pool_size[1] > X.shape[-2]) or (self.pool_size[2] > X.shape[-1]): X = self.pad(X) X = self.pooling(X) return X def pad(self,X): diff0 = self.pool_size[0] - X.shape[-3] if diff0<=0: diff0 = 0 diff1 = self.pool_size[1] - X.shape[-2] if diff1<=0: diff1 = 0 diff2 = self.pool_size[2] - X.shape[-1] if diff2<=0: diff2 = 0 pad = (int(np.ceil(np.abs(diff2)/2)), int(np.floor(np.abs(diff2))/2), int(np.ceil(np.abs(diff1)/2)), int(np.floor(np.abs(diff1))/2), int(np.ceil(np.abs(diff0)/2)), int(np.floor(np.abs(diff0))/2)) return nn.functional.pad(X, pad) def modify_operation(self, input_shape): pass
[docs] class AVGPooling1D(Brick): def __init__(self, input_shape, pool_size): super(AVGPooling1D, self).__init__(input_shape) if len(input_shape) > 1: c, l = input_shape else: c = input_shape[0] self.pool_size = pool_size self.pooling = nn.AvgPool1d(pool_size)
[docs] def forward(self, X): init_shape = X.shape if len(init_shape) < 3: X = X.unsqueeze(1) if self.pool_size>X.shape[-1]: X = self.pad(X) X = self.pooling(X) if len(init_shape) < 3: X = X.squeeze(1) return X
[docs] def modify_operation(self, input_shape): pass
[docs] def pad(self,X): diff = self.pool_size - X.shape[-1] sign = diff / np.abs(diff) if diff !=0 else 1 pad = (int(sign * np.ceil(np.abs(diff)/2)), int(sign * np.floor(np.abs(diff))/2)) return nn.functional.pad(X, pad)
[docs] class MaxPooling1D(Brick): def __init__(self, input_shape, pool_size): super(MaxPooling1D, self).__init__(input_shape) self.pool_size=pool_size self.pooling = nn.MaxPool1d(pool_size)
[docs] def forward(self, X): init_shape = X.shape if len(init_shape) < 3: X = X.unsqueeze(1) if self.pool_size>X.shape[-1]: X = self.pad(X) X = self.pooling(X) if len(init_shape) < 3: X = X.squeeze(1) return X
[docs] def modify_operation(self, input_shape): pass
[docs] def pad(self,X): diff = self.pool_size - X.shape[-1] sign = diff / np.abs(diff) if diff !=0 else 1 pad = (int(sign * np.ceil(np.abs(diff)/2)), int(sign * np.floor(np.abs(diff))/2)) return nn.functional.pad(X, pad)