目录
一.课程内容
二.代码复现
三.以后的学习和补充
非串型网络结构,即不是他的输出就是·他的输入。
面对复杂的网络,需要通过构造函数或者类来减少代码的冗余。
类似这种就是一个inception块。
注意:这里的average pooling可以通过padding不改变w,h的大小
在我们不确定超参数的选择时,例如使用多大的卷积核...我们就可以利用这种块,将所有可能的线路都尝试一边,当训练出结果时,有用的参数占比权重大,就会自动的筛选出来。
注意:这里的average pooling(平均池化)可以通过padding不改变w,h的大小
像这种1*1的卷积——我们可以用来降低运算量。
当网络层数越多,越复杂,反而训练效果越差。
有一种可能就是——梯度消失。当反向传播把梯度相乘时,如果权重全都小于1,那么得到的结果就会非常小,没有办法更新。
所以,出现了Residual learning,通过这样的相加,梯度就不会只在0左右,而在1的左右,也就不会出现梯度消失。
class Inception(torch.nn.Module):
def __init__(self,in_channels) :
super(Inception,self).__init__()
self.branch_pool=torch.nn.Conv2d(in_channels,24,kernel_size=1)
self.branch1x1=torch.nn.Conv2d(in_channels,16,kernel_size=1)
self.branch5x5_1=torch.nn.Conv2d(in_channels,16,kernel_size=1)
self.branch5x5_2=torch.nn.Conv2d(16,24,kernel_size=1,padding=2)
self.branch3x3_1=torch.nn.Conv2d(in_channels,16,kernel_size=1)
self.branch3x3_2=torch.nn.Conv2d(16,24,kernel_size=3,padding=1)
self.branch3x3_3=torch.nn.Conv2d(24,24,kernel_size=3,padding=1)
def forward(self,x):
branch_pool=F.avg_pool2d(x,kernel_size=3,stride=1,padding=1)
branch_pool=self.branch_pool(branch_pool)
branch1x1=self.branch1x1(x)
branch5x5=self.branch5x5_1(x)
branch5x5=self.branch5x5_2(branch5x5)
branch3x3=self.branch3x3_1(x)
branch3x3=self.branch3x3_2(branch3x3)
branch3x3=self.branch3x3_3(branch3x3)
outputs=[branch1x1,branch5x5,branch3x3,branch_pool]
return torch.cat(outputs,dim=1)
class Model(torch.nn.Module):
def __init__(self) :
super(Model,self).__init__()
self.Conv1=torch.nn.Conv2d(1,10,kernel_size=5)
self.Conv2=torch.nn.Conv2d(88,20,kernel_size=5)
self.incep1=Inception(in_channels=10)
self.incep2=Inception(in_channels=20)
self.pooling=torch.nn.MaxPool2d(2)
self.linear=torch.nn.Linear(1408,10)
# 1408和88就是有通道变化计算出来的值,例如88就是第一次进inception后输出的通道值
def forward(self,x):
batch_size=x.size(0)
x=F.relu(self.pooling(self.Conv1(x)))
x=self.incep1(x)
x=F.relu(self.pooling(self.Conv2(x)))
x=self.incep2(x)
x=x.view(batch_size,-1)
x=self.linear(x)
return x
class ResidualBlock(torch.nn.Module):
def __init__(self,channels):
super(ResidualBlock,self).__init__()
self.channels=channels
self.conv1=torch.nn.Conv2d(channels,channels,kernel_size=3,padding=1)#为了使大小不变
self.conv2=torch.nn.Conv2d(channels,channels,kernel_size=3,padding=1)
def forward(self,x):
y=F.relu(self.conv1(x))
y=self.conv2(y)
return F.relu(x+y)
class Model(torch.nn.Module):
def __init__(self) :
super(Model,self).__init__()
self.Conv1=torch.nn.Conv2d(1,16,kernel_size=5)
self.Conv2=torch.nn.Conv2d(16,32,kernel_size=5)
self.pooling=torch.nn.MaxPool2d(2)
self.rblock1=ResidualBlock(16)
self.rblock2=ResidualBlock(32)
self.linear=torch.nn.Linear(512,10)
def forward(self,x):
batch_size=x.size(0)
x=F.relu(self.pooling(self.Conv1(x)))
x=self.rblock1(x)
x=F.relu(self.pooling(self.Conv2(x)))
x=self.rblock2(x)
x=x.view(batch_size,-1)
x=self.linear(x)
return x
1,补充:在老师给的这个inception代码里,我觉得并没有给出自动筛选的结果,只是加了这样一层运算,然后通过最优结果,锁定跟踪参数,确定效果的参数。
2,学习计划:1)理论知识的补充2)通读文档3)读论文,代码,然后复现。