diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/.keep" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/.keep" new file mode 100644 index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/cbam_deeplabv3plus.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/cbam_deeplabv3plus.py" new file mode 100644 index 0000000000000000000000000000000000000000..68f363c681950c2d3c420d75a8bc40cd8a83860f --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/cbam_deeplabv3plus.py" @@ -0,0 +1,231 @@ + +""" +DeepLab V3+ with CBAM +""" +import logging +import torch.nn as nn +import numpy as np +#from torchsummary import summary +from utils import initialize_weights + +import torch.nn.functional as F +import torch.utils.model_zoo as model_zoo +from torchvision import models +from itertools import chain +import torch +class BaseModel(nn.Module): + def __init__(self): + super(BaseModel,self).__init__() + self.logger=logging.getLogger(self.__class__.__name__) + def forward(self): + raise NotImplementedError + def summary(self): + model_parameters=filter(lambda p:p.required_grad,self.parameters()) + nbr_params=sum([np.prod(p.size()) for p in model_parameters]) + self.logger.info(f'number of trainable parameters:{nbr_params}') + def __str__(self): + model_parameters=filter(lambda p:p.required_grad,self.parameters()) + nbr_params=sum([np.prod(p.size()) for p in model_parameters]) + return super(BaseModel, self).__str__()+f'\n number of trainable parameters:{nbr_params}' + +# resnet backbone +''' +ResNet一共有layer0-4,共5个layer。其中,layer0-2不变,仅改变layer3、4, +将普通卷积改为空洞卷积。若输出步幅(输入尺寸与输出尺寸之比)为8,则改动layer3和layer4; +若输出步幅为16,仅改动layer4 +''' +class ResNet(nn.Module): + def __init__(self,in_channels=3,output_stride=16,backbone='resnet101',pretrained=True): + super(ResNet,self).__init__() + model=getattr(models, backbone)(pretrained) + if not pretrained or in_channels!=3: + self.layer0=nn.Sequential( + nn.Conv2d(in_channels, 64, 7,stride=2,padding=3,biad=False), + nn.BatchNorm2d(64), + nn.ReLU(inplace=True), + nn.MaxPool2d(kernel_size=3,stride=2,padding=1) + + ) + initialize_weights(self.layer0) + else: + self.layer0=nn.Sequential(*list(model.children())[:4]) + self.layer1=model.layer1 + self.layer2=model.layer2 + self.layer3=model.layer3 + self.layer4=model.layer4 + if output_stride==16:s3,s4,d3,d4=(2,1,1,2) + elif output_stride==8:s3,s4,d3,d4=(1,1,2,4) + if output_stride==8: + for n,m in self.layer3.named_modules(): + if 'conv1' in n and (backbone=='resnet34' or backbone=='resnet18'): + m.dilation,m.padding,m.stride=(d3,d3),(d3,d3),(s3,s3) + elif 'conv2' in n: + m.dilation,m.padding,m.stride=(d3,d3),(d3,d3),(s3,s3) + elif 'downsample.0' in n: + m.stride=(s3,s3) + for n,m in self.layer4.named_modules(): + if 'conv1' in n and (backbone=='resnet34' or backbone=='resnet18'): + m.dilation,m.padding,m.stride=(d4,d4),(d4,d4),(s4,s4) + elif 'conv2' in n: + m.dilation,m.padding,m.stride=(d4,d4),(d4,d4),(s4,s4) + elif 'downsample.0' in n: + m.stride=(s4,s4) + def forward(self,x): + x=self.layer0(x) + x=self.layer1(x) + low_level_features=x + x=self.layer2(x) + x=self.layer3(x) + x=self.layer4(x) + return x,low_level_features + + +''' +the atrous spatial pyramid pooling + +''' +def assp_branch(in_channels,out_channels,kernel_size,dilation): + padding=0 if kernel_size==1 else dilation + return nn.Sequential( + nn.Conv2d(in_channels,out_channels,kernel_size,padding=padding,dilation=dilation,bias=False), + nn.BatchNorm2d(out_channels), + nn.ReLU(inplace=True) + ) +class ASSP(nn.Module): + def __init__(self,in_channels,output_stride): + super(ASSP, self).__init__() + assert output_stride in [8,16],'only output strides of 8 or 16 are suported' + if output_stride==16:dilation=[1,6,12,18] + elif output_stride==8:dilation=[1,12,24,36] + self.assp1=assp_branch(in_channels,256,1,dilation=dilation[0]) + self.assp2=assp_branch(in_channels,256,3,dilation=dilation[1]) + self.assp3=assp_branch(in_channels, 256,3, dilation=dilation[2]) + self.assp4=assp_branch(in_channels, 256, 3, dilation=dilation[3]) + self.avg_pool=nn.Sequential( + nn.AdaptiveAvgPool2d((1,1)), + nn.Conv2d(in_channels, 256, 1,bias=False), + nn.BatchNorm2d(256), + nn.ReLU(inplace=True) + ) + self.conv1=nn.Conv2d(256*5,256,1,bias=False) + self.bn1=nn.BatchNorm2d(256) + self.relu=nn.ReLU(inplace=True) + self.dropout=nn.Dropout(0.5) + initialize_weights(self) + def forward(self,x): + x1=self.assp1(x) + x2=self.assp2(x) + x3=self.assp3(x) + x4=self.assp4(x) + x5=F.interpolate(self.avg_pool(x),size=(x.size(2),x.size(3)),mode='bilinear',align_corners=True) + x=self.conv1(torch.cat((x1,x2,x3,x4,x5),dim=1)) + x=self.bn1(x) + x=self.dropout(self.relu(x)) + return x +class Decoder(nn.Module): + def __init__(self,low_level_channels,num_classes): + super(Decoder,self).__init__() + self.conv1=nn.Conv2d(low_level_channels, 48, 1,bias=False) + self.bn1=nn.BatchNorm2d(48) + self.relu=nn.ReLU(inplace=True) + self.output=nn.Sequential( + nn.Conv2d(48+256, 256, 3,stride=1,padding=1,bias=False), + nn.BatchNorm2d(256), + nn.ReLU(inplace=True), + nn.Conv2d(256, 256, 3,stride=1,padding=1,bias=False), + nn.BatchNorm2d(256), + nn.ReLU(inplace=True), + nn.Dropout(0.1), + nn.Conv2d(256, num_classes, 1,stride=1), + ) + initialize_weights(self) + def forward(self,x,low_level_features): + low_level_features=self.conv1(low_level_features) + low_level_features=self.relu(self.bn1(low_level_features)) + H,W=low_level_features.size(2),low_level_features.size(3) + x=F.interpolate(x,size=(H,W),mode='bilinear',align_corners=True) + x=self.output(torch.cat((low_level_features,x),dim=1)) + return x + +class ChannelAttention(nn.Module): + def __init__(self,in_channels,ratio=16): + super(ChannelAttention,self).__init__() + self.avgpool=nn.AdaptiveAvgPool2d(1) + self.maxpool=nn.AdaptiveMaxPool2d(1) + ''' + No1 + self.fc1=nn.Conv2d(in_channels, in_channels//16, kernel_size=1,bias=False) + self.relu1=nn.ReLU() + self.fc2=nn.Conv2d(in_channels//16, in_channels, kernel_size=1,bias=False) + No2 + self.fc1=nn.Conv2d(in_channels, in_channels*16, kernel_size=1,bias=False) + self.relu1=nn.ReLU() + self.fc2=nn.Conv2d(in_channels*16, in_channels, kernel_size=1,bias=False) + ''' + self.fc1=nn.Conv2d(in_channels, in_channels*16, kernel_size=1,bias=False) + self.relu1=nn.ReLU() + self.fc2=nn.Conv2d(in_channels*16, in_channels, kernel_size=1,bias=False) + + self.sigmoid=nn.Sigmoid() + def forward(self,x): + avg_out=self.fc2(self.relu1(self.fc1(self.avgpool(x)))) + max_out=self.fc2(self.relu1(self.fc1(self.maxpool(x)))) + out=avg_out+max_out + return self.sigmoid(out) +class SpatialAttention(nn.Module): + def __init__(self,kernel_size=7): + super(SpatialAttention,self).__init__() + assert kernel_size in (3,7) ,'kernel size must be 3 or 7' + padding=3 if kernel_size==7 else 1 + self.conv1=nn.Conv2d(2, 1, kernel_size,padding=padding,bias=False) + self.sigmoid=nn.Sigmoid() + def forward(self,x): + avg_out=torch.mean(x,dim=1,keepdim=True) + max_out,_=torch.max(x,dim=1,keepdim=True) + x=torch.cat([avg_out,max_out],dim=1) + x=self.conv1(x) + return self.sigmoid(x) +class CBAMDeepLab(BaseModel): + def __init__(self,num_classes=6,in_channels=3,backbone='resnet',pretrained=True,output_stride=16,freeze_bn=False,**_): + super(CBAMDeepLab, self).__init__() + assert('xception' or 'resnet' in backbone) + if 'resnet' in backbone: + self.backbone=ResNet(in_channels=in_channels,output_stride=output_stride,pretrained=pretrained) + low_level_channels=256 + + self.ASSP=ASSP(in_channels=2048,output_stride=output_stride) + self.ca1=ChannelAttention(3) + self.sa1=SpatialAttention() + self.ca2=ChannelAttention(256) + self.sa2=SpatialAttention() + #self.decoder=Decoder(64, num_classes) + #self.vgg=VGG() + self.decoder=Decoder(low_level_channels, num_classes) + if freeze_bn: + self.freeze_bn() + + def forward(self,x): + x=self.ca1(x)*x + x=self.sa1(x)*x + H,W=x.size(2),x.size(3) + x,low_level_features=self.backbone(x) + + #low_level_features=self.ca2(low_level_features)*low_level_features + #low_level_features=self.sa2(low_level_features)*low_level_features + #x,low_level_features=self.vgg(x) + x=self.ASSP(x) + #x=self.ca1(x)*x + #x=self.sa1(x)*x + x=self.decoder(x,low_level_features) + x=F.interpolate(x,size=(H,W),mode='bilinear',align_corners=True) + return x + def freeze_bn(self): + for module in self.modules(): + if isinstance(module,nn.BatchNorm2d): + module.eval() + def get_backbone_params(self): + return self.backbone.parameters() + def get_decoder_params(self): + return chain(self.ASSP.parameters(),self.decoder.parameters()) + + diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/dataset.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/dataset.py" new file mode 100644 index 0000000000000000000000000000000000000000..2bca3e62e9dab3d02a670c95b2609bc97efcddce --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/dataset.py" @@ -0,0 +1,68 @@ +# -*- coding: utf-8 -*- +""" +数据集导入 +""" +from torch.utils.data import Dataset +import torchvision.transforms as transforms +import numpy as np +from PIL import Image + +import torch + + + + +# 将一张彩色label转为一个单通道的图片数组 +# 每个颜色用一个整数代表,一个整数代表一个类别 +# ①非渗透表面 (RGB: 255, 255, 255) +# ②建筑物(RGB: 0, 0, 255) +# ③低矮植被 (RGB: 0, 255, 255) +# ④树木 (RGB: 0, 255, 0) +# ⑤汽车(RGB: 255, 255, 0) +# ⑥背景 (RGB: 255, 0, 0) + +class LabelUtil: + def __init__(self,color=[[255,255,255],[0,0,255],[0,255,255],[0,255,0],[255,255,0],[255,0,0]]): + # 创建一个hash数据,每一种颜色,给定一个下标值,这个下标所在的位置的值是一个整数id,一个id代表一个类别 + self.color=color + cm=np.zeros(256**3) + for cid,item in enumerate(color): + cm[(item[0]*256+item[1])*256+item[2]]=cid + self.colormap=cm + def __call__(self,pic): + # 3channels--> 1channel + label=np.array(pic,dtype='uint32') + cid=(label[:,:,0]*256+label[:,:,1])*256+label[:,:,2] + return np.array(self.colormap[cid],dtype='uint8') +class MyDataset(Dataset): + def __init__(self,data=[],filepath=''): + super(MyDataset,self).__init__() + self.data=data + self.filepath=filepath + self.transforms=transforms.Compose([ + transforms.ToTensor(), + transforms.Normalize([0.485, 0.456, 0.406], [0.229, 0.224, 0.225]) + ]) + + self.labelUtil=LabelUtil() + def __len__(self): + return len(self.data) + + def __getitem__(self, index): + + url=self.data[index] + + ''' + img=Image.open(self.filepath+'image\\'+url) + label=Image.open(self.filepath+'label\\'+url) + labelx=Image.new('RGB', label.size) + labelx.paste(label,(0,0)) + img,label=self.transforms(img),torch.from_numpy(self.labelUtil(label)) + ''' + img=Image.open(self.filepath+'\\image\\'+url) + label=Image.open(self.filepath+'\\label\\'+url) + labelx=Image.new('RGB', label.size) + labelx.paste(label,(0,0)) + img,label=self.transforms(img),torch.from_numpy(self.labelUtil(label)) + + return img, label \ No newline at end of file diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/deeplabv3plus.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/deeplabv3plus.py" new file mode 100644 index 0000000000000000000000000000000000000000..038801ae45703bb1d45098f3bb81b37196735efb --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/deeplabv3plus.py" @@ -0,0 +1,430 @@ +# -*- coding: utf-8 -*- +""" +DeepLab V3+ +""" +import logging +import torch.nn as nn +import numpy as np +#from torchsummary import summary +from utils import initialize_weights + +import torch.nn.functional as F +import torch.utils.model_zoo as model_zoo +from torchvision import models +from itertools import chain +import torch +class BaseModel(nn.Module): + def __init__(self): + super(BaseModel,self).__init__() + self.logger=logging.getLogger(self.__class__.__name__) + def forward(self): + raise NotImplementedError + def summary(self): + model_parameters=filter(lambda p:p.required_grad,self.parameters()) + nbr_params=sum([np.prod(p.size()) for p in model_parameters]) + self.logger.info(f'number of trainable parameters:{nbr_params}') + def __str__(self): + model_parameters=filter(lambda p:p.required_grad,self.parameters()) + nbr_params=sum([np.prod(p.size()) for p in model_parameters]) + return super(BaseModel, self).__str__()+f'\n number of trainable parameters:{nbr_params}' + +# resnet backbone +''' +ResNet一共有layer0-4,共5个layer。其中,layer0-2不变,仅改变layer3、4, +将普通卷积改为空洞卷积。若输出步幅(输入尺寸与输出尺寸之比)为8,则改动layer3和layer4; +若输出步幅为16,仅改动layer4 +''' +class ResNet(nn.Module): + def __init__(self,in_channels=3,output_stride=16,backbone='resnet101',pretrained=True): + super(ResNet,self).__init__() + model=getattr(models, backbone)(pretrained) + if not pretrained or in_channels!=3: + self.layer0=nn.Sequential( + nn.Conv2d(in_channels, 64, 7,stride=2,padding=3,biad=False), + nn.BatchNorm2d(64), + nn.ReLU(inplace=True), + nn.MaxPool2d(kernel_size=3,stride=2,padding=1) + + ) + initialize_weights(self.layer0) + else: + self.layer0=nn.Sequential(*list(model.children())[:4]) + self.layer1=model.layer1 + self.layer2=model.layer2 + self.layer3=model.layer3 + self.layer4=model.layer4 + if output_stride==16:s3,s4,d3,d4=(2,1,1,2) + elif output_stride==8:s3,s4,d3,d4=(1,1,2,4) + if output_stride==8: + for n,m in self.layer3.named_modules(): + if 'conv1' in n and (backbone=='resnet34' or backbone=='resnet18'): + m.dilation,m.padding,m.stride=(d3,d3),(d3,d3),(s3,s3) + elif 'conv2' in n: + m.dilation,m.padding,m.stride=(d3,d3),(d3,d3),(s3,s3) + elif 'downsample.0' in n: + m.stride=(s3,s3) + for n,m in self.layer4.named_modules(): + if 'conv1' in n and (backbone=='resnet34' or backbone=='resnet18'): + m.dilation,m.padding,m.stride=(d4,d4),(d4,d4),(s4,s4) + elif 'conv2' in n: + m.dilation,m.padding,m.stride=(d4,d4),(d4,d4),(s4,s4) + elif 'downsample.0' in n: + m.stride=(s4,s4) + def forward(self,x): + x=self.layer0(x) + x=self.layer1(x) + low_level_features=x + x=self.layer2(x) + x=self.layer3(x) + x=self.layer4(x) + return x,low_level_features + +# Xception backbone +class SeparableConv2d(nn.Module): + def __init__(self,in_channels,out_channels,kernel_size=3,stride=1,dilation=1,bias=False,BatchNorm=nn.BatchNorm2d): + super(SeparableConv2d,self).__init__() + if dilation>kernel_size//2:padding=dilation + else:padding=kernel_size//2 + self.conv1=nn.Conv2d(in_channels, in_channels, kernel_size,stride,padding=padding,dilation=dilation,groups=in_channels,bias=bias) + self.bn=nn.BatchNorm2d(in_channels) + self.pointwise=nn.Conv2d(in_channels, out_channels, 1,1,bias=bias) + def forward(self,x): + x=self.conv1(x) + x=self.bn(x) + x=self.pointwise(x) + return x +class Block(nn.Module): + def __init__(self,in_channels,out_channels,stride=1,dilation=1,exit_flow=False,use_lst_relu=True): + super(Block,self).__init__() + if in_channels!=out_channels or stride!=1: + self.skip=nn.Conv2d(in_channels, out_channels,1,stride=stride,bias=False) + self.skipbn=nn.BatchNorm2d(out_channels) + else: + self.skip=None + rep=[] + self.relu=nn.ReLU(inplace=True) + rep.append(self.relu) + rep.append(SeparableConv2d(in_channels, out_channels,3,stride=1,dilation=dilation)) + rep.append(nn.BatchNorm2d(out_channels)) + + rep.append(self.relu) + rep.append(SeparableConv2d(out_channels, out_channels,3,stride=1,dilation=dilation)) + rep.append(nn.BatchNorm2d(out_channels)) + + rep.append(self.relu) + rep.append(SeparableConv2d(out_channels, out_channels,3,stride=stride,dilation=dilation)) + rep.append(nn.BatchNorm2d(out_channels)) + + if exit_flow: + rep[3:6]=rep[:3] + rep[:3]=[self.relu,SeparableConv2d(in_channels, in_channels,3,1,dilation),nn.BatchNorm2d(in_channels)] + if not use_lst_relu: + rep=rep[1:] + self.rep=nn.Sequential(*rep) + def forward(self,x): + output=self.rep(x) + if self.skip is not None: + skip=self.skip(x) + skip=self.skipbn(skip) + else: + skip=x + x=output+skip + return x +''' +Xception:对中间流(middle flow)和出口流(exit flow)改动:去掉池化层并将卷积层替换为带有步长的可分离卷积 +入口流(entry flow)不变 +''' +class Xception(nn.Module): + def __init__(self,output_stride=16,in_channels=3,pretrained=True): + super(Xception,self).__init__() + + # stride for block 3(entry flow),and the dilation rates for middle flow and exit flow + if output_stride==16:b3_s,mf_d,ef_d=2,1,(1,2) + if output_stride==8:b3_s,mf_d,ef_d=1,2,(2,4) + + # entry flow + self.conv1=nn.Conv2d(in_channels,32, 3,2,padding=1,bias=False) + self.bn1=nn.BatchNorm2d(32) + self.relu=nn.ReLU(inplace=True) + self.conv2=nn.Conv2d(32,64, 3,1,padding=1,bias=False) + self.bn2=nn.BatchNorm2d(64) + + self.block1=Block(64, 128,stride=2,dilation=1,use_lst_relu=False) + self.block2=Block(128, 256,stride=2,dilation=1) + self.block3=Block(256,728,stride=b3_s,dilation=1) + + # middle flow + for i in range(16): + exec(f'self.block{i+4}=Block(728,728,stride=1,dilation=mf_d)') + + # exit flow + self.block20=Block(728, 1024,stride=1,dilation=ef_d[0],exit_flow=True) + self.conv3=SeparableConv2d(1024, 1536,3,stride=1,dilation=ef_d[1]) + self.bn3=nn.BatchNorm2d(1536) + self.conv4=SeparableConv2d(1536, 1536,3,stride=1,dilation=ef_d[1]) + self.bn4= nn.BatchNorm2d(1536) + self.conv5=SeparableConv2d(1536, 2048,3,stride=1,dilation=ef_d[1]) + self.bn5= nn.BatchNorm2d(2048) + + initialize_weights(self) + if pretrained: + self._load_pretrained_model() + def _load_pretrained_model(self): + #url = 'http://data.lip6.fr/cadene/pretrainedmodels/xception-b5690688.pth' + #pretrained_weights = model_zoo.load_url(url) + pretrained_weights=torch.load('E:/搜狗高速下载/gxq/xception-b5690688.pth') + state_dict = self.state_dict() + model_dict = {} + for k,v in pretrained_weights.items(): + if k in state_dict: + if 'pointwise' in k: + v=v.unsqueeze(-1).unsqueeze(-1) # [C,C]-->[C,C,1,1] + if k.startswith('block11'): + model_dict[k]=v + for i in range(8): + model_dict[k.replace('block11',f'block{i+12}')]=v + elif k.startswith('block12'): + + model_dict[k.replace('block12','block20')]=v + elif k.startswith('bn3'): + model_dict[k]=v + + model_dict[k.replace('bn3','bn4')]=v + elif k.startswith('conv4'): + + model_dict[k.replace('conv4','conv5')]=v + elif k.startswith('bn4'): + + model_dict[k.replace('bn4','bn5')]=v + else: + model_dict[k]=v + state_dict.update(model_dict) + self.load_state_dict(state_dict) + def forward(self,x): + # entry flow + x=self.conv1(x) + x=self.bn1(x) + x=self.relu(x) + x=self.conv2(x) + x=self.bn2(x) + x=self.block1(x) + low_level_features=x + x=F.relu(x) + x=self.block2(x) + x=self.block3(x) + + # middle flow + x = self.block4(x) + x = self.block5(x) + x = self.block6(x) + x = self.block7(x) + x = self.block8(x) + x = self.block9(x) + x = self.block10(x) + x = self.block11(x) + x = self.block12(x) + x = self.block13(x) + x = self.block14(x) + x = self.block15(x) + x = self.block16(x) + x = self.block17(x) + x = self.block18(x) + x = self.block19(x) + + # exit flow + x = self.block20(x) + x = self.relu(x) + x = self.conv3(x) + x = self.bn3(x) + x = self.relu(x) + + x = self.conv4(x) + x = self.bn4(x) + x = self.relu(x) + + x = self.conv5(x) + x = self.bn5(x) + x = self.relu(x) + + return x, low_level_features +''' +the atrous spatial pyramid pooling + +''' +def assp_branch(in_channels,out_channels,kernel_size,dilation): + padding=0 if kernel_size==1 else dilation + return nn.Sequential( + nn.Conv2d(in_channels,out_channels,kernel_size,padding=padding,dilation=dilation,bias=False), + nn.BatchNorm2d(out_channels), + nn.ReLU(inplace=True) + ) +class ASSP(nn.Module): + def __init__(self,in_channels,output_stride): + super(ASSP, self).__init__() + assert output_stride in [8,16],'only output strides of 8 or 16 are suported' + if output_stride==16:dilation=[1,6,12,18] + elif output_stride==8:dilation=[1,12,24,36] + self.assp1=assp_branch(in_channels,256,1,dilation=dilation[0]) + self.assp2=assp_branch(in_channels,256,3,dilation=dilation[1]) + self.assp3=assp_branch(in_channels, 256,3, dilation=dilation[2]) + self.assp4=assp_branch(in_channels, 256, 3, dilation=dilation[3]) + self.avg_pool=nn.Sequential( + nn.AdaptiveAvgPool2d((1,1)), + nn.Conv2d(in_channels, 256, 1,bias=False), + nn.BatchNorm2d(256), + nn.ReLU(inplace=True) + ) + self.conv1=nn.Conv2d(256*5,256,1,bias=False) + self.bn1=nn.BatchNorm2d(256) + self.relu=nn.ReLU(inplace=True) + self.dropout=nn.Dropout(0.5) + initialize_weights(self) + def forward(self,x): + x1=self.assp1(x) + x2=self.assp2(x) + x3=self.assp3(x) + x4=self.assp4(x) + x5=F.interpolate(self.avg_pool(x),size=(x.size(2),x.size(3)),mode='bilinear',align_corners=True) + x=self.conv1(torch.cat((x1,x2,x3,x4,x5),dim=1)) + x=self.bn1(x) + x=self.dropout(self.relu(x)) + return x +class Decoder(nn.Module): + def __init__(self,low_level_channels,num_classes): + super(Decoder,self).__init__() + self.conv1=nn.Conv2d(low_level_channels, 48, 1,bias=False) + self.bn1=nn.BatchNorm2d(48) + self.relu=nn.ReLU(inplace=True) + self.output=nn.Sequential( + nn.Conv2d(48+256, 256, 3,stride=1,padding=1,bias=False), + nn.BatchNorm2d(256), + nn.ReLU(inplace=True), + nn.Conv2d(256, 256, 3,stride=1,padding=1,bias=False), + nn.BatchNorm2d(256), + nn.ReLU(inplace=True), + nn.Dropout(0.1), + nn.Conv2d(256, num_classes, 1,stride=1), + ) + initialize_weights(self) + def forward(self,x,low_level_features): + low_level_features=self.conv1(low_level_features) + low_level_features=self.relu(self.bn1(low_level_features)) + H,W=low_level_features.size(2),low_level_features.size(3) + x=F.interpolate(x,size=(H,W),mode='bilinear',align_corners=True) + x=self.output(torch.cat((low_level_features,x),dim=1)) + return x +class VGG(nn.Module): + def __init__(self,in_channels=3): + super(VGG,self).__init__() + self.in_channels=in_channels + self.conv1=nn.Sequential( + nn.Conv2d(in_channels, 64, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(64), + nn.Conv2d(64, 64, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(64), + nn.MaxPool2d(kernel_size=3,stride=2,padding=1) + ) + self.conv2=nn.Sequential( + nn.Conv2d(64, 128, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(128), + nn.Conv2d(128, 128, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(128), + nn.MaxPool2d(kernel_size=3,stride=2,padding=1) + ) + self.conv3=nn.Sequential( + nn.Conv2d(128, 256, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(256), + nn.Conv2d(256, 256, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(256), + nn.Conv2d(256, 256, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(256), + nn.MaxPool2d(kernel_size=3,stride=2,padding=1) + ) + self.conv4=nn.Sequential( + nn.Conv2d(256, 512, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(512), + nn.Conv2d(512, 512, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(512), + nn.Conv2d(512, 512, kernel_size=3,stride=1,padding=1), + nn.ReLU(True), + nn.BatchNorm2d(512), + nn.MaxPool2d(kernel_size=3,stride=2,padding=1) + ) + self.conv5=nn.Sequential( + nn.Conv2d(512, 512, kernel_size=3,stride=1,padding=2,dilation=2), + nn.ReLU(True), + nn.BatchNorm2d(512), + nn.Conv2d(512, 512, kernel_size=3,stride=1,padding=2,dilation=2), + nn.ReLU(True), + nn.BatchNorm2d(512), + nn.Conv2d(512, 512, kernel_size=3,stride=1,padding=2,dilation=2), + nn.ReLU(True), + nn.BatchNorm2d(512), + nn.MaxPool2d(kernel_size=3,stride=2,padding=1), + nn.AvgPool2d(kernel_size=3,stride=1,padding=1) + ) + self.conv6=nn.Sequential( + nn.Conv2d(512, 1024, kernel_size=3,stride=1,padding=12,dilation=12), + nn.ReLU(True), + nn.BatchNorm2d(1024) + ) + self.conv7=nn.Sequential( + nn.Conv2d(1024, 2048, kernel_size=1), + nn.ReLU(True), + nn.BatchNorm2d(2048) + ) + initialize_weights(self) + def forward(self,x): + x=self.conv1(x) + low_level_features=x + x=self.conv2(x) + x=self.conv3(x) + x=self.conv4(x) + x=self.conv5(x) + x=self.conv6(x) + x=self.conv7(x) + return x,low_level_features +class DeepLab(BaseModel): + def __init__(self,num_classes=6,in_channels=3,backbone='resnet',pretrained=True,output_stride=16,freeze_bn=False,**_): + super(DeepLab, self).__init__() + assert('xception' or 'resnet' in backbone) + if 'resnet' in backbone: + self.backbone=ResNet(in_channels=in_channels,output_stride=output_stride,pretrained=pretrained) + low_level_channels=256 + else: + self.backbone=Xception(output_stride=output_stride,pretrained=pretrained) + low_level_channels=128 + self.ASSP=ASSP(in_channels=2048,output_stride=output_stride) + #self.decoder=Decoder(64, num_classes) + #self.vgg=VGG() + self.decoder=Decoder(low_level_channels, num_classes) + if freeze_bn: + self.freeze_bn() + + def forward(self,x): + H,W=x.size(2),x.size(3) + x,low_level_features=self.backbone(x) + #x,low_level_features=self.vgg(x) + x=self.ASSP(x) + x=self.decoder(x,low_level_features) + x=F.interpolate(x,size=(H,W),mode='bilinear',align_corners=True) + return x + def freeze_bn(self): + for module in self.modules(): + if isinstance(module,nn.BatchNorm2d): + module.eval() + def get_backbone_params(self): + return self.backbone.parameters() + def get_decoder_params(self): + return chain(self.ASSP.parameters(),self.decoder.parameters()) + + diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/fcns.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/fcns.py" new file mode 100644 index 0000000000000000000000000000000000000000..1d001462610f4ad65a2a57f8632e624191e4d5a4 --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/fcns.py" @@ -0,0 +1,569 @@ +# -*- coding: utf-8 -*- +""" +Created on Wed Jan 20 09:32:58 2021 + +@author: GXQ +""" + +import os.path as osp + + +import torch +import torchvision +import torch.nn as nn +import numpy as np +import os +os.environ['KMP_DUPLICATE_LIB_OK']='True' + +def VGG16(pretrained=False): + model = torchvision.models.vgg16(pretrained=False) + if not pretrained: + return model + model_file = 'D:\\搜狗高速下载\\gxq\\vgg16_from_caffe.npz' + state_dict = torch.load(model_file) + model.load_state_dict(state_dict) + return model + +def get_upsampling_weight(in_channels, out_channels, kernel_size): + """Make a 2D bilinear kernel suitable for upsampling""" + factor = (kernel_size + 1) // 2 + if kernel_size % 2 == 1: + center = factor - 1 + else: + center = factor - 0.5 + og = np.ogrid[:kernel_size, :kernel_size] + filt = (1 - abs(og[0] - center) / factor) * \ + (1 - abs(og[1] - center) / factor) + weight = np.zeros((in_channels, out_channels, kernel_size, kernel_size), + dtype=np.float64) + weight[range(in_channels), range(out_channels), :, :] = filt + return torch.from_numpy(weight).float() + +class FCN32s(nn.Module): + + def __init__(self,n_class): + super(FCN32s,self).__init__() + self.n_class=n_class + #conv1 1/2 + self.conv1_1=nn.Conv2d(3,64,3,padding=100) + self.relu1_1=nn.ReLU(inplace=True) + self.conv1_2=nn.Conv2d(64,64,3,padding=1) + self.relu1_2=nn.ReLU(inplace=True) + self.pool1=nn.MaxPool2d(2,stride=2,ceil_mode=True) + # conv2 1/4 + self.conv2_1=nn.Conv2d(64,128,3,padding=1) + self.relu2_1=nn.ReLU(inplace=True) + self.conv2_2=nn.Conv2d(128,128,3,padding=1) + self.relu2_2=nn.ReLU(inplace=True) + self.pool2=nn.MaxPool2d(2,stride=2,ceil_mode=True) + # conv3 1/8 + self.conv3_1=nn.Conv2d(128,256,3,padding=1) + self.relu3_1=nn.ReLU(inplace=True) + self.conv3_2=nn.Conv2d(256,256,3,padding=1) + self.relu3_2=nn.ReLU(inplace=True) + self.conv3_3=nn.Conv2d(256,256,3,padding=1) + self.relu3_3=nn.ReLU(inplace=True) + self.pool3=nn.MaxPool2d(2,stride=2,ceil_mode=True) + # conv4 1/16 + self.conv4_1=nn.Conv2d(256,512,3,padding=1) + self.relu4_1=nn.ReLU(inplace=True) + self.conv4_2=nn.Conv2d(512,512,3,padding=1) + self.relu4_2=nn.ReLU(inplace=True) + self.conv4_3=nn.Conv2d(512,512,3,padding=1) + self.relu4_3=nn.ReLU(inplace=True) + self.pool4=nn.MaxPool2d(2,stride=2,ceil_mode=True) + # conv5 1/32 + self.conv5_1=nn.Conv2d(512,512,3,padding=1) + self.relu5_1=nn.ReLU(inplace=True) + self.conv5_2=nn.Conv2d(512,512,3,padding=1) + self.relu5_2=nn.ReLU(inplace=True) + self.conv5_3=nn.Conv2d(512,512,3,padding=1) + self.relu5_3=nn.ReLU(inplace=True) + self.pool5=nn.MaxPool2d(2,stride=2,ceil_mode=True) + # fc6 + self.fc6=nn.Conv2d(512,4096,7) + self.relu6=nn.ReLU(inplace=True) + self.drop6=nn.Dropout2d() + # fc7 + self.fc7=nn.Conv2d(4096,4096,1) + self.relu7=nn.ReLU(inplace=True) + self.drop7=nn.Dropout2d() + self.score_fr=nn.Conv2d(4096,n_class,1) + self.upscore=nn.ConvTranspose2d(n_class,n_class,64,stride=32,bias=False) + self._initialize_weights() + def _initialize_weights(self): + for m in self.modules(): + if isinstance(m,nn.Conv2d): + m.weight.data.zero_() + if m.bias is not None: + m.bias.data.zero_() + if isinstance(m,nn.ConvTranspose2d): + assert m.kernel_size[0]==m.kernel_size[1] + initial_weight=get_upsampling_weight(m.in_channels,m.out_channels,m.kernel_size[0]) + m.weight.data.copy_(initial_weight) + def forward(self,x): + h=x + x=self.relu1_1(self.conv1_1(x)) + x=self.relu1_2(self.conv1_2(x)) + x=self.pool1(x) + + x=self.relu2_1(self.conv2_1(x)) + x=self.relu2_2(self.conv2_2(x)) + x=self.pool2(x) + + x=self.relu3_1(self.conv3_1(x)) + x=self.relu3_2(self.conv3_2(x)) + x=self.relu3_3(self.conv3_3(x)) + x=self.pool3(x) + + x=self.relu4_1(self.conv4_1(x)) + x=self.relu4_2(self.conv4_2(x)) + x=self.relu4_3(self.conv4_3(x)) + x=self.pool4(x) + + x=self.relu5_1(self.conv5_1(x)) + x=self.relu5_2(self.conv5_2(x)) + x=self.relu5_3(self.conv5_3(x)) + x=self.pool5(x) + + x=self.relu6(self.fc6(x)) + x=self.drop6(x) + + x=self.relu7(self.fc7(x)) + x=self.drop7(x) + + x=self.score_fr(x) + x=self.upscore(x) + x = x[:, :, 19:19 + h.size()[2], 19:19 + h.size()[3]].contiguous() + return x + def copy_params_from_vgg16(self,vgg16): + features = [ + self.conv1_1, self.relu1_1, + self.conv1_2, self.relu1_2, + self.pool1, + self.conv2_1, self.relu2_1, + self.conv2_2, self.relu2_2, + self.pool2, + self.conv3_1, self.relu3_1, + self.conv3_2, self.relu3_2, + self.conv3_3, self.relu3_3, + self.pool3, + self.conv4_1, self.relu4_1, + self.conv4_2, self.relu4_2, + self.conv4_3, self.relu4_3, + self.pool4, + self.conv5_1, self.relu5_1, + self.conv5_2, self.relu5_2, + self.conv5_3, self.relu5_3, + self.pool5, + ] + for l1,l2 in zip(vgg16.features,features): + if isinstance(l1,nn.Conv2d) and isinstance(l2,nn.Conv2d): + assert l1.weight.size()==l2.weight.size() + assert l1.bias.size()==l2.bias.size() + l2.weight.data=l1.weight.data + l2.bias.data=l2.bias.data + for i,name in zip([0,3],['fc6','fc7']): + l1=vgg16.classifier[i] + l2=getattr(self,name) + l2.weight.data=l1.weight.data.view(l2.weight.size()) + l2.bias.data=l1.bias.data.view(l2.bias.size()) + +class FCN16s(nn.Module): + + + def __init__(self, n_class=21): + super(FCN16s, self).__init__() + # conv1 + self.conv1_1 = nn.Conv2d(3, 64, 3, padding=100) + self.relu1_1 = nn.ReLU(inplace=True) + self.conv1_2 = nn.Conv2d(64, 64, 3, padding=1) + self.relu1_2 = nn.ReLU(inplace=True) + self.pool1 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/2 + + # conv2 + self.conv2_1 = nn.Conv2d(64, 128, 3, padding=1) + self.relu2_1 = nn.ReLU(inplace=True) + self.conv2_2 = nn.Conv2d(128, 128, 3, padding=1) + self.relu2_2 = nn.ReLU(inplace=True) + self.pool2 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/4 + + # conv3 + self.conv3_1 = nn.Conv2d(128, 256, 3, padding=1) + self.relu3_1 = nn.ReLU(inplace=True) + self.conv3_2 = nn.Conv2d(256, 256, 3, padding=1) + self.relu3_2 = nn.ReLU(inplace=True) + self.conv3_3 = nn.Conv2d(256, 256, 3, padding=1) + self.relu3_3 = nn.ReLU(inplace=True) + self.pool3 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/8 + + # conv4 + self.conv4_1 = nn.Conv2d(256, 512, 3, padding=1) + self.relu4_1 = nn.ReLU(inplace=True) + self.conv4_2 = nn.Conv2d(512, 512, 3, padding=1) + self.relu4_2 = nn.ReLU(inplace=True) + self.conv4_3 = nn.Conv2d(512, 512, 3, padding=1) + self.relu4_3 = nn.ReLU(inplace=True) + self.pool4 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/16 + + # conv5 + self.conv5_1 = nn.Conv2d(512, 512, 3, padding=1) + self.relu5_1 = nn.ReLU(inplace=True) + self.conv5_2 = nn.Conv2d(512, 512, 3, padding=1) + self.relu5_2 = nn.ReLU(inplace=True) + self.conv5_3 = nn.Conv2d(512, 512, 3, padding=1) + self.relu5_3 = nn.ReLU(inplace=True) + self.pool5 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/32 + + # fc6 + self.fc6 = nn.Conv2d(512, 4096, 7) + self.relu6 = nn.ReLU(inplace=True) + self.drop6 = nn.Dropout2d() + + # fc7 + self.fc7 = nn.Conv2d(4096, 4096, 1) + self.relu7 = nn.ReLU(inplace=True) + self.drop7 = nn.Dropout2d() + + self.score_fr = nn.Conv2d(4096, n_class, 1) + self.score_pool4 = nn.Conv2d(512, n_class, 1) + + self.upscore2 = nn.ConvTranspose2d( + n_class, n_class, 4, stride=2, bias=False) + self.upscore16 = nn.ConvTranspose2d( + n_class, n_class, 32, stride=16, bias=False) + + self._initialize_weights() + + def _initialize_weights(self): + for m in self.modules(): + if isinstance(m, nn.Conv2d): + m.weight.data.zero_() + if m.bias is not None: + m.bias.data.zero_() + if isinstance(m, nn.ConvTranspose2d): + assert m.kernel_size[0] == m.kernel_size[1] + initial_weight = get_upsampling_weight( + m.in_channels, m.out_channels, m.kernel_size[0]) + m.weight.data.copy_(initial_weight) + + def forward(self, x): + h = x + h = self.relu1_1(self.conv1_1(h)) + h = self.relu1_2(self.conv1_2(h)) + h = self.pool1(h) + + h = self.relu2_1(self.conv2_1(h)) + h = self.relu2_2(self.conv2_2(h)) + h = self.pool2(h) + + h = self.relu3_1(self.conv3_1(h)) + h = self.relu3_2(self.conv3_2(h)) + h = self.relu3_3(self.conv3_3(h)) + h = self.pool3(h) + + h = self.relu4_1(self.conv4_1(h)) + h = self.relu4_2(self.conv4_2(h)) + h = self.relu4_3(self.conv4_3(h)) + h = self.pool4(h) + pool4 = h # 1/16 + + h = self.relu5_1(self.conv5_1(h)) + h = self.relu5_2(self.conv5_2(h)) + h = self.relu5_3(self.conv5_3(h)) + h = self.pool5(h) + + h = self.relu6(self.fc6(h)) + h = self.drop6(h) + + h = self.relu7(self.fc7(h)) + h = self.drop7(h) + + h = self.score_fr(h) + h = self.upscore2(h) + upscore2 = h # 1/16 + + h = self.score_pool4(pool4) + h = h[:, :, 5:5 + upscore2.size()[2], 5:5 + upscore2.size()[3]] + score_pool4c = h # 1/16 + + h = upscore2 + score_pool4c + + h = self.upscore16(h) + h = h[:, :, 27:27 + x.size()[2], 27:27 + x.size()[3]].contiguous() + + return h + + def copy_params_from_fcn32s(self, fcn32s): + for name, l1 in fcn32s.named_children(): + try: + l2 = getattr(self, name) + l2.weight # skip ReLU / Dropout + except Exception: + continue + assert l1.weight.size() == l2.weight.size() + assert l1.bias.size() == l2.bias.size() + l2.weight.data.copy_(l1.weight.data) + l2.bias.data.copy_(l1.bias.data) + +class FCN8s(nn.Module): + + + + def __init__(self, n_class=6): + super(FCN8s, self).__init__() + self.conv1_1 = nn.Conv2d(3, 64, 3, padding=100) + self.bn1_1=nn.BatchNorm2d(64) + self.relu1_1 = nn.ReLU(inplace=True) + self.conv1_2 = nn.Conv2d(64, 64, 3, padding=1) + self.bn1_2=nn.BatchNorm2d(64) + self.relu1_2 = nn.ReLU(inplace=True) + self.pool1 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/2 + + # conv2 + self.conv2_1 = nn.Conv2d(64, 128, 3, padding=1) + self.bn2_1=nn.BatchNorm2d(128) + self.relu2_1 = nn.ReLU(inplace=True) + self.conv2_2 = nn.Conv2d(128, 128, 3, padding=1) + self.bn2_2=nn.BatchNorm2d(128) + self.relu2_2 = nn.ReLU(inplace=True) + self.pool2 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/4 + + # conv3 + self.conv3_1 = nn.Conv2d(128, 256, 3, padding=1) + self.bn3_1=nn.BatchNorm2d(256) + self.relu3_1 = nn.ReLU(inplace=True) + self.conv3_2 = nn.Conv2d(256, 256, 3, padding=1) + self.bn3_2=nn.BatchNorm2d(256) + self.relu3_2 = nn.ReLU(inplace=True) + self.conv3_3 = nn.Conv2d(256, 256, 3, padding=1) + self.bn3_3=nn.BatchNorm2d(256) + self.relu3_3 = nn.ReLU(inplace=True) + self.pool3 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/8 + + # conv4 + self.conv4_1 = nn.Conv2d(256, 512, 3, padding=1) + self.bn4_1=nn.BatchNorm2d(512) + self.relu4_1 = nn.ReLU(inplace=True) + self.conv4_2 = nn.Conv2d(512, 512, 3, padding=1) + self.bn4_2=nn.BatchNorm2d(512) + self.relu4_2 = nn.ReLU(inplace=True) + self.conv4_3 = nn.Conv2d(512, 512, 3, padding=1) + self.bn4_3=nn.BatchNorm2d(512) + self.relu4_3 = nn.ReLU(inplace=True) + self.pool4 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/16 + + # conv5 + self.conv5_1 = nn.Conv2d(512, 512, 3, padding=1) + self.bn5_1=nn.BatchNorm2d(512) + self.relu5_1 = nn.ReLU(inplace=True) + self.conv5_2 = nn.Conv2d(512, 512, 3, padding=1) + self.bn5_2=nn.BatchNorm2d(512) + self.relu5_2 = nn.ReLU(inplace=True) + self.conv5_3 = nn.Conv2d(512, 512, 3, padding=1) + self.bn5_3=nn.BatchNorm2d(512) + self.relu5_3 = nn.ReLU(inplace=True) + self.pool5 = nn.MaxPool2d(2, stride=2, ceil_mode=True) # 1/32 + + # fc6 + self.fc6 = nn.Conv2d(512, 4096, 7) + self.relu6 = nn.ReLU(inplace=True) + #self.drop6 = nn.Dropout2d() + + # fc7 + self.fc7 = nn.Conv2d(4096, 4096, 1) + self.relu7 = nn.ReLU(inplace=True) + #self.drop7 = nn.Dropout2d() + + self.score_fr = nn.Conv2d(4096, n_class, 1) + self.score_pool3 = nn.Conv2d(256, n_class, 1) + self.score_pool4 = nn.Conv2d(512, n_class, 1) + + self.upscore2 = nn.ConvTranspose2d( + n_class, n_class, 4, stride=2, bias=False) + self.upscore8 = nn.ConvTranspose2d( + n_class, n_class, 16, stride=8, bias=False) + self.upscore_pool4 = nn.ConvTranspose2d( + n_class, n_class, 4, stride=2, bias=False) + + self._initialize_weights() + + def _initialize_weights(self): + for m in self.modules(): + if isinstance(m, nn.Conv2d): + m.weight.data.zero_() + if m.bias is not None: + m.bias.data.zero_() + if isinstance(m, nn.ConvTranspose2d): + assert m.kernel_size[0] == m.kernel_size[1] + initial_weight = get_upsampling_weight( + m.in_channels, m.out_channels, m.kernel_size[0]) + m.weight.data.copy_(initial_weight) + + def forward(self, x): + h = x + h = self.relu1_1(self.bn1_1(self.conv1_1(h))) + h = self.relu1_2(self.bn1_2(self.conv1_2(h))) + h = self.pool1(h) + + h = self.relu2_1(self.bn2_1(self.conv2_1(h))) + h = self.relu2_2(self.bn2_2(self.conv2_2(h))) + h = self.pool2(h) + + h = self.relu3_1(self.bn3_1(self.conv3_1(h))) + h = self.relu3_2(self.bn3_2(self.conv3_2(h))) + h = self.relu3_3(self.bn3_3(self.conv3_3(h))) + h = self.pool3(h) + pool3 = h # 1/8 + + h = self.relu4_1(self.bn4_1(self.conv4_1(h))) + h = self.relu4_2(self.bn4_2(self.conv4_2(h))) + h = self.relu4_3(self.bn4_3(self.conv4_3(h))) + h = self.pool4(h) + pool4 = h # 1/16 + + h = self.relu5_1(self.bn5_1(self.conv5_1(h))) + h = self.relu5_2(self.bn5_2(self.conv5_2(h))) + h = self.relu5_3(self.bn5_3(self.conv5_3(h))) + h = self.pool5(h) + + h = self.relu6(self.fc6(h)) + #h = self.drop6(h) + + h = self.relu7(self.fc7(h)) + #h = self.drop7(h) + + h = self.score_fr(h) + h = self.upscore2(h) + upscore2 = h # 1/16 + + h = self.score_pool4(pool4) + h = h[:, :, 5:5 + upscore2.size()[2], 5:5 + upscore2.size()[3]] + score_pool4c = h # 1/16 + + h = upscore2 + score_pool4c # 1/16 + h = self.upscore_pool4(h) + upscore_pool4 = h # 1/8 + + h = self.score_pool3(pool3) + h = h[:, :, + 9:9 + upscore_pool4.size()[2], + 9:9 + upscore_pool4.size()[3]] + score_pool3c = h # 1/8 + + h = upscore_pool4 + score_pool3c # 1/8 + + h = self.upscore8(h) + h = h[:, :, 31:31 + x.size()[2], 31:31 + x.size()[3]].contiguous() + + return h + + def copy_params_from_fcn16s(self, fcn16s): + for name, l1 in fcn16s.named_children(): + try: + l2 = getattr(self, name) + l2.weight # skip ReLU / Dropout + except Exception: + continue + assert l1.weight.size() == l2.weight.size() + l2.weight.data.copy_(l1.weight.data) + if l1.bias is not None: + assert l1.bias.size() == l2.bias.size() + l2.bias.data.copy_(l1.bias.data) + + +class FCN8sAtOnce(FCN8s): + + + + def forward(self, x): + h = x + h = self.relu1_1(self.bn1_1(self.conv1_1(h))) + h = self.relu1_2(self.bn1_2(self.conv1_2(h))) + h = self.pool1(h) + + h = self.relu2_1(self.bn2_1(self.conv2_1(h))) + h = self.relu2_2(self.bn2_2(self.conv2_2(h))) + h = self.pool2(h) + + h = self.relu3_1(self.bn3_1(self.conv3_1(h))) + h = self.relu3_2(self.bn3_2(self.conv3_2(h))) + h = self.relu3_3(self.bn3_3(self.conv3_3(h))) + h = self.pool3(h) + pool3 = h # 1/8 + + h = self.relu4_1(self.bn4_1(self.conv4_1(h))) + h = self.relu4_2(self.bn4_2(self.conv4_2(h))) + h = self.relu4_3(self.bn4_3(self.conv4_3(h))) + h = self.pool4(h) + pool4 = h # 1/16 + + h = self.relu5_1(self.bn5_1(self.conv5_1(h))) + h = self.relu5_2(self.bn5_2(self.conv5_2(h))) + h = self.relu5_3(self.bn5_3(self.conv5_3(h))) + h = self.pool5(h) + + h = self.relu6(self.fc6(h)) + #h = self.drop6(h) + + h = self.relu7(self.fc7(h)) + #h = self.drop7(h) + + h = self.score_fr(h) + h = self.upscore2(h) + upscore2 = h # 1/16 + print(upscore2.shape) + h = self.score_pool4(pool4 * 0.01) # XXX: scaling to train at once + h = h[:, :, 5:5 + upscore2.size()[2], 5:5 + upscore2.size()[3]] + score_pool4c = h # 1/16 + print(score_pool4c.shape) + h = upscore2 + score_pool4c # 1/16 + h = self.upscore_pool4(h) + upscore_pool4 = h # 1/8 + print(upscore_pool4.shape) + h = self.score_pool3(pool3 * 0.0001) # XXX: scaling to train at once + h = h[:, :, + 9:9 + upscore_pool4.size()[2], + 9:9 + upscore_pool4.size()[3]] + score_pool3c = h # 1/8 + print(score_pool3c.shape) + h = upscore_pool4 + score_pool3c # 1/8 + + h = self.upscore8(h) + print(h.shape) + h = h[:, :, 31:31 + x.size()[2], 31:31 + x.size()[3]].contiguous() + + return h + + def copy_params_from_vgg16(self, vgg16): + features = [ + self.conv1_1, self.relu1_1, + self.conv1_2, self.relu1_2, + self.pool1, + self.conv2_1, self.relu2_1, + self.conv2_2, self.relu2_2, + self.pool2, + self.conv3_1, self.relu3_1, + self.conv3_2, self.relu3_2, + self.conv3_3, self.relu3_3, + self.pool3, + self.conv4_1, self.relu4_1, + self.conv4_2, self.relu4_2, + self.conv4_3, self.relu4_3, + self.pool4, + self.conv5_1, self.relu5_1, + self.conv5_2, self.relu5_2, + self.conv5_3, self.relu5_3, + self.pool5, + ] + for l1, l2 in zip(vgg16.features, features): + if isinstance(l1, nn.Conv2d) and isinstance(l2, nn.Conv2d): + assert l1.weight.size() == l2.weight.size() + assert l1.bias.size() == l2.bias.size() + l2.weight.data.copy_(l1.weight.data) + l2.bias.data.copy_(l1.bias.data) + for i, name in zip([0, 3], ['fc6', 'fc7']): + l1 = vgg16.classifier[i] + l2 = getattr(self, name) + l2.weight.data.copy_(l1.weight.data.view(l2.weight.size())) + l2.bias.data.copy_(l1.bias.data.view(l2.bias.size())) diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/learning_curve.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/learning_curve.py" new file mode 100644 index 0000000000000000000000000000000000000000..23b4917849eb58e10b4a23f78395313b345fff3f --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/learning_curve.py" @@ -0,0 +1,109 @@ +# -*- coding: utf-8 -*- +""" +learning curve +""" + +import os.path as osp +import matplotlib +matplotlib.use('Agg') # 运行不会显示图 +import matplotlib.pyplot as plt +import pandas as pd +import seaborn +def learning_curve(logfile): + df=pd.read_csv(logfile) + colors=['red','green','blue','purple','orange'] + colors=seaborn.xkcd_palette(colors) + plt.figure(figsize=(20,6),dpi=300) + row_min=df.min() + row_max=df.max() + + # initialize datafram for train + columns=[ + 'epoch', + 'iteration', + 'train/loss', + 'train/acc', + 'train/acc_cls', + 'train/mean_iu', + 'train/fwavacc', + + ] + df_train=df[columns] + if hasattr(df_train,'rolling'): + df_train=df_train.rolling(window=10).mean() + else: + df_train=pd.rolling_mean(df_train,windows=10) + df_train=df_train.dropna() + iter_per_epoch = df_train[df_train['epoch'] == 1]['iteration'].values[0] + df_train['epoch_detail'] = df_train['iteration'] / iter_per_epoch + + # initialize DataFrame for val + columns = [ + 'epoch', + 'iteration', + 'valid/loss', + 'valid/acc', + 'valid/acc_cls', + 'valid/mean_iu', + 'valid/fwavacc', + ] + df_valid = df[columns] + df_valid = df_valid.dropna() + df_valid['epoch_detail'] = df_valid['iteration'] / iter_per_epoch + + data_frames = {'train': df_train, 'valid': df_valid} + + n_row = 2 + n_col = 3 + for i, split in enumerate(['train', 'valid']): + df_split = data_frames[split] + + # loss + plt.subplot(n_row, n_col, i * n_col + 1) + plt.ticklabel_format(style='sci', axis='y', scilimits=(0, 0)) + plt.plot(df_split['epoch_detail'], df_split['%s/loss' % split], '-', + markersize=1, color=colors[0], alpha=.5, + label='%s loss' % split) + plt.xlim((0, row_max['epoch'])) + plt.ylim((min(row_min['train/loss'], row_min['valid/loss']), + max(row_max['train/loss'], row_max['valid/loss']))) + plt.xlabel('epoch') + plt.ylabel('%s loss' % split) + + # loss (log) + plt.subplot(n_row, n_col, i * n_col + 2) + plt.ticklabel_format(style='sci', axis='y', scilimits=(0, 0)) + plt.semilogy(df_split['epoch_detail'], df_split['%s/loss' % split], + '-', markersize=1, color=colors[0], alpha=.5, + label='%s loss' % split) + plt.xlim((0, row_max['epoch'])) + plt.ylim((min(row_min['train/loss'], row_min['valid/loss']), + max(row_max['train/loss'], row_max['valid/loss']))) + plt.xlabel('epoch') + plt.ylabel('%s loss (log)' % split) + + # lbl accuracy + plt.subplot(n_row, n_col, i * n_col + 3) + plt.ticklabel_format(style='sci', axis='y', scilimits=(0, 0)) + plt.plot(df_split['epoch_detail'], df_split['%s/acc' % split], + '-', markersize=1, color=colors[1], alpha=.5, + label='%s accuracy' % split) + plt.plot(df_split['epoch_detail'], df_split['%s/acc_cls' % split], + '-', markersize=1, color=colors[2], alpha=.5, + label='%s accuracy class' % split) + plt.plot(df_split['epoch_detail'], df_split['%s/mean_iu' % split], + '-', markersize=1, color=colors[3], alpha=.5, + label='%s mean IU' % split) + plt.plot(df_split['epoch_detail'], df_split['%s/fwavacc' % split], + '-', markersize=1, color=colors[4], alpha=.5, + label='%s fwav accuracy' % split) + plt.legend() + plt.xlim((0, row_max['epoch'])) + plt.ylim((0, 1)) + plt.xlabel('epoch') + plt.ylabel('%s label accuracy' % split) + out_file = osp.splitext(logfile)[0] + '.png' + plt.savefig(out_file) + print('==> Wrote figure to: %s' % out_file) +logfile=r'E:\gxq\256x256\Deeplab_logs\se3\log.csv' +learning_curve(logfile) \ No newline at end of file diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/mytrain.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/mytrain.py" new file mode 100644 index 0000000000000000000000000000000000000000..e8be1dcde08f10cd5295cedb3b96f37bf16a9ac0 --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/mytrain.py" @@ -0,0 +1,267 @@ +# -*- coding: utf-8 -*- +""" +定义训练器 +""" +import warnings +warnings.filterwarnings("ignore") +import datetime + + +import os +import os.path as osp +import shutil +from torch.utils.tensorboard import SummaryWriter +from utils import label_accuracy_score +import numpy as np + +import torch +from torch.autograd import Variable + +import tqdm + + +from utils import cross_entropy2d + + + +def getData(train_path,valid_path,test_path): + + train_set=[] + val_set=[] + test_set=[] + # 获取训练数据 + for i in os.listdir(train_path+'image'): + train_set.append(i) + for i in os.listdir(valid_path+'image'): + val_set.append(i) + for i in os.listdir(test_path+'image'): + test_set.append(i) + + return train_set,val_set,test_set + +class Trainer(object): + + def __init__(self, cuda, model, optimizer, + train_loader, val_loader, test_loader,out, max_iter, + size_average=False, interval_validate=None): + self.cuda = cuda + + self.model = model + self.optim = optimizer + + self.train_loader = train_loader + self.val_loader = val_loader + self.test_loader=test_loader + self.timestamp_start = datetime.datetime.now() + self.size_average = size_average + self.writer=SummaryWriter(log_dir=filepath+'deeplab2_writer') + + if interval_validate is None: + self.interval_validate = len(self.train_loader) + else: + self.interval_validate = interval_validate + + self.out = out + if not osp.exists(self.out): + os.makedirs(self.out) + + self.log_headers = [ + 'epoch', + 'iteration', + 'train/loss', + 'train/acc', + 'train/acc_cls', + 'train/mean_iu', + 'train/fwavacc', + 'valid/loss', + 'valid/acc', + 'valid/acc_cls', + 'valid/mean_iu', + 'valid/fwavacc', + 'elapsed_time', + ] + if not osp.exists(osp.join(self.out, 'log.csv')): + with open(osp.join(self.out, 'log.csv'), 'w') as f: + f.write(','.join(self.log_headers) + '\n') + + self.epoch = 0 + self.iteration = 0 + self.max_iter = max_iter + self.best_mean_iu = 0 + + def validate(self): + training = self.model.training + self.model.eval() + + + + val_loss = 0 + #visualizations = [] + label_trues, label_preds = [], [] + for batch_idx, (data, target) in tqdm.tqdm( + enumerate(self.val_loader), total=len(self.val_loader), + desc='Valid iteration=%d' % self.iteration, ncols=80, + leave=False): + if self.cuda: + data, target = data.cuda(), target.cuda() + #data= np.transpose(data, (0,3,1,2)) #训练unet需要 + data, target = Variable(data), Variable(target) + + + with torch.no_grad(): + score = self.model(data.float()) + + loss = cross_entropy2d(score, target, + size_average=self.size_average) + loss_data = loss.data.item() + if np.isnan(loss_data): + raise ValueError('loss is nan while validating') + val_loss += loss_data / len(data) + + #imgs = data.data.cpu() + lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :] + lbl_true = target.data.cpu().numpy() + label_trues.append(lbl_true) + label_preds.append(lbl_pred) + + + metrics=label_accuracy_score(label_trues,label_preds) + + val_loss /= len(self.val_loader) + with open(osp.join(self.out,'log.csv'),'a') as f: + elapsed_time=(datetime.datetime.now()-self.timestamp_start).total_seconds() + log = [self.epoch, self.iteration] + [''] * 5 + \ + [val_loss] + list(metrics) + [elapsed_time] + log = map(str, log) + f.write(','.join(log) + '\n') + mean_iu=metrics[2] + + is_best=mean_iu>self.best_mean_iu + if is_best: + self.best_mean_iu=mean_iu + self.writer.add_scalar('val_loss',val_loss,self.epoch) + + self.writer.add_scalar('val_mean_iu', mean_iu,self.epoch) + + torch.save({ + 'epoch': self.epoch, + 'iteration': self.iteration, + 'arch': self.model.__class__.__name__, + 'optim_state_dict': self.optim.state_dict(), + 'model_state_dict': self.model.state_dict(), + 'best_mean_iu':self.best_mean_iu, + + }, osp.join(self.out, 'checkpoint.pth.tar')) + + if is_best: + shutil.copy(osp.join(self.out, 'checkpoint.pth.tar'), + osp.join(self.out, 'model_best.pth.tar')) + + if training: + self.model.train() + + def train_epoch(self): + self.model.train() + + for batch_idx, (data, target) in tqdm.tqdm( + enumerate(self.train_loader), total=len(self.train_loader), + desc='Train epoch=%d' % self.epoch, ncols=80, leave=False): + iteration = batch_idx + self.epoch * len(self.train_loader) + if self.iteration != 0 and (iteration - 1) != self.iteration: + continue # for resuming + self.iteration = iteration + + if (self.iteration) % self.interval_validate == 0: + self.validate() + + assert self.model.training + + if self.cuda: + data, target = data.cuda(), target.cuda() + #data= np.transpose(data, (0,3,1,2))##训练unet需要 + data, target = Variable(data), Variable(target) + self.optim.zero_grad() + score = self.model(data.float()) + + loss = cross_entropy2d(score, target, + size_average=self.size_average) + loss /= len(data) + loss_data = loss.data.item() + + if np.isnan(loss_data): + raise ValueError('loss is nan while training') + loss.backward() + self.optim.step() + metrics=[] + lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :] + lbl_true = target.data.cpu().numpy() + acc,acc_cls,mean_iu,fwavacc=label_accuracy_score(lbl_pred,lbl_true) + metrics.append((acc,acc_cls,mean_iu,fwavacc)) + metrics=np.mean(metrics,axis=0) + + self.writer.add_scalar('train_acc',acc,self.epoch) + self.writer.add_scalar('train_acc_cls', acc_cls,self.epoch) + self.writer.add_scalar('train_mean_iu', mean_iu,self.epoch) + self.writer.add_scalar('train_fwavacc', fwavacc,self.epoch) + + with open(osp.join(self.out,'log.csv'),'a') as f: + elapsed_time=(datetime.datetime.now()-self.timestamp_start).total_seconds() + log=[self.epoch,self.iteration]+[loss_data]+metrics.tolist()+['']*5+[elapsed_time] + log=map(str,log) + f.write(','.join(log)+'\n') + + + if self.iteration >= self.max_iter: + break + + def train(self): + max_epoch = 1000 + # 将模型写入tensorboard + #init_img=torch.zeros(1,3,256,256) + #self.writer.add_graph(self.model,init_img) + for epoch in tqdm.trange(self.epoch, max_epoch, + desc='Train', ncols=80): + self.epoch = epoch + self.train_epoch() + if self.iteration >= self.max_iter: + break + + def test(self): + + test_loss=0 + label_preds=[] + label_trues=[] + self.model.load_state_dict(torch.load(osp.join(self.out, 'model_best.pth.tar'))['model_state_dict']) + #self.model.load_state_dict(torch.load(r'E:\gxq\256x256\Deeplab_logs\se2\model_best.pth.tar')['model_state_dict']) + + for i,(data,target) in enumerate(self.test_loader): + self.model.eval() + if self.cuda: + data=data.cuda() + target=target.cuda() + self.model=self.model.cuda() + data, target = Variable(data), Variable(target) + with torch.no_grad(): + score=self.model(data.float()) + loss = cross_entropy2d(score, target, + size_average=self.size_average) + loss_data = loss.data.item() + + if np.isnan(loss_data): + raise ValueError('loss is nan while testing') + + + #imgs = data.data.cpu() + lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :] + lbl_true = target.data.cpu().numpy() + label_trues.append(lbl_true) + label_preds.append(lbl_pred) + test_loss+=loss_data + test_loss/=len(self.test_loader) + print('test loss:',test_loss) + metrics=[] + acc,acc_cls,mean_iu,fwavacc=label_accuracy_score(label_trues,label_preds) + metrics.append((acc,acc_cls,mean_iu,fwavacc)) + metrics=np.mean(metrics,axis=0) + print(metrics) + \ No newline at end of file diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/predict.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/predict.py" new file mode 100644 index 0000000000000000000000000000000000000000..273eb867550a9fcc69b80cd1a4e43965430e4062 --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/predict.py" @@ -0,0 +1,131 @@ +# -*- coding: utf-8 -*- +""" +预测并显示 +""" +import torch +import torch.nn.functional as F +from PIL import Image +import numpy as np +import torchvision.transforms as transforms +import os +import cv2 +import matplotlib.pyplot as plt +from time import time +import stn_deeplabv3 + + +basePath=r'E:\gxq' +def clip(filepath): + img=Image.open(filepath) + save_path=basePath+'\\predict256_label' + if not os.path.exists(save_path): + os.makedirs(save_path) + for j in range(int(6000/256)): + for k in range(int(6000/256)): + src_roi=img.crop((j*256,k*256,(j+1)*256,(k+1)*256)) + src_roi.save(os.path.join(save_path,'_'+str(k)+'_'+str(j)+'.png')) +#clip(r'E:\搜狗高速下载\gxq\Postdam_Labels_all\top_potsdam_7_7_label.tif') +def merge(filepath,ncols,nrows): + file_name=file(filepath) + result=np.zeros((nrows*256,ncols*256,3),np.uint8) + for i in range(len(file_name)): + img=cv2.imread(os.path.join(filepath,file_name[i])) + cols_th=int(file_name[i].split("_")[-1].split('.')[0]) + rows_th=int(file_name[i].split("_")[-2]) + roi=img[0:256,0:256,:] + result[rows_th*256:(rows_th+1)*256,cols_th*256:(cols_th+1)*256,:]=roi + cv2.imwrite(filepath+'merge.png',result) +#merge(basePath+'predict_ocrnet',23,23) +def file(filepath): + file=[] + for root,dirs,files in os.walk(filepath): + for f in files: + file.append(f) + return file +#file(basePath+'\\predict_deeplab') +class Predict: + def __init__(self,modelSavePath,net,colormap): + model_data = torch.load(modelSavePath) + try: + net.load_state_dict(model_data) + except Exception: + net.load_state_dict(model_data['model_state_dict']) + #net.load_state_dict(torch.load(modelSavePath)) + + net.eval() + self.net=net + self.colormap=np.array(colormap).astype('uint8') + self.ImageTransToTensor=transforms.Compose([transforms.ToTensor(),transforms.Normalize([0.485, 0.456, 0.406], [0.229, 0.224, 0.225])]) + def __call__(self,imagePath,resultPath): + img=Image.open(imagePath) + img=self.ImageTransToTensor(img) + img=torch.unsqueeze(img, dim=0) + score=self.net(img) + score=F.log_softmax(score,dim=1) + preMatrix=score.max(1)[1].squeeze().cpu().data.numpy() + resultArr=self.colormap[preMatrix] + preImg=Image.fromarray(resultArr).convert('RGB') + preImg.save(resultPath) + #preImg.show() + + +from PIL.Image import NEAREST, BILINEAR, BICUBIC, LANCZOS, BOX, HAMMING +modelSavePath=r'E:\gxq\256x256\Deeplab_logs\stn_low\model_best.pth.tar' +net=stn_deeplabv3.Stn_DeepLab() +color=[[255,255,255,200],[0,0,255,200],[0,255,255,200],[0,255,0,200],[255,255,0,200],[255,0,0,200]] +#img=Image.open('E:\\gxq\\image\\top_potsdam_2_10_RGB.png') +st = time() +img_path=basePath+'\\predict256\\' +file_name=file(img_path) +for i in range(len(file_name)): + p=Predict(modelSavePath, net, color) + resultPath=basePath+'\\predict_stndeeplab\\'+str(file_name[i]) + p(img_path+file_name[i],resultPath) +end=time()-st +print('预测时间为:',end) +def pre2mask(imagePath,resultPath,combinePath,labelPath): + # + ''' + img1 = cv2.imdecode(np.fromfile(imagePath,dtype=np.uint8),-1) + img2 = cv2.imdecode(np.fromfile(resultPath,dtype=np.uint8),-1) # this one has transparency + h, w, c = img2.shape + + img1 = cv2.resize(img1, (w, h), interpolation = cv2.INTER_CUBIC) + + result=np.zeros((h,w,3),np.uint8) + + alpha=img2[:,:,3]/255.0 + result[:,:,0]=(1.-alpha)*img1[:,:,0]+alpha*img2[:, :, 0] + result[:,:,1]=(1.-alpha)*img1[:,:,1]+alpha*img2[:, :, 1] + result[:,:,2]=(1.-alpha)*img1[:,:,2]+alpha*img2[:, :, 2] + #cv2.imshow('combine',result) + cv2.imwrite(combinePath,result) + + a,b,c=Image.open(imagePath),Image.open(combinePath),Image.open(labelPath) + d=Image.new('RGB', (a.size[0]*3,a.size[1])) + d.paste(a,(0,0)) + d.paste(b,(a.size[0],0)) + d.paste(c,(a.size[0]+b.size[0],0)) + plt.imshow(d) + ''' + img1=Image.open(imagePath) + img2=Image.open(resultPath) + img1=img1.convert('RGBA') + img2=img2.convert('RGBA') + img=Image.blend(img1, img2, 0.3) + img.show() + img.save(combinePath) +''' +imagePath= r'E:\gxq\predict256merge.png' +combinePath='E:\\gxq\\combineunet.png' +labelPath=r'E:\搜狗高速下载\gxq\Postdam_Labels_all\top_potsdam_7_7_label.tif' +resultPath=r'E:\gxq\predict_unetmerge.png' +pre2mask(imagePath, resultPath, combinePath, labelPath) +a,b,c=Image.open(imagePath),Image.open(resultPath),Image.open(labelPath) +a=a.crop((0,0,b.size[0],b.size[1])) +d=Image.new('RGB', (a.size[0]*3,a.size[1])) +d.paste(a,(0,0)) +d.paste(b,(a.size[0],0)) +d.paste(c,(a.size[0]+b.size[0],0)) +plt.imshow(d) +''' diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/readme.md" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/readme.md" new file mode 100644 index 0000000000000000000000000000000000000000..f514701507a15c82aa5bf80e2138573eec3d873d --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/readme.md" @@ -0,0 +1,12 @@ + **主要代码文件说明:** +1.dataset.py:定义数据集的读取 +2.fcns.py:fcn8s模型 + unet.py:U-Net模型 + deeplabv3plus.py:deeplabV3+模型 + cbam_deeplabv3plus.py:嵌入CBAM的DeepLab V3+模型 +3.mytrain.py:模型训练代码 + train_X.py:各模型具体训练的实现代码,需更改数据路径及结果保存路径 +4.test.py:模型测试代码 +5.predict.py:可视化分割结果 + + diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/test.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/test.py" new file mode 100644 index 0000000000000000000000000000000000000000..896ff02d76e39922bfa98280dddcf8787adbffd1 --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/test.py" @@ -0,0 +1,74 @@ +# -*- coding: utf-8 -*- +""" +Created on Fri Mar 12 11:00:40 2021 + +@author: dl +""" +import torch +from torch.autograd import Variable +import utils +import numpy as np +def _fast_hist(label_true, label_pred, n_class): + mask = (label_true >= 0) & (label_true < n_class) + hist = np.bincount( + n_class * label_true[mask].astype(int) + + label_pred[mask], minlength=n_class ** 2).reshape(n_class, n_class) + return hist +def iou(label_trues, label_preds, n_class=6): + """Returns accuracy score evaluation result. + - overall accuracy + - mean accuracy + - mean IU + - fwavacc + """ + hist = np.zeros((n_class, n_class)) + for lt, lp in zip(label_trues, label_preds): + hist += _fast_hist(lt.flatten(), lp.flatten(), n_class) + + with np.errstate(divide='ignore', invalid='ignore'): + iu = np.diag(hist) / ( + hist.sum(axis=1) + hist.sum(axis=0) - np.diag(hist) + ) + + return hist,iu + +def test_model(model,test_loader,best_model): + test_loss=0 + label_preds=[] + label_trues=[] + model.load_state_dict(torch.load(best_model)['model_state_dict']) + + for i,(data,target) in enumerate(test_loader): + model.eval() + if torch.cuda.is_available(): + data=data.cuda() + target=target.cuda() + model=model.cuda() + data, target = Variable(data), Variable(target) + with torch.no_grad(): + score=model(data.float()) + loss = utils.cross_entropy2d(score, target, + size_average=False) + loss_data = loss.data.item() + + if np.isnan(loss_data): + raise ValueError('loss is nan while testing') + + + #imgs = data.data.cpu() + lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :] + lbl_true = target.data.cpu().numpy() + label_trues.append(lbl_true) + label_preds.append(lbl_pred) + + test_loss+=loss_data + test_loss/=len(test_loader) + print('test loss:',test_loss) + hist,iu=iou(label_trues, label_preds) + print(hist) + print(iu) + + + + + diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_cbamdeeplab.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_cbamdeeplab.py" new file mode 100644 index 0000000000000000000000000000000000000000..53fc26f9fa85890bcf062ae236c4712c55f4e8eb --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_cbamdeeplab.py" @@ -0,0 +1,129 @@ +# -*- coding: utf-8 -*- +""" +训练deeplab v3+ cbam +""" + +import datetime +import os +import os.path as osp + + +import torch + +import dataset +import cbam_deeplabv3 +import mytrain + +cuda = torch.cuda.is_available() + +torch.manual_seed(1337) +if cuda: + torch.cuda.manual_seed(1337) +# 1.data +# kwargs = {'num_workers': 4, 'pin_memory': True} if cuda else {} + +train_path='E:\\gxq\\256x256\\train\\' +valid_path='E:\\gxq\\256x256\\valid\\' +test_path='E:\\gxq\\256x256\\test\\' +train_set,val_set,test_set=mytrain.getData(train_path,valid_path,test_path) +train_loader = torch.utils.data.DataLoader( + dataset.MyDataset(train_set,filepath=train_path), batch_size=16, shuffle=True) +val_loader = torch.utils.data.DataLoader( + dataset.MyDataset(val_set,filepath=valid_path), batch_size=16, shuffle=True) +test_loader = torch.utils.data.DataLoader( + dataset.MyDataset(test_set,filepath=test_path), batch_size=16, shuffle=False) +# 2.model +model = cbam_deeplabv3.CBAMDeepLab() +start_epoch = 0 +start_iteration = 1 + + +if cuda: + model = model.cuda() + +# 3.optimizer +optim=torch.optim.SGD(model.parameters(),lr=2.0e-10,weight_decay=0.0005,momentum=0.99) +out=osp.join('E:\\gxq\\256x256\\', 'Deeplab_logs', datetime.datetime.now().strftime('%Y%m%d_%H%M%S.%f')) +if not osp.exists(out): + os.makedirs(out) +max_iteration=100000 +trainer =mytrain.Trainer( + cuda=cuda, + model=model, + optimizer=optim, + train_loader=train_loader, + val_loader=val_loader, + test_loader=test_loader, + out=out, + max_iter=max_iteration, + interval_validate=4000, + ) +trainer.epoch = start_epoch +trainer.iteration = start_iteration +#trainer.train() +#trainer.test() + +import torch +from torch.autograd import Variable +import utils +import numpy as np +def _fast_hist(label_true, label_pred, n_class): + mask = (label_true >= 0) & (label_true < n_class) + hist = np.bincount( + n_class * label_true[mask].astype(int) + + label_pred[mask], minlength=n_class ** 2).reshape(n_class, n_class) + return hist +def iou(label_trues, label_preds, n_class=6): + """Returns accuracy score evaluation result. + - overall accuracy + - mean accuracy + - mean IU + - fwavacc + """ + hist = np.zeros((n_class, n_class)) + for lt, lp in zip(label_trues, label_preds): + hist += _fast_hist(lt.flatten(), lp.flatten(), n_class) + + with np.errstate(divide='ignore', invalid='ignore'): + iu = np.diag(hist) / ( + hist.sum(axis=1) + hist.sum(axis=0) - np.diag(hist) + ) + + return hist,iu + +def testmodel(model,test_loader,best_model): + test_loss=0 + label_preds=[] + label_trues=[] + model.load_state_dict(torch.load(best_model)['model_state_dict']) + + for i,(data,target) in enumerate(test_loader): + model.eval() + if torch.cuda.is_available(): + data=data.cuda() + target=target.cuda() + model=model.cuda() + data, target = Variable(data), Variable(target) + with torch.no_grad(): + score=model(data.float()) + loss = utils.cross_entropy2d(score, target, + size_average=False) + loss_data = loss.data.item() + + if np.isnan(loss_data): + raise ValueError('loss is nan while testing') + + + #imgs = data.data.cpu() + lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :] + lbl_true = target.data.cpu().numpy() + label_trues.append(lbl_true) + label_preds.append(lbl_pred) + + test_loss+=loss_data + test_loss/=len(test_loader) + print('test loss:',test_loss) + hist,iu=iou(label_trues, label_preds) + print(hist) + print(iu) +testmodel(model,test_loader,r'E:\gxq\256x256\Deeplab_logs\20210509_211601.857552\model_best.pth.tar') diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_deeplabv3plus.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_deeplabv3plus.py" new file mode 100644 index 0000000000000000000000000000000000000000..a2d7f8dff7610da4d5394af274a3d1ee7ae06924 --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_deeplabv3plus.py" @@ -0,0 +1,62 @@ +# -*- coding: utf-8 -*- +""" +训练deeplabv3 +""" +import os +os.environ['KMP_DUPLICATE_LIB_OK']='True' +import datetime + +import os.path as osp + + +import torch + +import dataset +import deeplabv3 +import mytrain + +cuda = torch.cuda.is_available() + +torch.manual_seed(1337) +if cuda: + torch.cuda.manual_seed(1337) +# 1.data +# kwargs = {'num_workers': 4, 'pin_memory': True} if cuda else {} +train_path='E:\\gxq\\256x256\\train\\' +valid_path='E:\\gxq\\256x256\\valid\\' +test_path='E:\\gxq\\256x256\\test\\' +train_set,val_set,test_set=mytrain.getData(train_path,valid_path,test_path) +train_loader = torch.utils.data.DataLoader( + dataset.MyDataset(train_set,filepath=train_path), batch_size=16, shuffle=True) +val_loader = torch.utils.data.DataLoader( + dataset.MyDataset(val_set,filepath=valid_path), batch_size=16, shuffle=True) +test_loader = torch.utils.data.DataLoader( + dataset.MyDataset(test_set,filepath=test_path), batch_size=16, shuffle=False) +# 2.model +model = deeplabv3.DeepLab(n_class=6,pretrained=True) +start_epoch = 0 +start_iteration = 1 + +if cuda: + model = model.cuda() + +# 3.optimizer +optim=torch.optim.SGD(model.parameters(),lr=2.0e-10,weight_decay=0.0005,momentum=0.99) +out=osp.join('E:\\gxq\\256x256\\', 'DeepLvb_logs', datetime.datetime.now().strftime('%Y%m%d_%H%M%S.%f')) +if not osp.exists(out): + os.makedirs(out) +max_iteration=100000 +trainer =mytrain.Trainer( + cuda=cuda, + model=model, + optimizer=optim, + train_loader=train_loader, + val_loader=val_loader, + test_loader=test_loader, + out=out, + max_iter=max_iteration, + interval_validate=4000, + ) +trainer.epoch = start_epoch +trainer.iteration = start_iteration +trainer.train() \ No newline at end of file diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_fcn8s_atonce.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_fcn8s_atonce.py" new file mode 100644 index 0000000000000000000000000000000000000000..5199e350b0ed45b052a89067021680fde77d2491 --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_fcn8s_atonce.py" @@ -0,0 +1,128 @@ +# -*- coding: utf-8 -*- +""" +训练fcn8s +""" + +import datetime +import os +import os.path as osp + + +import torch + +import dataset +import fcns +import mytrain + +cuda = torch.cuda.is_available() + +torch.manual_seed(1337) +if cuda: + torch.cuda.manual_seed(1337) +# 1.data +# kwargs = {'num_workers': 4, 'pin_memory': True} if cuda else {} + +train_path='E:\\gxq\\256x256\\train\\' +valid_path='E:\\gxq\\256x256\\valid\\' +test_path='E:\\gxq\\256x256\\test\\' +train_set,val_set,test_set=mytrain.getData(train_path,valid_path,test_path) +train_loader = torch.utils.data.DataLoader( + dataset.MyDataset(train_set,filepath=train_path), batch_size=16, shuffle=True) +val_loader = torch.utils.data.DataLoader( + dataset.MyDataset(val_set,filepath=valid_path), batch_size=16, shuffle=True) +test_loader = torch.utils.data.DataLoader( + dataset.MyDataset(test_set,filepath=test_path), batch_size=16, shuffle=False) +# 2.model +model = fcns.FCN8sAtOnce(n_class=6) +start_epoch = 0 +start_iteration = 1 + +vgg16 =fcns.VGG16(pretrained=False) +model.copy_params_from_vgg16(vgg16) +if cuda: + model = model.cuda() + +# 3.optimizer +optim=torch.optim.SGD(model.parameters(),lr=2.0e-10,weight_decay=0.0005,momentum=0.99) +out=osp.join('E:\\gxq\\256x256\\', 'FCN8s_logs', datetime.datetime.now().strftime('%Y%m%d_%H%M%S.%f')) +if not osp.exists(out): + os.makedirs(out) +max_iteration=100000 +trainer =mytrain.Trainer( + cuda=cuda, + model=model, + optimizer=optim, + train_loader=train_loader, + val_loader=val_loader, + test_loader=test_loader, + out=out, + max_iter=max_iteration, + interval_validate=4000, + ) +trainer.epoch = start_epoch +trainer.iteration = start_iteration +trainer.train() +import torch +from torch.autograd import Variable +import utils +import numpy as np +def _fast_hist(label_true, label_pred, n_class): + mask = (label_true >= 0) & (label_true < n_class) + hist = np.bincount( + n_class * label_true[mask].astype(int) + + label_pred[mask], minlength=n_class ** 2).reshape(n_class, n_class) + return hist +def iou(label_trues, label_preds, n_class=6): + """Returns accuracy score evaluation result. + - overall accuracy + - mean accuracy + - mean IU + - fwavacc + """ + hist = np.zeros((n_class, n_class)) + for lt, lp in zip(label_trues, label_preds): + hist += _fast_hist(lt.flatten(), lp.flatten(), n_class) + + with np.errstate(divide='ignore', invalid='ignore'): + iu = np.diag(hist) / ( + hist.sum(axis=1) + hist.sum(axis=0) - np.diag(hist) + ) + + return hist,iu + +def test_model(model,test_loader,best_model): + test_loss=0 + label_preds=[] + label_trues=[] + model.load_state_dict(torch.load(best_model)['model_state_dict']) + + for i,(data,target) in enumerate(test_loader): + model.eval() + if torch.cuda.is_available(): + data=data.cuda() + target=target.cuda() + model=model.cuda() + data, target = Variable(data), Variable(target) + with torch.no_grad(): + score=model(data.float()) + loss = utils.cross_entropy2d(score, target, + size_average=False) + loss_data = loss.data.item() + + if np.isnan(loss_data): + raise ValueError('loss is nan while testing') + + + #imgs = data.data.cpu() + lbl_pred = score.data.max(1)[1].cpu().numpy()[:, :, :] + lbl_true = target.data.cpu().numpy() + label_trues.append(lbl_true) + label_preds.append(lbl_pred) + + test_loss+=loss_data + test_loss/=len(test_loader) + print('test loss:',test_loss) + hist,iu=iou(label_trues, label_preds) + print(hist) + print(iu) +test_model(model,test_loader,r'E:\gxq\256x256\FCN8s_logs\20210312_101013.686216\model_best.pth.tar') diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_unet.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_unet.py" new file mode 100644 index 0000000000000000000000000000000000000000..2a707c21e775b1e1b300293b6faa0d5d7160a8ce --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/train_unet.py" @@ -0,0 +1,74 @@ +# -*- coding: utf-8 -*- +""" +训练unet +""" + +import os +#os.environ['KMP_DUPLICATE_LIB_OK']='True' + +import datetime + +import os.path as osp + + +import torch +torch.cuda.empty_cache() +import dataset +import unet +import mytrain + +cuda = torch.cuda.is_available() + +torch.manual_seed(1337) +if cuda: + torch.cuda.manual_seed(1337) +# 1.data +# kwargs = {'num_workers': 4, 'pin_memory': True} if cuda else {} +#修改为自己的数据路径 +train_path='E:\\gxq\\256x256\\train\\' +valid_path='E:\\gxq\\256x256\\valid\\' +test_path='E:\\gxq\\256x256\\test\\' +train_set,val_set,test_set=mytrain.getData(train_path,valid_path,test_path) +train_loader = torch.utils.data.DataLoader( + dataset.MyDataset(train_set,filepath=train_path), batch_size=16, shuffle=True) +val_loader = torch.utils.data.DataLoader( + dataset.MyDataset(val_set,filepath=valid_path), batch_size=16, shuffle=True) +test_loader = torch.utils.data.DataLoader( + dataset.MyDataset(test_set,filepath=test_path), batch_size=16, shuffle=False) +''' +train_set,val_set=trainer.get_train_val() +train_loader = torch.utils.data.DataLoader( + dataset.MyDataset(train_set), batch_size=16, shuffle=True) +val_loader = torch.utils.data.DataLoader( + dataset.MyDataset(val_set), batch_size=16, shuffle=True) +''' +# 2.model +model = unet.Unet() +start_epoch = 0 +start_iteration = 1 + + +if cuda: + model = model.cuda() + +# 3.optimizer +optim=torch.optim.SGD(model.parameters(),lr=2.0e-10,weight_decay=0.0005,momentum=0.99) +out=osp.join('E:\\gxq\\256x256\\', 'unet_logs', datetime.datetime.now().strftime('%Y%m%d_%H%M%S.%f')) +if not osp.exists(out): + os.makedirs(out) +max_iteration=100000 +trainer =mytrain.Trainer( + cuda=cuda, + model=model, + optimizer=optim, + train_loader=train_loader, + val_loader=val_loader, + test_loader=test_loader, + out=out, + max_iter=max_iteration, + interval_validate=4000, + ) +trainer.epoch = start_epoch +trainer.iteration = start_iteration +trainer.train() + diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/unet.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/unet.py" new file mode 100644 index 0000000000000000000000000000000000000000..aec6a6a2994daeef1f2874dc8c5c217c5b08aa8a --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/unet.py" @@ -0,0 +1,189 @@ +# -*- coding: utf-8 -*- +""" +unet +""" +import torch.nn as nn +import torch + +import torch.nn.functional as F + + +class DoubleConv(nn.Module): + '''(conv-->BN-->Relu)* 2''' + def __init__(self, in_channels, out_channels, mid_channels=None): + super().__init__() + if not mid_channels: + mid_channels = out_channels + self.double_conv = nn.Sequential( + nn.Conv2d(in_channels, mid_channels, kernel_size=3, padding=1), + nn.BatchNorm2d(mid_channels), + nn.ReLU(inplace=True), + nn.Conv2d(mid_channels, out_channels, kernel_size=3, padding=1), + nn.BatchNorm2d(out_channels), + nn.ReLU(inplace=True) + ) + + def forward(self,x): + return self.double_conv(x) +class Down(nn.Module): + '''Downscaling with maxpool then double_conv''' + def __init__(self,in_channels,out_channels): + super().__init__() + self.maxpool_conv=nn.Sequential( + nn.MaxPool2d(2), + DoubleConv(in_channels, out_channels) + + ) + def forward(self,x): + return self.maxpool_conv(x) +class Up(nn.Module): + '''upscaling then double conv''' + def __init__(self,in_channels,out_channels,bilinear=True): + super().__init__() + # if bilinear,use the normal convolutions to reduce the number of channels + if bilinear: + self.up=nn.Upsample(scale_factor=2,mode='bilinear',align_corners=True) + self.conv=DoubleConv(in_channels, out_channels,in_channels//2) + else: + self.up=nn.ConvTranspose2d(in_channels, in_channels//2, kernel_size=2,stride=2) + self.conv=DoubleConv(in_channels, out_channels) + def forward(self,x1,x2): + x1=self.up(x1) + diffY = x2.size()[2] - x1.size()[2] + diffX = x2.size()[3] - x1.size()[3] + x1 = F.pad(x1, [diffX // 2, diffX - diffX // 2, diffY // 2, diffY - diffY // 2]) + + x = torch.cat([x2, x1], dim=1) + return self.conv(x) +class OutConv(nn.Module): + def __init__(self,in_channels,out_channels): + super(OutConv,self).__init__() + self.conv=nn.Conv2d(in_channels, out_channels, kernel_size=1) + def forward(self,x): + return self.conv(x) +class Unet(nn.Module): + def __init__(self,n_channels=3,n_classes=6,bilinear=True): + super(Unet,self).__init__() + self.n_channels=n_channels + self.n_classes=n_classes + self.bilinear=bilinear + + self.inc=DoubleConv(n_channels,64) + self.down1=Down(64,128) + self.down2=Down(128,256) + self.down3=Down(256,512) + factor=2 if bilinear else 1 + self.down4=Down(512, 1024//factor) + self.up1=Up(1024,512//factor,bilinear) + self.up2=Up(512,256//factor,bilinear) + self.up3=Up(256,128//factor,bilinear) + self.up4=Up(128,64,bilinear) + self.outc=OutConv(64, n_classes) + def forward(self,x): + + x1=self.inc(x) + x2=self.down1(x1) + x3=self.down2(x2) + x4=self.down3(x3) + x5=self.down4(x4) + x=self.up1(x5,x4) + x=self.up2(x,x3) + x=self.up3(x,x2) + x=self.up4(x,x1) + logits=self.outc(x) + return logits + +class unetConv2(nn.Module): + def __init__(self,in_size,out_size,is_batchnorm): + super(unetConv2,self).__init__() + if is_batchnorm: + self.conv1 = nn.Sequential( + nn.Conv2d(in_size, out_size, 3, 1, 0), nn.BatchNorm2d(out_size), nn.ReLU() + ) + self.conv2 = nn.Sequential( + nn.Conv2d(out_size, out_size, 3, 1, 0), nn.BatchNorm2d(out_size), nn.ReLU() + ) + else: + self.conv1 = nn.Sequential(nn.Conv2d(in_size, out_size, 3, 1, 0), nn.ReLU()) + self.conv2 = nn.Sequential(nn.Conv2d(out_size, out_size, 3, 1, 0), nn.ReLU()) + + def forward(self, inputs): + #inputs=inputs.permute([0,3,1,2]) + #img_new= np.transpose(inputs, (0,3,1,2)) + + outputs = self.conv1(inputs) + + outputs = self.conv2(outputs) + return outputs +class unetUp(nn.Module): + def __init__(self,in_size,out_size,is_deconv): + super(unetUp,self).__init__() + self.conv = unetConv2(in_size, out_size, False) + if is_deconv: + self.up = nn.ConvTranspose2d(in_size, out_size, kernel_size=2, stride=2) + else: + self.up = nn.UpsamplingBilinear2d(scale_factor=2) + + def forward(self, x1, x2): + x1 = self.up(x1) + diffY = x2.size()[2] - x1.size()[2] + diffX = x2.size()[3] - x1.size()[3] + x1 = F.pad(x1, [diffX // 2, diffX - diffX // 2, diffY // 2, diffY - diffY // 2]) + x = torch.cat([x1, x2], dim=1) + return self.conv(x) +class unet(nn.Module): + def __init__(self,feature_scale=4,n_class=6,is_deconv=True,in_channels=3,is_batchnorm=True): + super(unet,self).__init__() + self.is_deconv=is_deconv + self.in_channels=in_channels + self.is_batchnorm=is_batchnorm + self.feature_scale=feature_scale + filters=[64,128,256,512,1024] + filters=[int(x/self.feature_scale) for x in filters] + # downsampling + self.conv1 = unetConv2(self.in_channels, filters[0], self.is_batchnorm) + self.maxpool1 = nn.MaxPool2d(kernel_size=2) + + self.conv2 = unetConv2(filters[0], filters[1], self.is_batchnorm) + self.maxpool2 = nn.MaxPool2d(kernel_size=2) + + self.conv3 = unetConv2(filters[1], filters[2], self.is_batchnorm) + self.maxpool3 = nn.MaxPool2d(kernel_size=2) + + self.conv4 = unetConv2(filters[2], filters[3], self.is_batchnorm) + self.maxpool4 = nn.MaxPool2d(kernel_size=2) + + self.center = unetConv2(filters[3], filters[4], self.is_batchnorm) + + # upsampling + self.up_concat4 = unetUp(filters[4], filters[3], self.is_deconv) + self.up_concat3 = unetUp(filters[3], filters[2], self.is_deconv) + self.up_concat2 = unetUp(filters[2], filters[1], self.is_deconv) + self.up_concat1 = unetUp(filters[1], filters[0], self.is_deconv) + + # final conv (without any concat) + self.final = nn.Conv2d(filters[0], n_class, 1) + + def forward(self,x): + + conv1 = self.conv1(x) + maxpool1 = self.maxpool1(conv1) + + conv2 = self.conv2(maxpool1) + maxpool2 = self.maxpool2(conv2) + + conv3 = self.conv3(maxpool2) + maxpool3 = self.maxpool3(conv3) + + conv4 = self.conv4(maxpool3) + maxpool4 = self.maxpool4(conv4) + + center = self.center(maxpool4) + up4 = self.up_concat4( center,conv4) + up3 = self.up_concat3( up4,conv3) + up2 = self.up_concat2( up3,conv2) + up1 = self.up_concat1( up2,conv1) + + final = self.final(up1) + + return final \ No newline at end of file diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/utils.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/utils.py" new file mode 100644 index 0000000000000000000000000000000000000000..55ea1345d64c6b9e1878bcacd17509d36e8fc0be --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/utils.py" @@ -0,0 +1,439 @@ +# -*- coding: utf-8 -*- +""" +定义函数工具 +""" + +import numpy as np +from distutils.version import LooseVersion +import math +import shutil +import skimage.io +from torch.autograd import Variable +import torch.nn.functional as F +import tqdm +import torch +import copy +import math +import warnings +import six +import skimage +import skimage.color +import skimage.transform +import scipy.ndimage +import torch.nn as nn +import pkg_resources + +try: + import cv2 +except ImportError: + cv2 = None + +def initialize_weights(*models): + for model in models: + for m in model.modules(): + if isinstance(m,nn.Conv2d): + nn.init.kaiming_normal_(m.weight.data,nonlinearity='relu') + elif isinstance(m,nn.BatchNorm2d): + m.weight.data.fill_(1.) + m.bias.data.fill_(1e-4) + elif isinstance(m,nn.Linear): + m.weight.data.normal_(0.0,0.0001) + m.bias.data.zero_() + +# 模型评价指标 + +def _fast_hist(label_true, label_pred, n_class): + mask = (label_true >= 0) & (label_true < n_class) + hist = np.bincount( + n_class * label_true[mask].astype(int) + + label_pred[mask], minlength=n_class ** 2).reshape(n_class, n_class) + return hist + + +def label_accuracy_score(label_trues, label_preds, n_class=6): + """Returns accuracy score evaluation result. + - overall accuracy + - mean accuracy + - mean IU + - fwavacc + """ + hist = np.zeros((n_class, n_class)) + for lt, lp in zip(label_trues, label_preds): + hist += _fast_hist(lt.flatten(), lp.flatten(), n_class) + acc = np.diag(hist).sum() / hist.sum() + with np.errstate(divide='ignore', invalid='ignore'): + acc_cls = np.diag(hist) / hist.sum(axis=1) + acc_cls = np.nanmean(acc_cls) + with np.errstate(divide='ignore', invalid='ignore'): + iu = np.diag(hist) / ( + hist.sum(axis=1) + hist.sum(axis=0) - np.diag(hist) + ) + mean_iu = np.nanmean(iu) + freq = hist.sum(axis=1) / hist.sum() + fwavacc = (freq[freq > 0] * iu[freq > 0]).sum() + return acc, acc_cls, mean_iu, fwavacc + +# 损失函数 +''' +def cross_entropy2d(inputs,targets,weight=None,size_average=True): + # inputs:(n,c,h,w) targets:(n,h,w) log_p:(n,c,h,w) + n,c,h,w=inputs.size() + nt,ht,wt=targets.size() + if h!=ht and w!=wt: # 若输入维度不同则进行处理 + inputs= F.interpolate(inputs, size=(ht, wt), mode="bilinear", align_corners=True) + + + if LooseVersion(torch.__version__)=0] + log_p = log_p.view(-1, c) + # target: (n*h*w,) + mask = targets >= 0 + targets = targets[mask] + + loss = F.nll_loss(log_p, targets, weight=weight, reduction='sum') + if size_average: + loss /= mask.data.sum() + return loss +''' +def cross_entropy2d(input, target, weight=None, size_average=True): + n, c, h, w = input.size() + nt, ht, wt = target.size() + target=target.long() + # Handle inconsistent size between input and target + if h != ht and w != wt: # upsample labels + input = F.interpolate(input, size=(ht, wt), mode="bilinear", align_corners=True) + + input = input.transpose(1, 2).transpose(2, 3).contiguous().view(-1, c) + target = target.view(-1) + loss = F.cross_entropy( + input, target, weight=weight, size_average=size_average + ) + return loss + +# 定义visualization +## color util +def bitget(byteval, idx): + return ((byteval & (1 << idx)) != 0) +def label_colormap(N=256): + cmap = np.zeros((N, 3)) + for i in six.moves.range(0, N): + id = i + r, g, b = 0, 0, 0 + for j in six.moves.range(0, 8): + r = np.bitwise_or(r, (bitget(id, 0) << 7 - j)) + g = np.bitwise_or(g, (bitget(id, 1) << 7 - j)) + b = np.bitwise_or(b, (bitget(id, 2) << 7 - j)) + id = (id >> 3) + cmap[i, 0] = r + cmap[i, 1] = g + cmap[i, 2] = b + cmap = cmap.astype(np.float32) / 255 + return cmap +def visualize_label_colormap(cmap): + n_colors = len(cmap) + ret = np.zeros((n_colors, 10 * 10, 3)) + for i in six.moves.range(n_colors): + ret[i, ...] = cmap[i] + return ret.reshape((n_colors * 10, 10, 3)) +def get_label_colortable(n_labels, shape): + if cv2 is None: + raise RuntimeError('get_label_colortable requires OpenCV (cv2)') + rows, cols = shape + if rows * cols < n_labels: + raise ValueError + cmap = label_colormap(n_labels) + table = np.zeros((rows * cols, 50, 50, 3), dtype=np.uint8) + for lbl_id, color in enumerate(cmap): + color_uint8 = (color * 255).astype(np.uint8) + table[lbl_id, :, :] = color_uint8 + text = '{:<2}'.format(lbl_id) + cv2.putText(table[lbl_id], text, (5, 35), + cv2.cv.CV_FONT_HERSHEY_SIMPLEX, 0.8, (255, 255, 255), 3) + table = table.reshape(rows, cols, 50, 50, 3) + table = table.transpose(0, 2, 1, 3, 4) + table = table.reshape(rows * 50, cols * 50, 3) + return table +## visualization +def centerize(src, dst_shape, margin_color=None): + """Centerize image for specified image size + @param src: image to centerize + @param dst_shape: image shape (height, width) or (height, width, channel) + """ + if src.shape[:2] == dst_shape[:2]: + return src + centerized = np.zeros(dst_shape, dtype=src.dtype) + if margin_color: + centerized[:, :] = margin_color + pad_vertical, pad_horizontal = 0, 0 + h, w = src.shape[:2] + dst_h, dst_w = dst_shape[:2] + if h < dst_h: + pad_vertical = (dst_h - h) // 2 + if w < dst_w: + pad_horizontal = (dst_w - w) // 2 + centerized[pad_vertical:pad_vertical + h, + pad_horizontal:pad_horizontal + w] = src + return centerized +def _tile_images(imgs, tile_shape, concatenated_image): + """Concatenate images whose sizes are same. + @param imgs: image list which should be concatenated + @param tile_shape: shape for which images should be concatenated + @param concatenated_image: returned image. + if it is None, new image will be created. + """ + y_num, x_num = tile_shape + one_width = imgs[0].shape[1] + one_height = imgs[0].shape[0] + if concatenated_image is None: + if len(imgs[0].shape) == 3: + n_channels = imgs[0].shape[2] + assert all(im.shape[2] == n_channels for im in imgs) + concatenated_image = np.zeros( + (one_height * y_num, one_width * x_num, n_channels), + dtype=np.uint8, + ) + else: + concatenated_image = np.zeros( + (one_height * y_num, one_width * x_num), dtype=np.uint8) + for y in six.moves.range(y_num): + for x in six.moves.range(x_num): + i = x + y * x_num + if i >= len(imgs): + pass + else: + concatenated_image[y * one_height:(y + 1) * one_height, + x * one_width:(x + 1) * one_width] = imgs[i] + return concatenated_image + + +def get_tile_image(imgs, tile_shape=None, result_img=None, margin_color=None): + """Concatenate images whose sizes are different. + @param imgs: image list which should be concatenated + @param tile_shape: shape for which images should be concatenated + @param result_img: numpy array to put result image + """ + def resize(*args, **kwargs): + # anti_aliasing arg cannot be passed to skimage<0.14 + # use LooseVersion to allow 0.14dev. + if LooseVersion(skimage.__version__) < LooseVersion('0.14'): + kwargs.pop('anti_aliasing', None) + return skimage.transform.resize(*args, **kwargs) + + def get_tile_shape(img_num): + x_num = 0 + y_num = int(math.sqrt(img_num)) + while x_num * y_num < img_num: + x_num += 1 + return y_num, x_num + + if tile_shape is None: + tile_shape = get_tile_shape(len(imgs)) + + # get max tile size to which each image should be resized + max_height, max_width = np.inf, np.inf + for img in imgs: + max_height = min([max_height, img.shape[0]]) + max_width = min([max_width, img.shape[1]]) + + # resize and concatenate images + for i, img in enumerate(imgs): + h, w = img.shape[:2] + dtype = img.dtype + h_scale, w_scale = max_height / h, max_width / w + scale = min([h_scale, w_scale]) + h, w = int(scale * h), int(scale * w) + img = resize( + image=img, + output_shape=(h, w), + mode='reflect', + preserve_range=True, + anti_aliasing=True, + ).astype(dtype) + if len(img.shape) == 3: + img = centerize(img, (max_height, max_width, 3), margin_color) + else: + img = centerize(img, (max_height, max_width), margin_color) + imgs[i] = img + return _tile_images(imgs, tile_shape, result_img) + + +def label2rgb(lbl, img=None, label_names=None, n_labels=None, + alpha=0.5, thresh_suppress=0): + if label_names is None: + if n_labels is None: + n_labels = lbl.max() + 1 # +1 for bg_label 0 + else: + if n_labels is None: + n_labels = len(label_names) + else: + assert n_labels == len(label_names) + cmap = label_colormap(n_labels) + cmap = (cmap * 255).astype(np.uint8) + + lbl_viz = cmap[lbl] + lbl_viz[lbl == -1] = (0, 0, 0) # unlabeled + + if img is not None: + img_gray = skimage.color.rgb2gray(img) + img_gray = skimage.color.gray2rgb(img_gray) + img_gray *= 255 + lbl_viz = alpha * lbl_viz + (1 - alpha) * img_gray + lbl_viz = lbl_viz.astype(np.uint8) + + if label_names is None: + return lbl_viz + + # cv2 is required only if label_names is not None + import cv2 + if cv2 is None: + warnings.warn('label2rgb with label_names requires OpenCV (cv2), ' + 'so ignoring label_names values.') + return lbl_viz + + np.random.seed(1234) + for label in np.unique(lbl): + if label == -1: + continue # unlabeled + + mask = lbl == label + if 1. * mask.sum() / mask.size < thresh_suppress: + continue + mask = (mask * 255).astype(np.uint8) + y, x = scipy.ndimage.center_of_mass(mask) + y, x = map(int, [y, x]) + + if lbl[y, x] != label: + Y, X = np.where(mask) + point_index = np.random.randint(0, len(Y)) + y, x = Y[point_index], X[point_index] + + text = label_names[label] + font_face = cv2.FONT_HERSHEY_SIMPLEX + font_scale = 0.7 + thickness = 2 + text_size, baseline = cv2.getTextSize( + text, font_face, font_scale, thickness) + + def get_text_color(color): + if color[0] * 0.299 + color[1] * 0.587 + color[2] * 0.114 > 170: + return (0, 0, 0) + return (255, 255, 255) + + color = get_text_color(lbl_viz[y, x]) + cv2.putText(lbl_viz, text, + (x - text_size[0] // 2, y), + font_face, font_scale, color, thickness) + return lbl_viz + + +def visualize_segmentation(**kwargs): + """Visualize segmentation. + Parameters + ---------- + img: ndarray + Input image to predict label. + lbl_true: ndarray + Ground truth of the label. + lbl_pred: ndarray + Label predicted. + n_class: int + Number of classes. + label_names: dict or list + Names of each label value. + Key or index is label_value and value is its name. + Returns + ------- + img_array: ndarray + Visualized image. + """ + img = kwargs.pop('img', None) + lbl_true = kwargs.pop('lbl_true', None) + lbl_pred = kwargs.pop('lbl_pred', None) + n_class = kwargs.pop('n_class', None) + label_names = kwargs.pop('label_names', None) + if kwargs: + raise RuntimeError( + 'Unexpected keys in kwargs: {}'.format(kwargs.keys())) + + if lbl_true is None and lbl_pred is None: + raise ValueError('lbl_true or lbl_pred must be not None.') + + lbl_true = copy.deepcopy(lbl_true) + lbl_pred = copy.deepcopy(lbl_pred) + + mask_unlabeled = None + viz_unlabeled = None + if lbl_true is not None: + mask_unlabeled = lbl_true == -1 + lbl_true[mask_unlabeled] = 0 + viz_unlabeled = ( + np.random.random((lbl_true.shape[0], lbl_true.shape[1], 3)) * 255 + ).astype(np.uint8) + if lbl_pred is not None: + lbl_pred[mask_unlabeled] = 0 + + vizs = [] + + if lbl_true is not None: + viz_trues = [ + img, + label2rgb(lbl_true, label_names=label_names, n_labels=n_class), + label2rgb(lbl_true, img, label_names=label_names, + n_labels=n_class), + ] + viz_trues[1][mask_unlabeled] = viz_unlabeled[mask_unlabeled] + viz_trues[2][mask_unlabeled] = viz_unlabeled[mask_unlabeled] + vizs.append(get_tile_image(viz_trues, (1, 3))) + + if lbl_pred is not None: + viz_preds = [ + img, + label2rgb(lbl_pred, label_names=label_names, n_labels=n_class), + label2rgb(lbl_pred, img, label_names=label_names, + n_labels=n_class), + ] + if mask_unlabeled is not None and viz_unlabeled is not None: + viz_preds[1][mask_unlabeled] = viz_unlabeled[mask_unlabeled] + viz_preds[2][mask_unlabeled] = viz_unlabeled[mask_unlabeled] + vizs.append(get_tile_image(viz_preds, (1, 3))) + + if len(vizs) == 1: + return vizs[0] + elif len(vizs) == 2: + return get_tile_image(vizs, (2, 1)) + else: + raise RuntimeError + +# 从模型中获得参数 +def get_parameters(model, bias=False): + import torch.nn as nn + modules_skipped = ( + nn.ReLU, + nn.MaxPool2d, + nn.Dropout2d, + nn.Sequential, + + ) + for m in model.modules(): + if isinstance(m, nn.Conv2d): + if bias: + yield m.bias + else: + yield m.weight + elif isinstance(m, nn.ConvTranspose2d): + # weight is frozen because it is just a bilinear upsampling + if bias: + assert m.bias is None + elif isinstance(m, modules_skipped): + continue + else: + raise ValueError('Unexpected module: %s' % str(m)) + +# 定义模型转换caffe-->pytorch + + diff --git "a/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/view_log.py" "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/view_log.py" new file mode 100644 index 0000000000000000000000000000000000000000..4c15ebcb60390e6ed39f4324d48f02279dc15eac --- /dev/null +++ "b/code/2021_autumn/\351\203\255\351\233\252\347\220\264_\345\237\272\344\272\216\345\215\267\347\247\257\347\245\236\347\273\217\345\205\203\347\275\221\347\273\234\345\222\214\346\263\250\346\204\217\345\212\233\346\234\272\345\210\266\347\232\204\351\201\245\346\204\237\345\233\276\345\203\217\345\234\260\347\211\251\350\246\206\347\233\226\345\210\206\347\261\273/view_log.py" @@ -0,0 +1,66 @@ +# -*- coding: utf-8 -*- +""" +view log +""" +from __future__ import print_function +import os.path as osp +import sys +import time +import numpy as np +import pandas as pd +def print_bar(title='',width=80): + if title: + title=' '+title+' ' + length=len(title) + if length%2==0: + length_left=length_right=length//2 + else: + length_left=length//2 + length_right=length-length_left + print('='*(width//2-1-length_left)+title+'='*(width//2-length_right)) +def view_log(logfile): + pd.set_option('display.width',200) + pd.set_option('display.float_format',lambda x:'%.3f'%x) + + while True: + try: + df=pd.read_csv(logfile) + df=df.set_index(['epoch','iteration']) + train_cols,valid_cols,else_cols=[],[],[] + for col in df.columns: + if col.startswith('validation/') or col.startswith('valid/'): + valid_cols.append(col) + elif col.startswith('train/'): + train_cols.append(col) + else: + else_cols.append(col) + width=len(' '.join(['epoch','iteration'])+' '.join(train_cols+else_cols)+' ') + try: + df_train=df[train_cols+else_cols].dropna(thresh=len(train_cols)) + except: + df_train=df[train_cols+else_cols].dropna() + if not df_train.empty: + print_bar('train',width=width) + print(df_train.tail(n=5)) + print() + try: + df_valid=df[valid_cols+else_cols].dropna(thresh=len(valid_cols)) + except: + df_valid=df[valid_cols+else_cols].dropna() + if not df_valid.empty: + print_bar('valid',width=width) + print(df_valid.tail(n=3)) + print() + print_bar(width=width) + except KeyboardInterrupt: + break + except IOError as e: + print(chr(27) + "[2J") + print(e) + time.sleep(1) + continue + except Exception as e: + print(e) + break +logfile=r'E:\gxq\gxq\FCN8s_logs\20210308_172459.915182\log.csv' +view_log(logfile) \ No newline at end of file