2012_Alex-Net
图:
网络结构:
网络总共的层数为8层,5层卷积,3层全连接层。第一层:卷积层1,输入为 224 × 224 × 3 224\times224\times3 224×224×3,卷积核的数量为96,论文中两片GPU分别计算48个核; 第二层:卷积层2, 输入为上一层卷积的feature map, 卷积的个数为256个,论文中的两个GPU分别有128个卷积核。第三层:卷积层3, 输入为第二层的输出,卷积核个数为384, kernel_size = 3×3);第四层:卷积4, 输入为第三层的输出,卷积核个数为384, kernel_size = (3 × 3);第五层:卷积5, 输入为第四层的输出,卷积核个数为256, kernel_size = (3 × 3 );第五层:卷积5, 输入为第四层的输出,卷积核个数为256, kernel_size = (3 × 3);第六七八层是全连接层,每一层的神经元的个数为4096,最终输出softmax为1000,ImageNet这个比赛的分类个数为1000。全连接层中使用了RELU和Dropout。
特点,优点:
(1)使用11x11,5x5,3x3的卷积核
(2)使用最大池化层
(3)接入3层全连接层
(4)加入GPU进行训练
(5)使用ReLU激活函数
(6)使用Dropout正则化技术
(7)使用图像增强技术
(8)LRN全称为Local Response Normalization,即局部响应归一化层,LRN函数类似Dropout,是一种防止过拟合的方法。对局部神经元的活动创建竞争机制,使得其中响应比较大的值变得相对更大,并抑制其他反馈较小的神经元,增强了模型的泛化能力。
代码:
keras实现:
def AlexNet(input_shape=(224,224,3),output_shape=2):
# AlexNet
model = Sequential()
# 使用步长为4x4,大小为11的卷积核对图像进行卷积,输出的特征层为96层,输出的shape为(55,55,96);
# 所建模型后输出为48特征层
model.add(Conv2D(
filters=48,
kernel_size=(11,11),
strides=(4,4),
padding='valid',
input_shape=input_shape,
activation='relu'
)
)
model.add(BatchNormalization())
# 使用步长为2的最大池化层进行池化,此时输出的shape为(27,27,96)
model.add(MaxPooling2D(
pool_size=(3,3),
strides=(2,2),
padding='valid'
)
)
# 使用步长为1x1,大小为5的卷积核对图像进行卷积,输出的特征层为256层,输出的shape为(27,27,256);
# 所建模型后输出为128特征层
model.add(
Conv2D(
filters=128,
kernel_size=(5,5),
strides=(1,1),
padding='same',
activation='relu'
)
)
model.add(BatchNormalization())
# 使用步长为2的最大池化层进行池化,此时输出的shape为(13,13,256);
model.add(
MaxPooling2D(
pool_size=(3,3),
strides=(2,2),
padding='valid'
)
)
# 使用步长为1x1,大小为3的卷积核对图像进行卷积,输出的特征层为384层,输出的shape为(13,13,384);
# 所建模型后输出为192特征层
model.add(
Conv2D(
filters=192,
kernel_size=(3,3),
strides=(1,1),
padding='same',
activation='relu'
)
)
# 使用步长为1x1,大小为3的卷积核对图像进行卷积,输出的特征层为384层,输出的shape为(13,13,384);
# 所建模型后输出为192特征层
model.add(
Conv2D(
filters=192,
kernel_size=(3,3),
strides=(1,1),
padding='same',
activation='relu'
)
)
# 使用步长为1x1,大小为3的卷积核对图像进行卷积,输出的特征层为256层,输出的shape为(13,13,256);
# 所建模型后输出为128特征层
model.add(
Conv2D(
filters=128,
kernel_size=(3,3),
strides=(1,1),
padding='same',
activation='relu'
)
)
# 使用步长为2的最大池化层进行池化,此时输出的shape为(6,6,256);
model.add(
MaxPooling2D(
pool_size=(3,3),
strides=(2,2),
padding='valid'
)
)
# 两个全连接层,最后输出为1000类,这里改为2类
# 缩减为1024
model.add(Flatten())
model.add(Dense(256, activation='relu'))
model.add(Dropout(0.5))
model.add(Dense(128, activation='relu'))
model.add(Dropout(0.5))
model.add(Dense(output_shape, activation='softmax'))
return model
pytorch实现:
class AlexNet(nn.Module):
def __init__(self,num_classes=1000):
super(AlexNet,self).__init__()
self.feature_extraction = nn.Sequential(
nn.Conv2d(in_channels=3,out_channels=96,kernel_size=11,stride=4,padding=2,bias=False),
nn.ReLU(inplace=True),
nn.MaxPool2d(kernel_size=3,stride=2,padding=0),
nn.Conv2d(in_channels=96,out_channels=192,kernel_size=5,stride=1,padding=2,bias=False),
nn.ReLU(inplace=True),
nn.MaxPool2d(kernel_size=3,stride=2,padding=0),
nn.Conv2d(in_channels=192,out_channels=384,kernel_size=3,stride=1,padding=1,bias=False),
nn.ReLU(inplace=True),
nn.Conv2d(in_channels=384,out_channels=256,kernel_size=3,stride=1,padding=1,bias=False),
nn.ReLU(inplace=True),
nn.Conv2d(in_channels=256,out_channels=256,kernel_size=3,stride=1,padding=1,bias=False),
nn.ReLU(inplace=True),
nn.MaxPool2d(kernel_size=3, stride=2, padding=0),
)
self.classifier = nn.Sequential(
nn.Dropout(p=0.5),
nn.Linear(in_features=256*6*6,out_features=4096),
nn.ReLU(inplace=True),
nn.Dropout(p=0.5),
nn.Linear(in_features=4096, out_features=4096),
nn.ReLU(inplace=True),
nn.Linear(in_features=4096, out_features=num_classes),
)
def forward(self,x):
x = self.feature_extraction(x)
x = x.view(x.size(0),256*6*6)
x = self.classifier(x)
return x